feat: improve call handling with manual hangup support and UI updates

This commit is contained in:
AlexisDanlos 2025-06-18 18:58:05 +02:00 committed by stcb
parent 71485a4346
commit 68761b6e44
2 changed files with 59 additions and 17 deletions

View File

@ -47,10 +47,8 @@ class CallService {
_manualHangupFlag = true; // Mark that hangup was manual
print('CallService: Manual hangup flag set to $_manualHangupFlag');
} else {
print(
'CallService: No pending SIM switch to cancel, but setting manual hangup flag');
_manualHangupFlag =
true; // Still mark as manual even if no pending switch
print('CallService: No pending SIM switch to cancel');
// Don't set manual hangup flag if there's no SIM switch to cancel
}
}
@ -97,8 +95,15 @@ class CallService {
'CallService: State changed to $state, wasPhoneLocked: $wasPhoneLocked');
_callStateController.add(state);
if (state == "disconnected" || state == "disconnecting") {
print('CallService: ========== CALL DISCONNECTED ==========');
print(
'CallService: _pendingSimSwitch: ${_pendingSimSwitch != null}');
print('CallService: _manualHangupFlag: $_manualHangupFlag');
print('CallService: _isCallPageVisible: $_isCallPageVisible');
// Close call page if no pending SIM switch OR if it was a manual hangup
if (_pendingSimSwitch == null || _manualHangupFlag) {
print('CallService: Condition met, calling _closeCallPage()');
_closeCallPage();
// Only reset manual hangup flag after successful page close
if (_manualHangupFlag) {
@ -106,6 +111,8 @@ class CallService {
'CallService: Resetting manual hangup flag after page close');
_manualHangupFlag = false;
}
} else {
print('CallService: NOT closing call page - condition not met');
}
if (wasPhoneLocked) {
await _channel.invokeMethod("callEndedFromFlutter");
@ -156,10 +163,24 @@ class CallService {
case "callEnded":
case "callRemoved":
wasPhoneLocked = call.arguments["wasPhoneLocked"] as bool? ?? false;
print(
'CallService: Call ended/removed, wasPhoneLocked: $wasPhoneLocked'); // Only close call page if there's no pending SIM switch AND no manual hangup in progress
if (_pendingSimSwitch == null && !_manualHangupFlag) {
print('CallService: ========== CALL ENDED/REMOVED ==========');
print('CallService: wasPhoneLocked: $wasPhoneLocked');
print('CallService: _pendingSimSwitch: ${_pendingSimSwitch != null}');
print('CallService: _manualHangupFlag: $_manualHangupFlag');
print('CallService: _isCallPageVisible: $_isCallPageVisible');
// Only close call page if there's no pending SIM switch OR if it was a manual hangup during SIM switch
if (_pendingSimSwitch == null || _manualHangupFlag) {
print('CallService: Condition met, calling _closeCallPage()');
_closeCallPage();
// Reset manual hangup flag after closing page
if (_manualHangupFlag) {
print(
'CallService: Resetting manual hangup flag after callEnded');
_manualHangupFlag = false;
}
} else {
print('CallService: NOT closing call page - condition not met');
}
if (wasPhoneLocked) {
await _channel.invokeMethod("callEndedFromFlutter");
@ -388,7 +409,7 @@ class CallService {
return;
}
_activeCallNumber = currentPhoneNumber;
Navigator.pushReplacement(
Navigator.push(
context,
MaterialPageRoute(
settings: const RouteSettings(name: '/call'),
@ -468,7 +489,7 @@ class CallService {
}
print(
'CallService: Closing call page, _isCallPageVisible: $_isCallPageVisible');
'CallService: Closing call page, _isCallPageVisible: $_isCallPageVisible, _pendingSimSwitch: ${_pendingSimSwitch != null}, _manualHangupFlag: $_manualHangupFlag');
if (Navigator.canPop(context)) {
print('CallService: Popping call page');
Navigator.pop(context);
@ -556,18 +577,34 @@ class CallService {
// Getter to check if there's a pending SIM switch
static bool get hasPendingSimSwitch => _pendingSimSwitch != null;
Future<Map<String, dynamic>> hangUpCall(BuildContext context) async {
try {
print('CallService: Hanging up call');
print('CallService: ========== HANGUP INITIATED ==========');
print('CallService: _pendingSimSwitch: ${_pendingSimSwitch != null}');
print('CallService: _manualHangupFlag: $_manualHangupFlag');
print('CallService: _isCallPageVisible: $_isCallPageVisible');
final result = await _channel.invokeMethod('hangUpCall');
print('CallService: hangUpCall result: $result');
final resultMap = Map<String, dynamic>.from(result as Map);
if (resultMap["status"] != "ended") {
ScaffoldMessenger.of(context).showSnackBar(
SnackBar(content: Text("Failed to end call")),
);
} else {
// If hangup was successful, ensure call page closes after a short delay
// This is a fallback in case the native call state events don't fire properly
Future.delayed(const Duration(milliseconds: 1500), () {
if (_isCallPageVisible) {
print(
'CallService: FALLBACK - Force closing call page after hangup');
_closeCallPage();
_manualHangupFlag = false; // Reset flag
}
});
}
return resultMap;
} catch (e) {
print("CallService: Error hanging up call: $e");

View File

@ -284,6 +284,12 @@ class _CallPageState extends State<CallPage> {
print(
'CallPage: Initiating manual hangUp - canceling any pending SIM switch');
// Immediately mark call as inactive to allow page navigation
setState(() {
_isCallActive = false;
_callStatus = "Ending Call...";
});
// Cancel any pending SIM switch since user is manually hanging up
_callService.cancelPendingSimSwitch();
@ -327,13 +333,12 @@ class _CallPageState extends State<CallPage> {
print(
'CallPage: Building UI, _callStatus: $_callStatus, route: ${ModalRoute.of(context)?.settings.name ?? "unknown"}');
return PopScope(
canPop: !_isCallActive,
canPop:
true, // Always allow popping - CallService manages when it's appropriate
onPopInvoked: (didPop) {
if (!didPop && _isCallActive) {
ScaffoldMessenger.of(context).showSnackBar(
SnackBar(content: Text('Cannot leave during an active call')),
);
}
print(
'CallPage: PopScope onPopInvoked - didPop: $didPop, _isCallActive: $_isCallActive, _callStatus: $_callStatus');
// No longer prevent popping during active calls - CallService handles this
},
child: Scaffold(
body: Container(