JxBrowser supports Swing/AWT and JavaFX UI toolkits. It provides two implementations of the BrowserView class that can be used for embedding JxBrowser into Swing/AWT and JavaFX applications:(JxBrowser支持Swing / AWT和JavaFX UI工具箱。它提供了BrowserView类的两种实现,可用于将JxBrowser嵌入到Swing / AWT和JavaFX应用程序中:)

  • com.teamdev.jxbrowser.chromium.swing.BrowserView(com.teamdev.jxbrowser.chromium.swing.BrowserView)
  • com.teamdev.jxbrowser.chromium.javafx.BrowserView(com.teamdev.jxbrowser.chromium.javafx.BrowserView)

To embed JxBrowser into SWT applications you can use the approaches described below. These approaches are based on the third-party SWT-AWT and SWT-JavaFX components (bridges).(要将JxBrowser嵌入到SWT应用程序中,可以使用下面描述的方法。这些方法基于第三方SWT-AWT和SWT-JavaFX组件(桥)。)


Note: please note that mixing the two UI toolkits isn't a simple task, so there might be some integration issues such as focus transferring, flickering, freezing, thread deadlocks, etc. You can read more about possible issues in the Swing/SWT Integration article.

Important for macOS: Java should be run with -XstartOnFirstThread parameter in case you are not starting the script via Eclipse using macOS. Otherwise you will  get the "org.eclipse.swt.SWTException: Invalid thread access" error. If you are using Eclipse, this parameter is applied automatically and you won't encounter this error.

Since JxBrowser 6.0 we started initializing Chromium engine in Java process to enable heavyweight rendering mode. Chromium engine actively uses Cocoa UI threads as well as Java Swing, and SWT. It's very important to initialize Chromium in Cocoa UI thread (AppKit). With using the -XstartOnFirstThread VM flag, default UI thread is changed to Java "main" thread which breaks Chromium functionality that requires AppKit thread. As result, Chromium fails to initialize in "main" thread and you see the freezing issue and later the "IPC cannot start because Chromium doesn't respond" error message.
(注意:请注意,混合使用两个UI工具包并不是一件容易的事,因此可能存在一些集成问题,例如焦点转移,闪烁,冻结,线程死锁等。您可以在Swing / SWT中阅读更多有关可能的问题的文章。
对于macOS重要:如果不使用macOS通过Eclipse启动脚本,则Java应该与-XstartOnFirstThread参数一起运行。否则,您将收到“ org.eclipse.swt.SWTException:无效的线程访问”错误。如果您使用的是Eclipse,则会自动应用此参数,并且不会遇到此错误。
从JxBrowser 6.0开始,我们开始在Java进程中初始化Chromium引擎以启用重量级渲染模式。 Chromium引擎积极使用Cocoa UI线程以及Java Swing和SWT。在Cocoa UI线程(AppKit)中初始化Chromium非常重要。通过使用-XstartOnFirstThread VM标志,默认的UI线程将更改为Java“主”线程,这破坏了需要AppKit线程的Chromium功能。结果,Chromium无法在“主”线程中初始化,并且您看到冻结问题,并且随后出现“由于Chromium无法响应,IPC无法启动”错误消息。)


This is a regression issue caused by architectural changes in 6.0. It should be completely resolved after the implementation of SWT support.(这是由6.0中的体系结构更改引起的回归问题。实施SWT支持后,应完全解决该问题。)


Meanwhile, as a workaround, you can use lightweight rendering mode with the jxbrowser.ipc.external=true JVM parameter. In this case, Chromium engine will be initialized in a separate native process, so you will not see this issue anymore. Please note that with this JVM parameter you can use only lightweight browser mode.(同时,作为一种解决方法,可以将轻量级呈现模式与jxbrowser.ipc.external = true J​​VM参数一起使用。在这种情况下,Chromium引擎将在单独的本机进程中初始化,因此您将不再看到此问题。请注意,使用此JVM参数,您只能使用轻量级浏览器模式。)


Swing & SWT(Swing和SWT)

To embed Swing/AWT implementation of com.teamdev.jxbrowser.chromium.swing.BrowserView into SWT application use the org.eclipse.swt.awt.SWT_AWT instance as shown below: (要将com.teamdev.jxbrowser.chromium.swing.BrowserView的Swing / AWT实现嵌入到SWT应用程序中,请使用org.eclipse.swt.awt.SWT_AWT实例,如下所示:)

import java.awt.Frame;
 
import org.eclipse.swt.SWT;
import org.eclipse.swt.awt.SWT_AWT;
import org.eclipse.swt.layout.FillLayout;
import org.eclipse.swt.widgets.Composite;
import org.eclipse.swt.widgets.Display;
import org.eclipse.swt.widgets.Shell;
 
import com.teamdev.jxbrowser.chromium.Browser;
import com.teamdev.jxbrowser.chromium.swing.BrowserView;
 
/**
 * The sample demonstrates how to use JxBrowser Swing control in 
 * SWT application using SWT_AWT bridge.
 */
public class JxBrowserSwingSWT {
    public static void main(String[] arguments) {
        Browser browser = new Browser();
        BrowserView view = new BrowserView(browser);
 
        Display display = new Display();
        Shell shell = new Shell(display);
        shell.setLayout(new FillLayout());
         
        Composite composite = new Composite(shell, 
                SWT.EMBEDDED | SWT.NO_BACKGROUND);
        Frame frame = SWT_AWT.new_Frame(composite);
        frame.add(view);
         
        browser.loadURL("http://google.com");
         
        shell.open();
         
        while (!shell.isDisposed()) {
            if (!display.readAndDispatch()) {
                display.sleep();
            }
        }
        display.dispose();
    }
}


JavaFX & SWT(JavaFX和SWT)

To embed JavaFX implementation of com.teamdev.jxbrowser.chromium.javafx.BrowserView into SWT application use the javafx.embed.swt.FXCanvas instance as shown below: (要将com.teamdev.jxbrowser.chromium.javafx.BrowserView的JavaFX实现嵌入到SWT应用程序中,请使用javafx.embed.swt.FXCanvas实例,如下所示:)

import javafx.embed.swt.FXCanvas;
import javafx.scene.Scene;
 
import org.eclipse.swt.SWT;
import org.eclipse.swt.layout.FillLayout;
import org.eclipse.swt.widgets.Display;
import org.eclipse.swt.widgets.Shell;
 
import com.teamdev.jxbrowser.chromium.Browser;
import com.teamdev.jxbrowser.chromium.javafx.BrowserView;
 
/**
 * The sample demonstrates how to use JxBrowser JavaFX 
 * control in SWT application using FXCanvas.
 */
public class JxBrowserJavaFXSWT {
    public static void main(String[] arguments) {
        Display display = new Display();
        Shell shell = new Shell(display);
        shell.setLayout(new FillLayout());
         
        Browser browser = new Browser();
        FXCanvas canvas = new FXCanvas(shell, SWT.NONE);
         
        // BrowserView instance must be initialized after FXCanvas.
        BrowserView view = new BrowserView(browser);
        canvas.setScene(new Scene(view));
         
        browser.loadURL("http://google.com");
         
        shell.open();
        while (!shell.isDisposed()) {
               if (!display.readAndDispatch()) {
                     display.sleep();
               }
        }
        display.dispose();
    }
}