mirror of
https://github.com/Novaloop-AG/element-x-ios.git
synced 2026-11-03 06:55:59 +00:00
EC: Native switch for audio outputs/inputs and earpiece (#4136)
* EC: native switch for audio outputs/inputs and earpiece also includes proximity sensor enabling when the earpiece is used. * test disabling and re-enabling audio on audio change * Revert "test disabling and re-enabling audio on audio change" This reverts commit 907c791b8df7009214f5c164ecf8fe7d90a8addc. * pr suggestions * pr suggestion and small refactor of the widgetAction handler
This commit is contained in:
@@ -75,6 +75,7 @@ private struct CallView: UIViewRepresentable {
|
||||
private var webView: WKWebView!
|
||||
private var pictureInPictureController: AVPictureInPictureController?
|
||||
private let pictureInPictureViewController: AVPictureInPictureVideoCallViewController
|
||||
private var routePickerView: AVRoutePickerView!
|
||||
|
||||
/// The view to be shown in the app. This will contain the web view when picture in picture isn't running.
|
||||
let webViewWrapper = WebViewWrapper(frame: .zero)
|
||||
@@ -97,7 +98,9 @@ private struct CallView: UIViewRepresentable {
|
||||
let configuration = WKWebViewConfiguration()
|
||||
|
||||
let userContentController = WKUserContentController()
|
||||
userContentController.add(WKScriptMessageHandlerWrapper(self), name: viewModelContext.viewState.messageHandler)
|
||||
CallScreenJavaScriptMessageName.allCases.forEach {
|
||||
userContentController.add(WKScriptMessageHandlerWrapper(self), name: $0.rawValue)
|
||||
}
|
||||
|
||||
// Required to allow a webview that uses file URL to load its own assets
|
||||
configuration.preferences.setValue(true, forKey: "allowFileAccessFromFileURLs")
|
||||
@@ -123,6 +126,12 @@ private struct CallView: UIViewRepresentable {
|
||||
webView.backgroundColor = .compound.bgCanvasDefault
|
||||
webView.scrollView.backgroundColor = .compound.bgCanvasDefault
|
||||
|
||||
// This button is always hidden and is only used to be programmaticaly tapped
|
||||
routePickerView = AVRoutePickerView(frame: .zero)
|
||||
routePickerView.isHidden = true
|
||||
routePickerView.isUserInteractionEnabled = false
|
||||
webView.addSubview(routePickerView)
|
||||
|
||||
webViewWrapper.addMatchedSubview(webView)
|
||||
|
||||
if AVPictureInPictureController.isPictureInPictureSupported() {
|
||||
@@ -161,7 +170,32 @@ private struct CallView: UIViewRepresentable {
|
||||
}
|
||||
|
||||
func userContentController(_ userContentController: WKUserContentController, didReceive message: WKScriptMessage) {
|
||||
viewModelContext?.javaScriptMessageHandler?(message.body)
|
||||
guard let handlerID = CallScreenJavaScriptMessageName(rawValue: message.name) else {
|
||||
return
|
||||
}
|
||||
|
||||
switch handlerID {
|
||||
case .widgetAction:
|
||||
guard let message = message.body as? String else { return }
|
||||
viewModelContext?.send(viewAction: .widgetAction(message: message))
|
||||
case .showNativeOutputDevicePicker:
|
||||
DispatchQueue.main.async {
|
||||
self.tapRoutePickerView()
|
||||
}
|
||||
case .onOutputDeviceSelect:
|
||||
guard let deviceID = message.body as? String else { return }
|
||||
viewModelContext?.send(viewAction: .outputDeviceSelected(deviceID: deviceID))
|
||||
}
|
||||
}
|
||||
|
||||
// This function is called by the webview output routing button
|
||||
// it allows to open the OS output selector using the hidden button.
|
||||
private func tapRoutePickerView() {
|
||||
guard let button = routePickerView.subviews.first(where: { $0 is UIButton }) as? UIButton else {
|
||||
return
|
||||
}
|
||||
|
||||
button.sendActions(for: .touchUpInside)
|
||||
}
|
||||
|
||||
// MARK: - WKUIDelegate
|
||||
@@ -172,6 +206,7 @@ private struct CallView: UIViewRepresentable {
|
||||
return .deny
|
||||
}
|
||||
|
||||
viewModelContext?.send(viewAction: .mediaCapturePermissionGranted)
|
||||
return .grant
|
||||
}
|
||||
|
||||
|
||||
Reference in New Issue
Block a user