我怎么可能在 JFrame 的 canvas 中绘制 JavaFX 视频?

How can I possibly draw a JavaFX video in a JFrame's canvas?

基本上,我想 "add" 一个 JavaFX 视频到 Java Swing JFrame,但我也想在那个 canvas 中绘制,以做其他播放视频时的事情。我使用此代码播放视频:

    public class ExtVideoPlayer extends Application implements dev.ckitty.kc.utils.interf.MediaPlayer {

    @Override
    public MediaPlayerType[] getAcceptedTypes() {
        return new MediaPlayerType[] { MediaPlayerType.VIDEO };
    }

    @Override
    public void init(File f, String s) {

    }

    @Override
    public void start() {
        ExtVideoPlayer.launch(new String[0]);
    }

    @Override
    public void command(String[] args) {

    }

    @Override
    public void stop() {

    }

    @Override
    public void start(Stage primaryStage) throws Exception {
        StackPane root = new StackPane();

        File video = new File("C:\Users\980001005\Videos\IMG_6503.mp4");
        String url = video.toURI().toURL().toString();
        Media media = new Media(url);
        MediaPlayer player = new MediaPlayer(media);
        MediaView mediaView = new MediaView(player);

        root.getChildren().add(mediaView);
        Scene scene = new Scene(root, mediaView.getFitWidth(), mediaView.getFitHeight());

        primaryStage.setScene(scene);
        primaryStage.show();

        player.play();
    }

}

这工作正常,但创建其他 windows!当然我可以把它做成弹出式视频,但那样看起来会很糟糕。

例如,我希望它看起来像 Youtube。人们将能够为视频投票,投票结果将显示在 Youtube 显示推荐视频和添加视频的位置。

我见过一些将视频作为组件放入 JFrame 的技巧,但我希望它有一个我也可以使用的 Canvas。 (这样我就可以在正在播放的视频上画画什么的)

请帮忙!

编辑! This 答案似乎是我必须使用的答案。

编辑 2

现在我在同一个JFrame中得到了canvas和视频,但是canvas不透明!

密码

   public class LayeredDisplay extends Display {

    protected JLayeredPane pane;
    protected JPanel ontop, behind;
    protected JFXPanel jfxPanel;

    public LayeredDisplay(String title, int w, int h) {
        super(title, w, h, false);
        this.createLayers();
        this.frame.pack();
        this.frame.requestFocus();
        this.frame.setSize(w, h);
        this.frame.setVisible(true);
    }

    protected void createLayers() {

        this.jfxPanel = new JFXPanel();
        this.canvas = new Canvas();

        Dimension dim = new Dimension(this.w, this.h);

        this.canvas.setPreferredSize(dim);
        this.canvas.setMaximumSize(dim);
        this.canvas.setMinimumSize(dim);
        this.canvas.setFocusable(false);

        //this.ontop.add(this.canvas);

        //pane.add(this.ontop, 2);
        //pane.add(this.behind, 1);

        this.frame.add(this.jfxPanel, 0);
        this.frame.add(canvas, 1);
    }

    public JLayeredPane getPane() {
        return this.pane;
    }

    public JPanel getFront() {
        return this.ontop;
    }

    public JPanel getBack() {
        return this.behind;
    }

    public void addComponent(Component comp) {
        this.behind.add(comp);
    }

    public void addVideo(File video1) {
        Util.initJavaFX();

        SwingUtilities.invokeLater(new Runnable() {
            @Override
            public void run() {
                //Code to change Swing data.

                File video = new File("C:\Users\980001005\Videos\IMG_6503.mp4");
                String url = null;

                try {
                    url = video.toURI().toURL().toString();
                } catch (MalformedURLException e) {
                    e.printStackTrace();
                }

                Media media = new Media(url);
                MediaPlayer player = new MediaPlayer(media);
                MediaView view = new MediaView(player);

                player.play();
                jfxPanel.setScene(new Scene(new Group(view)));
            }
        });

    }

}

我正在扩展的显示 class 包含 canvas 和 JFrame,并为我提供了要在 canvas 中绘制的 Graphics 对象,没什么特别的。

我得到了我需要的结果! 我将 JFXPanel 放在 class 中来管理视频。您基本上需要将 JFXPanel 添加到 JPanel

public class FramePlayer {

    private Display disp;
    private JFXPanel jfxPanel;
    private int w, h;

    public FramePlayer(Display disp, int w, int h, boolean autoInit) {
        this.disp = disp;
        this.w = w;
        this.h = h;
        if(autoInit) this.init();
    }

    public void init() {
        this.jfxPanel = new JFXPanel();

        Dimension dim = new Dimension(w, h);
        this.jfxPanel.setPreferredSize(dim);
        this.jfxPanel.setBackground(new Color(0, 0, 0, 255));
        this.jfxPanel.setOpaque(false);

        this.disp.getFrame().add(this.jfxPanel, 1);
    }

    public void addVideo(File video1) {
        Util.initJavaFX();

        SwingUtilities.invokeLater(new Runnable() {
            @Override
            public void run() {
                // Code to change Swing data.

                File video = new File("C:\Users\980001005\Videos\IMG_6503.mp4");
                String url = null;

                try {
                    url = video.toURI().toURL().toString();
                } catch (MalformedURLException e) {
                    e.printStackTrace();
                }

                Media media = new Media(url);
                MediaPlayer player = new MediaPlayer(media);
                MediaView view = new MediaView(player);

                Group g = new Group(view);
                Scene s = new Scene(g);
                s.setFill(Paint.valueOf("TRANSPARENT")); // THIS MAKES IT TRANSPARENT!

                player.play();
                jfxPanel.setScene(s);
            }
        });
    }

    public void renderVideo() {
        this.jfxPanel.paint(this.disp.getGfx().get());
    }

    public void renderVideo(KCGraphics gfx) {
        this.jfxPanel.paint(gfx.get());
    }

}

你需要 1.将JFXPanel添加到JPanel 2. 强制将 JFXPanel 绘制到 canvas(好吧,这就是我必须做的......) 3. 享受吧!