【问题标题】:JavaFx WebView video: onended eventJavaFx WebView 视频:onended 事件
【发布时间】:2018-06-30 09:04:04
【问题描述】:

我正在制作一个使用 Webview 来显示本地 HTML 页面的 JavaFX 应用程序。将页面加载到Webview 后,通过调用JavaScript 函数open() 显示初始视频。该函数将onended 事件侦听器附加到<video> 元素。不幸的是,尽管playing 事件可以触发,但我无法触发onended 事件。

Javascript:

function open()
{
    //set position
    pos = 0;
    //display the black, add video, play.
    var video = document.getElementById('vid');
    video.style.display = "block";
    video.setAttribute('src', breakout);
    video.load();
    video.play();

    //video.addEventListener("playing", clear, false);
    video.addEventListener("ended", clear, false); 
}

function clear()
{
    alert("clear"); //was the method called? 
    //clear anything that was displayed.
    document.getElementById('vid').style.display = "none";
    document.getElementById('vid').setAttribute('src', "");
    document.getElementById('image').style.display = "none";
    document.getElementById('image').setAttribute('src', "");
    //get next.
    change();
}

Java:

public class WebviewController
{

    @FXML
    private WebView webView;
    private WebEngine engine;
    private State state;

    @FXML
    public void initialize()
    {
        engine = webView.getEngine();
        engine.setJavaScriptEnabled(true);
        engine.setOnAlert(new EventHandler<WebEvent<String>>()
        {
            @Override
            public void handle(WebEvent<String> event)
            {
                Dialog<Void> alert = new Dialog<>();
                alert.getDialogPane().setContentText(event.getData());
                alert.getDialogPane().getButtonTypes().add(ButtonType.OK);
                alert.showAndWait();
            }
        });
        engine.load(getClass().getResource("/web/newhtml.html").t‌​oExternalForm());
        afterLoad();
    }

    public void afterLoad()
    {
        engine.getLoadWorker().stateProperty().addListener(
                new ChangeListener<Worker.State>()
        {
            @Override
            public void changed(ObservableValue ov, Worker.State oldState, Worker.State newState)
            {
                if (newState == Worker.State.SUCCEEDED)
                {
                    breakout();
                }
            }
        });
    }

    public void breakout()
    {
        engine.executeScript("open()");
    }
}

HTML:

<div class="col-8">
     <div class="slideshow">
            <video id="vid" src=""></video>
            <img id="image" src='' alt="" />
      </div>
</div>

我尝试将onended="clear()" 添加到视频元素中,看看是否是JavaScript 的Open() 方法有问题,但没有成功。我还尝试触发playing 事件(如评论),它有效。所以看来onended事件触发器有问题。

要让onended 事件起作用,我缺少什么?

【问题讨论】:

    标签: javascript java javafx webview


    【解决方案1】:

    您可能遇到了 WebView 的错误。实际上,它是一个有点原始的实用程序。例如,我无法播放 Big Back Bunny 视频,但我在 JDK 1.8.0_121 上对另一个视频进行了简单测试,它可以正常工作:

    public class VideoTest extends Application {
    
        @Override
        public void start(Stage primaryStage) throws Exception {
            WebConsoleListener.setDefaultListener((webView, message, lineNumber, sourceId) -> {
                System.out.println(message + "[at " + lineNumber + "]");
            });
    
            WebView webView = new WebView();
            WebEngine engine = webView.getEngine();
            engine.setJavaScriptEnabled(true);
    
            StringBuilder codeBuilder = new StringBuilder("<video id='test' src='http://techslides.com/demos/sample-videos/small.mp4' width='200' height='200' controls></video>");
            codeBuilder.append("<script>");
            codeBuilder.append("document.querySelector('#test').addEventListener('playing', function(e) { console.log('playing'); }, false);");
            codeBuilder.append("document.querySelector('#test').addEventListener('ended', function(e) { console.log('ended'); }, false);");
            codeBuilder.append("document.querySelector('#test').load();");
            codeBuilder.append("document.querySelector('#test').play();");
            codeBuilder.append("</script>");
            engine.loadContent(codeBuilder.toString());
    
            Scene scene = new Scene(webView, 600, 300);
            primaryStage.setScene(scene);
            primaryStage.show();
        }
    
    }
    

    无论如何,我对如何使用 WebView 有一些建议:

    • 您可以通过WebConsoleListener.setDefaultListener 从com.sun.javafx.webkit 包中打印到控制台,而不是alert()

    • 准确来说,应该先注册监听器,然后调用load()或play()等函数

    • 让您的代码尽可能简单,并逐段扩展

    您也可以尝试将 WebView 替换为 MediaView 或使用其他嵌入式浏览器组件。例如,您可以使用JCEF(Java Chromium Embedded Framework)

    【讨论】:

      猜你喜欢
      • 2015-11-27
      • 1970-01-01
      • 1970-01-01
      • 2015-01-27
      • 2023-03-05
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2015-02-04
      相关资源
      最近更新 更多