如何在 javafx webkit 中使用 file://... 添加本地 img

how to add a local img with file://... in javafx webkit

我想在 javafx webview 本地显示图片 html。这是我的代码,但是我发现图片不能是 shown.The 图片 url 是 "file:/D:/a.jpg".

//Main WebViewBrowser.java

public class WebViewBrowser extends Application {

    @Override public void start(Stage stage) throws Exception {
        WebView browser = new WebView();
        browser.setContextMenuEnabled(false);
        WebEngine webEngine = browser.getEngine();
        String url = this.getClass().getResource("t.html").toExternalForm();
        System.out.println(url);
        //out put is "jar:file:/D:/data/netbeans/WebViewBrowser1/dist/run690102893/WebViewBrowser.jar!/webviewbrowser/t.html"
        Scene scene = new Scene(browser);
        webEngine.load(url);
        stage.setScene(scene);
        stage.show();
    }

    public static void main(String[] args) {
        launch(args);
    }
}


//t.html
//.............
<html>
<head>
    <title>TODO supply a title</title>
    <meta charset="UTF-8">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
</head>
<body>
    <div>TODO write content</div>
    <img src="a.jpg" alt="aaa"/>  <!-- the relative path works -->
    <img src="file:/D:/a.jpg" alt="aaa"/>  <!-- the absolute path dos not work.why ?-->
</body>
 </html>

我只想知道如何加载 url 类似于 'file:/D:/a.jpg' 的图像。 非常感谢你。

根据您的问题的新描述,我也可以重现它:如果从 jar 文件加载网页,似乎 WebView 无法访问本地文件。

经过一段时间的搜索,我刚刚在 JIRA 上找到了这个错误报告(您需要注册才能访问它):

  • RT-39031 [WebView] 从 jar 文件加载网页时未加载本地图像

正如报告中指出的那样,如果您右键单击 alt 描述,您可以在新的 window 上加载图像,这意味着这不是安全限制的问题(沙盒) .

目前没有简单的解决方案。还 here 提出的一种方法是将图像编码为 base64 字符串:

<img src="data:image/png;base64,(...)" />

public String pathToBase64(String path) throws IOException {
    return Base64.getEncoder().encodeToString(Files.readAllBytes(Paths.get(path)));
} 

其他解决方案正在使用 webEngine.loadContent()。已经有一个可能有效的示例 here

编辑

正如 OP 指出的那样,还有另一种解决方法可以处理本地图像加载,它基于自定义 URL 协议的使用。在这个 question 中已经有一个可行的解决方案。对于图像加载,这是一个可能的实现:

private void loadImage() throws IOException {
    String imgPath = getURL().toExternalForm();
    String ext = imgPath.substring(imgPath.lastIndexOf('.')+1);
    imgPath = imgPath.startsWith(PROTOCOL+"://") ? 
                 imgPath.substring((PROTOCOL+"://").length()) :
                 imgPath.substring((PROTOCOL+":").length());

    try{
        BufferedImage read = ImageIO.read(new File(imgPath));
        ByteArrayOutputStream os = new ByteArrayOutputStream();
        ImageIO.write(read, ext, os);
        data=os.toByteArray();
    } catch(IOException ioe){
        System.out.println("IO exception: "+ioe);
    }
}