如何在Jetpack Compose WebView的iframe视频中实现播放/暂停按钮?
实现WebView中iframe视频的播放/暂停控制按钮
我希望创建一个图标按钮,用于控制WebView中iframe视频的播放/暂停。请问如何在下方的代码中实现播放/暂停功能?
原始代码:
@Composable fun Stream(activity: ComponentActivity) { val frameVideo = "<html><iframe width=\"100%\" height=\"100%\"src=\"https://static.videezy.com/system/resources/previews/000/000/168/original/Record.mp4\" frameborder= \"0\" allow= \"autoplay; encrypted-media\" allowfullscreen></iframe></html></html>" val state = rememberWebViewState(url = frameVideo) val navigator = rememberWebViewNavigator() val chromeClient = remember { CustomChromeClient(activity) } Column { Button(onClick = { }) { Text("Play/Pause") } WebView( state = rememberWebViewStateWithHTMLData(data = frameVideo), modifier = Modifier.fillMaxSize(), navigator = navigator, chromeClient = chromeClient, //This is what concerns us for fullscreen mode onCreated = { webView -> webView.settings.javaScriptEnabled=true webView.loadData(frameVideo, "text/html", "utf-8") //configuring the webview settings here such as enabling javascript } ) } }
实现方案
核心思路是通过JavaScript调用iframe内部的视频元素来控制播放状态,同时持有WebView实例并维护播放状态标记,具体修改如下:
- 保存WebView实例,方便按钮点击时调用执行JS代码
- 维护播放状态变量,用于切换按钮文本和控制逻辑
- 编写JS脚本,穿透iframe获取视频元素并执行播放/暂停操作
- 调整WebView设置,确保能访问iframe内部DOM
修改后的完整代码:
@Composable fun Stream(activity: ComponentActivity) { val frameVideo = "<html><iframe width=\"100%\" height=\"100%\"src=\"https://static.videezy.com/system/resources/previews/000/000/168/original/Record.mp4\" frameborder= \"0\" allow= \"autoplay; encrypted-media\" allowfullscreen></iframe></html>" val navigator = rememberWebViewNavigator() val chromeClient = remember { CustomChromeClient(activity) } // 持有WebView实例 val webView = remember { mutableStateOf<WebView?>(null) } // 维护播放状态,初始为暂停 val isPlaying = remember { mutableStateOf(false) } Column { Button(onClick = { webView.value?.let { wv -> // 切换播放状态 isPlaying.value = !isPlaying.value // 执行JS控制视频 val jsCode = if (isPlaying.value) { "document.querySelector('iframe').contentWindow.document.querySelector('video').play();" } else { "document.querySelector('iframe').contentWindow.document.querySelector('video').pause();" } wv.evaluateJavascript(jsCode, null) } }) { Text(if (isPlaying.value) "暂停" else "播放") } WebView( state = rememberWebViewStateWithHTMLData(data = frameVideo), modifier = Modifier.fillMaxSize(), navigator = navigator, chromeClient = chromeClient, onCreated = { wv -> webView.value = wv wv.settings.javaScriptEnabled = true // 允许跨域访问iframe内容,否则无法获取内部视频元素 wv.settings.allowUniversalAccessFromFileURLs = true wv.loadData(frameVideo, "text/html", "utf-8") } ) } }
关键注意点
- 必须开启
javascriptEnabled和allowUniversalAccessFromFileURLs,否则无法穿透iframe访问内部DOM元素 - 如果页面存在多个video元素,需要调整
document.querySelector('video')的选择器,确保定位到目标视频 - 按钮文本会根据播放状态自动切换,提升交互体验
内容的提问来源于stack exchange,提问作者SyahmiSam
相关产品推荐
相关产品推荐

