Android Webview HTML加载Javascript问题

发布于 2024-10-22 11:37:21 字数 2986 浏览 2 评论 0原文

我已经与这个问题作斗争超过 48 小时了,但我一直无法在网络上的任何地方找到答案。设置如下:

我的 Android 应用程序在首次运行期间下载内容(内容超过 20MB),并且文件将解压缩到用户的 SD 卡上的 /mnt/sdcard/{my package}/folder。内容包括HTML文件、CSS文件、JS文件和图像。以下是写入 SD 卡的完整结构(其中 / = /mnt/sdcard/{my package}/folder/):

/content/

a.html
b.html
images/
  image1.jpg

/css/

c.css
d.css

/js/

e.js
f.js

这是我的代码,它从SD 卡:

    webView = (WebView) findViewById(R.id.pageBrowser);
    webView.getSettings().setJavaScriptEnabled(true);
    webView.addJavascriptInterface(new LinkHandlerInterface(), "Android");
    webView.setWebViewClient(new PageWebViewClient());

    // contentLocation + url is equal to the full path to the html file
    webView.loadUrl("file://" + contentLocation + url);

此代码成功加载 HTML 页面。还没有问题。每个页面都有以下 head 标签:

    <link rel="stylesheet" type="text/css" href="../css/screen.css" media="all" />
    <link rel="stylesheet" type="text/css" href="../css/inPractice.css" media="all" />
    <link rel="stylesheet" type="text/css" href="../css/inPracticeScheme.css" media="all" />
    <link rel="stylesheet" type="text/css" href="../css/mobile/iPad.css" media="all" />
    <script type="text/javascript" src="../js/jquery-1.3.2.min.js"></script>
    <script type="text/javascript" src="../js/inPractice-utilities.js"></script>
    <script type="text/javascript" src="../js/inPractice.js"></script>
    <script type="text/javascript" src="../js/mobile/inpractice.ipad.js"></script>

这是问题所在。我的 WebView 渲染 HTML 效果很好。它甚至可以完美地加载和应用 CSS。但是,它拒绝加载和执行 Javascript。如果您还记得上面的内容,js 文件夹实际上是 html 文件的上一层,因此它指向正确的位置。

以下是我所知道的列表:

  • 我正在使用的 CSS 应用得很好,所以我知道问题不在于文件位置。

  • 我之前使用过相同的代码,但是从我的应用程序的资产文件夹(file:///android_assets/...)加载文件并且它工作得很好。由于内容太大,我无法将其与我的应用程序捆绑在一起,因此移动到 SD 卡。

  • 如果我更改 HTML 文件,将所有 Javascript 方法都列在脚本标记内,则效果很好。我无法控制 HTML,因此无法永久应用此更改。这告诉我,WebView 执行 Javascript 没有问题。

  • 图像加载良好。

我现在没什么想法了。有谁知道为什么我的 WebView 无法加载我的 Javascript 文件?有人见过这个吗?

编辑:以下是我尝试使用的JS文件,可以在这里查看:

http://www.automatastudios.com/clients/cco/inpractice/css/inPractice.css http://www.automatastudios.com/clients/cco/inpractice/css /inPracticeScheme.css http://www.automatastudios.com/clients/cco/inpractice/css /screen.css http://www.automatastudios.com/clients/cco/inpractice /css/mobile/iPad.css

  • 注意:这些 CSS 文件不是我创作的。

I've been battling this problem for over 48 hours now and I have been unable to find an answer anywhere on the net. Here's the setup:

My Android application is downloading content during first run (content is over 20MB) and the files are unzipped onto the user's SD card at /mnt/sdcard/{my package}/folder. The content includes HTML files, CSS files, JS files and images. Here's the full structure of what is written to the SD card (where / = /mnt/sdcard/{my package}/folder/):

/content/

a.html
b.html
images/
  image1.jpg

/css/

c.css
d.css

/js/

e.js
f.js

Here is my code that loads the html file from the SD card:

    webView = (WebView) findViewById(R.id.pageBrowser);
    webView.getSettings().setJavaScriptEnabled(true);
    webView.addJavascriptInterface(new LinkHandlerInterface(), "Android");
    webView.setWebViewClient(new PageWebViewClient());

    // contentLocation + url is equal to the full path to the html file
    webView.loadUrl("file://" + contentLocation + url);

This code successfully loads the HTML page. No problems yet. Each page has the following head tag:

    <link rel="stylesheet" type="text/css" href="../css/screen.css" media="all" />
    <link rel="stylesheet" type="text/css" href="../css/inPractice.css" media="all" />
    <link rel="stylesheet" type="text/css" href="../css/inPracticeScheme.css" media="all" />
    <link rel="stylesheet" type="text/css" href="../css/mobile/iPad.css" media="all" />
    <script type="text/javascript" src="../js/jquery-1.3.2.min.js"></script>
    <script type="text/javascript" src="../js/inPractice-utilities.js"></script>
    <script type="text/javascript" src="../js/inPractice.js"></script>
    <script type="text/javascript" src="../js/mobile/inpractice.ipad.js"></script>

Here is where the problem is. My WebView renders the HTML just fine. It even loads and applies the CSS perfectly. However, it refuses to load and execute the Javascript. If you remember from above, the js folder is, in fact, one leve up from the html file, so it's pointing to the correct place.

Here's a list of what I know:

  • The CSS I'm using is being applied fine, so I know the issue is not with the file location.

  • I used this same code before, but was loading the files from my application's assets folder (file:///android_assets/...) and it worked perfectly. Since the content is so large, I can't bundle it with my application, hence the move to the SD card.

  • If I change the HTML files in such a way that all the Javascript methods are listed inside a script tag, it works fine. I don't have control over the HTML, so I can't apply this change permanently. This tells me that the WebView has no problem executing the Javascript.

  • Images load fine.

I'm fresh out of ideas now. Does anyone have any clue why my WebView cannot load my Javascript files? Has anyone seen this before?

EDIT: Here are the JS files I'm trying to use can be viewed here:

http://www.automatastudios.com/clients/cco/inpractice/css/inPractice.css
http://www.automatastudios.com/clients/cco/inpractice/css/inPracticeScheme.css
http://www.automatastudios.com/clients/cco/inpractice/css/screen.css
http://www.automatastudios.com/clients/cco/inpractice/css/mobile/iPad.css

  • NOTE: These CSS files were not authored by me.

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(2

遮云壑 2024-10-29 11:37:21

始终无法找到解决方案。

我最终只是编辑了 HTML 文件,将 Javascript 源文件更改为内联 Javascript。这有效(正如我预期的那样)。

Was never able to find a solution to this.

I ended up just editing the HTML files, such that changed the Javascript source files to inline Javascript. That worked (as I expected it would).

尾戒 2024-10-29 11:37:21

加载引用js、css的html的首选方法是使用

webView.loadDataWithBaseURL()

我们需要传递在文件系统上找到html、js、css的位置的根目录作为baseURL。这里需要注意的重要一点是我们只需要使用“文件”方案 URL。

在您的情况下,代码应该是

    String html = readFileAsString(
       new FileInputStream("file://" + contentLocation + url) );
webView.loadDataWithBaseURL("file://" + contentLocation,html,"text/html","utf-8",null);


public static StringBuffer streamToString(InputStream stream ){

        StringBuffer fileContent = new StringBuffer("");
        try {

            int size = stream.available();
            byte[] buffer = new byte[size];
            int length;
            while ((length = stream.read(buffer)) != -1) {
                fileContent.append(new String(buffer));
            }
            stream.close();
        } catch (IOException e) {
            // TODO Auto-generated catch block
            e.printStackTrace();
            try {
                stream.close();
            } catch (IOException e1) {
                // TODO Auto-generated catch block
                e1.printStackTrace();
            }
        }

        return fileContent;
    }

希望答案可以帮助未来的访客

PS:
上面的代码片段没有被编译

The preferred way to to load a html which references js, css is to use

webView.loadDataWithBaseURL()

We need to pass the root directory of the location where the html,js,css are found on the file system as the baseURL. Important thing to note here is that we need to use "file" scheme URL only.

In your case code should be

    String html = readFileAsString(
       new FileInputStream("file://" + contentLocation + url) );
webView.loadDataWithBaseURL("file://" + contentLocation,html,"text/html","utf-8",null);


public static StringBuffer streamToString(InputStream stream ){

        StringBuffer fileContent = new StringBuffer("");
        try {

            int size = stream.available();
            byte[] buffer = new byte[size];
            int length;
            while ((length = stream.read(buffer)) != -1) {
                fileContent.append(new String(buffer));
            }
            stream.close();
        } catch (IOException e) {
            // TODO Auto-generated catch block
            e.printStackTrace();
            try {
                stream.close();
            } catch (IOException e1) {
                // TODO Auto-generated catch block
                e1.printStackTrace();
            }
        }

        return fileContent;
    }

Hope the answer helps future visitors

PS:
The above code snippet is not compiled

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文