如何在WKWebKit中实现AVPlayer播放结束时OC向JS发送通知?
解决方案:在WKWebKit中从Objective-C向JavaScript发送音频结束通知
你已经成功捕获到音频播放结束的事件了,接下来只需要在playerItemDidReachEnd方法里给JavaScript发送消息即可,下面提供两种常用的实现方式:
方式一:直接调用JavaScript全局函数
这种方式最简单,适合不需要传递复杂数据的场景:
1. 在JavaScript端定义全局处理函数
提前在你的网页代码里定义一个处理音频结束的全局函数:
// 定义音频结束后的处理函数 function onAudioPlaybackEnded() { console.log("音频播放结束啦!"); // 在这里执行后续需要的操作 }
2. 在Objective-C的结束回调中调用该函数
修改你的playerItemDidReachEnd方法,通过WKWebView的evaluateJavaScript:completionHandler:方法触发JS函数:
- (void)playerItemDidReachEnd { NSLog(@"audio ended"); // 调用JS的全局处理函数 [self.webView evaluateJavaScript:@"onAudioPlaybackEnded()" completionHandler:^(id _Nullable result, NSError * _Nullable error) { if (error) { NSLog(@"调用JS函数失败: %@", error.localizedDescription); } }]; // 重要:移除通知观察者,避免重复监听或内存泄漏 [[NSNotificationCenter defaultCenter] removeObserver:self name:AVPlayerItemDidPlayToEndTimeNotification object:_contentAudioPlayer.currentItem]; }
方式二:通过WKScriptMessageHandler反向传递消息
这种方式和你之前调用Objective-C的逻辑一致,适合需要传递额外数据的场景:
1. 在JavaScript端注册消息处理器
提前在网页代码里注册一个接收音频结束通知的消息处理器:
// 注册接收音频结束通知的处理器 window.webkit.messageHandlers.audioEnded.addListener(function(message) { console.log("收到音频结束通知:", message); // 执行后续操作 });
2. 在Objective-C的结束回调中发送消息
修改playerItemDidReachEnd方法,通过evaluateJavaScript触发JS的消息处理器:
- (void)playerItemDidReachEnd { NSLog(@"audio ended"); // 向JS发送音频结束的消息,可传递自定义数据(比如音频源地址) NSString *jsCommand = [NSString stringWithFormat:@"window.webkit.messageHandlers.audioEnded.postMessage('%@')", _contentAudioPlayer.currentItem.URL.absoluteString]; [self.webView evaluateJavaScript:jsCommand completionHandler:nil]; // 移除通知观察者 [[NSNotificationCenter defaultCenter] removeObserver:self name:AVPlayerItemDidPlayToEndTimeNotification object:_contentAudioPlayer.currentItem]; }
注意事项
- 确保
self.webView是当前有效的WKWebView实例,避免出现空指针问题 - 一定要移除通知观察者,否则多次播放音频后可能会重复触发回调,还可能导致内存泄漏
- 确保JS端的函数或消息处理器在Objective-C发送消息前已经完成注册,否则会出现调用无效的情况
内容的提问来源于stack exchange,提问作者w0ns88
相关产品推荐
相关产品推荐

