在 Android WebView 中拦截 HTML5 视频源请求

Posted

技术标签:

【中文标题】在 Android WebView 中拦截 HTML5 视频源请求【英文标题】:Intercepting HTML5 video source request in Android WebView 【发布时间】:2012-02-18 11:02:19 【问题描述】:

我有一个应用程序,它在 WebView 中显示带有视频元素的 html5 页面。我花了一段时间才弄清楚如何让视频正常工作,但最后我成功地在三星 Galaxy Tab(android 3.1)上播放嵌入在 WebView 中的视频。我为视频标签使用了以下代码:

<video controls poster="img/poster.jpg"  >
        <source src="video/BigBuck.m4v">
        <source src="video/BigBuck.theora.ogv" type="video/ogg">
        <source src="video/BigBuck.webm" type="video/webm">
        HTML5 video not supported.
</video>

视频元素有多个来源,现在我尝试在视频开始播放之前捕获选定的视频来源(和格式)。当我点击播放按钮时,我看到视频文件的 HTTP 请求到达存储视频文件的 Web 服务器,但我没有成功在应用端拦截此请求。

我查看了几种方法来查看视频文件的请求是否通过那里,但我没有看到它通过其中任何一个。

在我的WebViewClient 中的shouldOverrideUrlLoading(WebView view, String url) 中,只有初始的HTML5 页面请求通过。 在shouldInterceptRequest (WebView view, String url) 在我的WebViewClient 中,我看到只传递了初始HTML5 页面请求和对视频海报图像的请求,而不是视频文件。 我的WebChromeClient 中的onShowCustomView(View view, CustomViewCallback callback) 仅在视频已经播放时单击HTML5 页面上的全屏控制按钮时调用,但在我单击播放按钮时不会调用。 (这种方法的实际目的是什么?)

是否有人对我可以捕获对视频文件的请求的另一种方法提出建议,或者谁能解释我单击视频元素上的播放按钮时实际发生的情况?

【问题讨论】:

您能否发布您用于视频标签的代码。我最近处理了这个问题,shouldOverrideUrlLoading(WebView view, String url) 为我工作(虽然在 Gingerbread 中)。 【参考方案1】:

我使用 javascript 方法解决了这个问题。加载 HTML 页面时,会在加载视频元数据时触发 loadedmetadata 事件。从那一刻起,您可以从 video 元素的 currentSrc 属性中获取选定的视频源,并通过 JavascriptInterface 将其传递给 Android 原生代码。

下面是 HTML5 视频元素的代码。 “Android”是可以在 javascript 中访问 JavascriptInterface 的名称。

<video poster="image/poster.jpg"   onloadedmetadata="Android.interceptPlay(this.currentSrc);">
    <source src="video/BigBuck.m4v">
    <source src="video/BigBuck.webm" type="video/webm">
    <source src="video/BigBuck.theora.ogv" type="video/ogg">
    HTML5 video not supported.
</video>

JavascriptInterface的代码

private class JavaScriptInterface 
    Context mContext;

    /* Instantiate the interface and set the context */
    JavaScriptInterface(Context c) 
        mContext = c;
    

    public void interceptPlay(String source) 
        // do something
    

最后在 Activity 创建时将 JavascriptInterface 添加到 WebView

mWebView.addJavascriptInterface(new JavaScriptInterface(this), "Android");

通过将onloadedmetadata 属性添加到HTML5 视频元素而不是通过在页面加载时通过addEventListener("loadedmetadata",...) 注册事件侦听器来捕获loadedmetadata 事件很重要,因为在快速网络上loadedmetadata 事件可能是在监听器注册之前触发(见http://dev.opera.com/articles/view/consistent-event-firing-with-html5-video)

【讨论】:

感谢您的解决方案,Erika;这看起来也正是我所需要的。 我说得太早了。我需要在第一次按下播放按钮时拦截它(我正在下载一次视频)。你觉得有一个简单的方法吗? 您有没有为此找到“真正的”解决方案?我真的需要拦截 url,因为在我的情况下,事件永远不会被触发。

以上是关于在 Android WebView 中拦截 HTML5 视频源请求的主要内容,如果未能解决你的问题,请参考以下文章

在 Android WebView 中拦截 HTML5 视频源请求

android WebView拦截请求详解

Android:拦截来自WebView的AJAX调用

webview怎么获取拦截页面中的Post数据?

Android在string.xml中定义html文档并加载显示,以及拦截WebView链接事件

一手遮天 Android