Fixed an issue where you could answer calls without having the mic permission

pull/1018/head
Morgan Pretty 7 months ago
parent e1aedb36da
commit 597f94a954

@ -902,8 +902,22 @@ extension ConversationVC:
// For call info messages show the "call missed" modal
guard cellViewModel.variant != .infoCall else {
let callMissedTipsModal: CallMissedTipsModal = CallMissedTipsModal(caller: cellViewModel.authorName)
present(callMissedTipsModal, animated: true, completion: nil)
// If the failure was due to the mic permission being denied then we want to show the permission modal,
// otherwise we want to show the call missed tips modal
guard
let infoMessageData: Data = (cellViewModel.rawBody ?? "").data(using: .utf8),
let messageInfo: CallMessage.MessageInfo = try? JSONDecoder().decode(
CallMessage.MessageInfo.self,
from: infoMessageData
),
messageInfo.state == .permissionDeniedMicrophone
else {
let callMissedTipsModal: CallMissedTipsModal = CallMissedTipsModal(caller: cellViewModel.authorName)
present(callMissedTipsModal, animated: true, completion: nil)
return
}
Permissions.requestMicrophonePermissionIfNeeded(presentingViewController: self)
return
}

@ -1,6 +1,7 @@
// Copyright © 2022 Rangeproof Pty Ltd. All rights reserved.
import UIKit
import AVFAudio
import SessionUIKit
import SessionMessagingKit
import SessionUtilitiesKit
@ -147,14 +148,15 @@ final class CallMessageCell: MessageCell {
switch messageInfo.state {
case .outgoing: return UIImage(named: "CallOutgoing")?.withRenderingMode(.alwaysTemplate)
case .incoming: return UIImage(named: "CallIncoming")?.withRenderingMode(.alwaysTemplate)
case .missed, .permissionDenied: return UIImage(named: "CallMissed")?.withRenderingMode(.alwaysTemplate)
case .missed, .permissionDenied, .permissionDeniedMicrophone:
return UIImage(named: "CallMissed")?.withRenderingMode(.alwaysTemplate)
default: return nil
}
}()
iconImageView.themeTintColor = {
switch messageInfo.state {
case .outgoing, .incoming: return .textPrimary
case .missed, .permissionDenied: return .danger
case .missed, .permissionDenied, .permissionDeniedMicrophone: return .danger
default: return nil
}
}()
@ -162,8 +164,13 @@ final class CallMessageCell: MessageCell {
iconImageViewHeightConstraint.constant = (iconImageView.image != nil ? CallMessageCell.iconSize : 0)
let shouldShowInfoIcon: Bool = (
messageInfo.state == .permissionDenied &&
!Storage.shared[.areCallsEnabled]
(
messageInfo.state == .permissionDenied &&
!Storage.shared[.areCallsEnabled]
) || (
messageInfo.state == .permissionDeniedMicrophone &&
AVAudioSession.sharedInstance().recordPermission != .granted
)
)
infoImageViewWidthConstraint.constant = (shouldShowInfoIcon ? CallMessageCell.iconSize : 0)
infoImageViewHeightConstraint.constant = (shouldShowInfoIcon ? CallMessageCell.iconSize : 0)
@ -217,7 +224,15 @@ final class CallMessageCell: MessageCell {
else { return }
// Should only be tappable if the info icon is visible
guard messageInfo.state == .permissionDenied && !Storage.shared[.areCallsEnabled] else { return }
guard
(
messageInfo.state == .permissionDenied &&
!Storage.shared[.areCallsEnabled]
) || (
messageInfo.state == .permissionDeniedMicrophone &&
AVAudioSession.sharedInstance().recordPermission != .granted
)
else { return }
self.delegate?.handleItemTapped(cellViewModel, cell: self, cellLocation: gestureRecognizer.location(in: self))
}

@ -244,7 +244,10 @@ public class NotificationPresenter: NotificationsProtocol {
else { return }
// Only notify missed calls
guard messageInfo.state == .missed || messageInfo.state == .permissionDenied else { return }
switch messageInfo.state {
case .missed, .permissionDenied, .permissionDeniedMicrophone: break
default: return
}
let category = AppNotificationCategory.errorMessage
let previewType: Preferences.NotificationPreviewType = db[.preferencesNotificationPreviewType]
@ -264,6 +267,11 @@ public class NotificationPresenter: NotificationsProtocol {
format: "modal_call_missed_tips_explanation".localized(),
senderName
)
case .permissionDeniedMicrophone:
return String(
format: "call_missed".localized(),
senderName
)
case .missed:
return String(
format: "call_missed".localized(),

@ -3,6 +3,7 @@
import UIKit
import Photos
import PhotosUI
import AVFAudio
import SessionUIKit
import SessionUtilitiesKit
import SessionMessagingKit

@ -226,6 +226,7 @@ public extension CallMessage {
case outgoing
case missed
case permissionDenied
case permissionDeniedMicrophone
case unknown
}
@ -253,7 +254,7 @@ public extension CallMessage {
threadContactDisplayName
)
case .missed, .permissionDenied:
case .missed, .permissionDenied, .permissionDeniedMicrophone:
return String(
format: "call_missed".localized(),
threadContactDisplayName

@ -1,6 +1,7 @@
// Copyright © 2022 Rangeproof Pty Ltd. All rights reserved.
import Foundation
import AVFAudio
import GRDB
import WebRTC
import SessionUtilitiesKit
@ -75,8 +76,11 @@ extension MessageReceiver {
return
}
guard db[.areCallsEnabled] else {
if let interaction: Interaction = try MessageReceiver.insertCallInfoMessage(db, for: message, state: .permissionDenied, using: dependencies) {
let hasMicrophonePermission: Bool = (AVAudioSession.sharedInstance().recordPermission == .granted)
guard db[.areCallsEnabled] && hasMicrophonePermission else {
let state: CallMessage.MessageInfo.State = (db[.areCallsEnabled] ? .permissionDeniedMicrophone : .permissionDenied)
if let interaction: Interaction = try MessageReceiver.insertCallInfoMessage(db, for: message, state: state, using: dependencies) {
let thread: SessionThread = try SessionThread
.fetchOrCreate(db, id: sender, variant: .contact, shouldBeVisible: nil)

@ -146,7 +146,10 @@ public class NSENotificationPresenter: NSObject, NotificationsProtocol {
else { return }
// Only notify missed calls
guard messageInfo.state == .missed || messageInfo.state == .permissionDenied else { return }
switch messageInfo.state {
case .missed, .permissionDenied, .permissionDeniedMicrophone: break
default: return
}
let userInfo: [String: Any] = [
NotificationServiceExtension.isFromRemoteKey: true,
@ -174,6 +177,12 @@ public class NSENotificationPresenter: NSObject, NotificationsProtocol {
senderName
)
}
else if messageInfo.state == .permissionDeniedMicrophone {
notificationContent.body = String(
format: "call_missed".localized(),
senderName
)
}
addNotifcationRequest(
identifier: UUID().uuidString,

@ -1,6 +1,7 @@
// Copyright © 2022 Rangeproof Pty Ltd. All rights reserved.
import Foundation
import AVFAudio
import Combine
import GRDB
import CallKit
@ -158,14 +159,15 @@ public final class NotificationServiceExtension: UNNotificationServiceExtension
throw NotificationError.ignorableMessage
}
switch (db[.areCallsEnabled], isCallOngoing) {
let hasMicrophonePermission: Bool = (AVAudioSession.sharedInstance().recordPermission == .granted)
switch ((db[.areCallsEnabled] && hasMicrophonePermission), isCallOngoing) {
case (false, _):
if
let sender: String = callMessage.sender,
let interaction: Interaction = try MessageReceiver.insertCallInfoMessage(
db,
for: callMessage,
state: .permissionDenied,
state: (db[.areCallsEnabled] ? .permissionDeniedMicrophone : .permissionDenied),
using: dependencies
)
{

Loading…
Cancel
Save