Open magreenblatt opened 9 years ago
Original comment by Patrick Sweeney (Bitbucket: Klobersaurus).
I have been wanting this for months. The JavaFX WebView is not cutting it from a Javascript performance standpoint. I also tried with the SwingNode but JCEF would not render, at all. SwingNode has a disclaimer saying that it cannot render anything too complicated.
Original comment by Anand Tiwari (Bitbucket: anandktiwari26, GitHub: anandktiwari26).
Hello Sebastian Klaar, Try it.
CefApp cefApp = CefApp.getInstance(); CefClient client = cefApp.createClient(); CefBrowser browser = client.createBrowser("https://www.google.com", OS.isLinux(), false); Component browerUI = browser.getUIComponent(); JPanel panel = new JPanel(); panel.add(browerUI); SwingNode swingNode = new SwingNode(); swingNode.setContent(panel);
Original comment by Patrick Sweeney (Bitbucket: Klobersaurus).
Anand Tiwari, I just tried this and had no luck. Did you actually manage to get this to work? I'm developing against JDK8u40 64-bit on Windows 7.
Here's some information on JOGL's attempts to integrate with JavaFX: https://jogamp.org/bugzilla/show_bug.cgi?id=607. Sounds like using JOGL + JavaFX on Windows at least is not currently possible, so we would be looking at developing an alternative JavaFX-based off-screen rendering implementation to completely replace the JOGL usage. I'm not sure what would be required to support windowed JCEF with JavaFX or if that even makes sense given JavaFX's intended usage.
Original comment by Aaron Ong (Bitbucket: Aaron Ong).
Hi. I needed to embed CEF into our pre-existing JavaFX UI as well, so I did a little experimenting. What worked for me was going into the CefBrowserOsr.java file, and changing the type of canvas_
from GLCanvas
to GLJPanel
, which is a lightweight component that's compatible with JavaFX's SwingNode
. The two classes seem to be mostly equivalent, so you don't have to change any method calls to canvas_
.
The only caveat with this approach is that you must use OSR mode for this to work, but I'll take anything I can get at this point. I also haven't checked if there are any side effects, but I've tested it a bit so far and it seems to be enough for our use case.
Edit: The only issue I've seen so far is that backspace, tab, and certain other keys don't work when embedded in a SwingNode
, but they do when using Swing.
Original comment by Aaron Ong (Bitbucket: Aaron Ong).
I did a little more digging, and it turns out that the problem with the backspace key was due to JavaFX's different way of handling key events. It took a bit of hackery, but I created a new SwingNode class that overrides the default key handling behavior of the original JavaFX version: http://pastebin.com/EA26Mz6m
The main difference here starts at line 45, where it just copies the key code value (cast into a char) to the key char value if key char's integer value is 0. I'm not sure if this is entirely correct, but I was able to get backspace to work, at least.
Original comment by Aaron Ong (Bitbucket: Aaron Ong).
I can't test this right now because I don't have the right environment. This one uses the modified SwingNode I provided to make the backspace key work. Some other keys still don't work correctly though, so I guess it still needs some more remapping.
import javafx.application.Application; import javafx.scene.Scene; import javafx.scene.layout.Pane; import javafx.stage.Stage; import org.cef.CefApp; import org.cef.CefClient; import org.cef.browser.CefBrowser;
import javax.media.opengl.awt.GLJPanel;
public class CefBrowserSample extends Application {
@Override
public void start( Stage primaryStage ) {
Pane root = new Pane();
SwingNode swingNode = new SwingNode();
root.getChildren().add( swingNode );
Scene scene = new Scene( root, 500, 500 );
primaryStage.setTitle( "JCEF Example" );
primaryStage.setScene( scene );
CefApp app = CefApp.getInstance();
CefClient client = app.createClient();
CefBrowser browser = client.createBrowser( "www.google.com", true, false );
swingNode.setContent( ( GLJPanel) browser.getUIComponent() );
primaryStage.show();
}
public static void main( String[] args ) {
launch( args );
}
}
Original comment by DragonWarri0r (Bitbucket: DragonWarri0r, GitHub: DragonWarri0r).
@aaon, it`s works, but very-very slow
Original comment by Aaron Ong (Bitbucket: Aaron Ong).
You'll have to go native if you want a proper JavaFX implementation of JCEF btw
A PR to add this functionality could be accepted if the changes are reasonable in scope.
Original comment by truejasonxiefans (Bitbucket: truejasonxiefans).
Any further news or plan for this feature?. We are suffering from intergrating the JCEF into JavaFX.
Original comment by Marcus Ataide (Bitbucket: Marcus Ataide).
Any news?
Original comment by Former user (Bitbucket: Former user).
Is there any news about this issue?
Also, I see from earlier comments that many people wanted this feature long time ago. Is there anyone who can share if they found a hack/temporary solution? Is it possible to get a ~not perfect~ but decent performance in JavaFX?
Original comment by Vinicius Lemes Da Silva (Bitbucket: Vinicius Lemes).
Any news on this?
Original comment by doni mbeng (Bitbucket: jeffartdo).
Hello did some have solution about JCEF into JavaFX
Original comment by ZUchiha Shishui (Bitbucket: zuchiha shishui).
Hi Dev. Please add JCEF to JavaFX. Pleaseeeeeeeeeeeeee
Original comment by Chigozirim Chukwu (Bitbucket: smac89, GitHub: smac89).
There is a promising project which could potentially allow one to embed a GLCanvas in a javafx node (not SwingNode).
https://github.com/eclipse-efx/efxclipse-drift
I have a ready-to-go fork which uses gradle to run the application so you can see it in action:
https://github.com/smac89/efxclipse-drift
If anyone has the know-how, they can contribute to this project so that we can see this happen sooner than later.
Original comment by ZUchiha Shishui (Bitbucket: zuchiha shishui).
This issue have existed since 2015, now In 2019, They couldn’t fixed it. What are they doing?
Original comment by Dominik (Bitbucket: domino2, GitHub: domino2).
From my view of perspective, this should be highly prioritize as web technologies are taking over the desktop for long time already and I suppose that we want to keep Java as good desktop gui as it was. Out there are not so good GUI frameworks and result of this issue can boost right direction and potentially offer nice transferability to different CEF implementation.
Original comment by Omar Mainegra (Bitbucket: Omar Mainegra).
News about this?
Original comment by Bohdan Shkliarenko (Bitbucket: Bohdan Shkliarenko).
What about new PixelBuffer in OpenJFX 13? Or NativeFX project?
I saw some experiments with new PixelBuffer and vlcj (https://twitter.com/hashtag/vlcj)
I think we all are getting closer to use cef project inside JavaFX without swing.
Original comment by Lucas Owen (Bitbucket: Lucas Owen).
this needs to be top priority IMO
Original comment by Mitch Francis (Bitbucket: Mitch Francis).
There seems to be a few questions that need to be answered before this can be resolved:
My thoughts on a solution are the following
Create a CefView class that derives from Parent and either:
OR
I’m still digging to understand the complexities, but have a vested interest in solving this issue. Feel free to provide an details or insights if I have overlooked something critical.
Original comment by Jacky Guo (Bitbucket: jgcodes, GitHub: jgcodes).
This Stack Overflow question seems to suggest that Prism can use OpenGL internally.
https://stackoverflow.com/a/16949909/10808912
If that’s right, porting everything into Prism might be a wee bit easier. For you guys pleading, I want this too, but don’t spam comment.
Update: I find that Prism doesn’t have a stable API. That’s a huge shame.
Original comment by Thomas Wilde (Bitbucket: Thomas Wilde).
This project is an excellent working example of JCEF in JavaFX via a modified SwingNode and OSR.
https://github.com/wang9426/FxJCEF
If there is a way to avoid a SwingNode altogether, that’d be great.
Original comment by laram (Bitbucket: laram, GitHub: laram).
如何将miniblink集成到javafx中来啊?https://github.com/weolar/miniblink49 https://stackoverflow.com/questions/62577832/how-does-javafx-integrate-miniblink-with-chromium-core
Original comment by Jacky Guo (Bitbucket: jgcodes, GitHub: jgcodes).
For a public API for this, I’d add a new method to CefBrowser
, used like so:
CefClient client = CefApp.getInstance.createClient();
CefBrowser browser = client.createBrowser();
Node cefNode = browser.getFxUIComponent();
Also, if you upgraded to Java 11+, you would be able to take advantage of PixelBuffer. If the pixel data used for OSR can be represented by a java.nio.Buffer
or one of its subclasses, you could simply have a pixel buffer writing images to the screen.
https://openjfx.io/javadoc/14/javafx.graphics/javafx/scene/image/PixelBuffer.html
Original comment by Jacky Guo (Bitbucket: jgcodes, GitHub: jgcodes).
Check out NativeFX.
https://github.com/miho/NativeFX
You might be able to use Miniblink or CEF with it.
Original comment by Jacky Guo (Bitbucket: jgcodes, GitHub: jgcodes).
Sorry, I haven’t made a demo yet. I might see if I can figure something out.
EDIT: see proposal #381 for a general idea of the internal workings. I have yet to find a buffer to work off of.
Original comment by Jacky Guo (Bitbucket: jgcodes, GitHub: jgcodes).
@{557058:2f2a2aee-b500-4023-9734-037e9897c3ab} and others, this is a rough sketch of how PixelBuffer can be used to skip the JOGL usage when it comes to JFX.
https://gist.github.com/jgcodes2020/e5d99fbf9aa6bfcf7f1f9d53b60d4eb8
Issue #381 was marked as a duplicate of this issue.
Original comment by Peng Liu (Bitbucket: Dapengsechs, GitHub: Dapengsechs).
Aaron Ong
Hi. I needed to embed CEF into our pre-existing JavaFX UI as well, so I did a little experimenting. What worked for me was going into the CefBrowserOsr.java file, and changing the type of
canvas_
fromGLCanvas
toGLJPanel
, which is a lightweight component that's compatible with JavaFX'sSwingNode
. The two classes seem to be mostly equivalent, so you don't have to change any method calls tocanvas_
.The only caveat with this approach is that you must use OSR mode for this to work, but I'll take anything I can get at this point. I also haven't checked if there are any side effects, but I've tested it a bit so far and it seems to be enough for our use case.
Edit: The only issue I've seen so far is that backspace, tab, and certain other keys don't work when embedded in a
SwingNode
, but they do when using Swing.
Yes, the solution of Aaron Ong works perfect when the off-screen mode is true.
How can we make it also work for not-off-screen (off-screen mode is false)? i.e. using CefBrowserWr.java?
Because applying the same modification above to CefBrowserWr.java doen’t work. But withou necessary modification an error will be thrown.
org.cef.browser.CefBrowserWr$3 cannot be cast to com.jogamp.opengl.awt.GLJPanel
Exception in thread "JavaFX Application Thread" java.lang.ClassCastException: org.cef.browser.CefBrowserWr$3 cannot be cast to com.jogamp.opengl.awt.GLJPanel
at org.charts.dataviewer.javafx.jcef.CefWebview.getBrowser(CefWebview.java:43)
at org.charts.dataviewer.javafx.jcef.CefWebview.load(CefWebview.java:30)
at org.charts.dataviewer.javafx.JavaFxDataViewer.createCefView(JavaFxDataViewer.java:51)
at org.charts.dataviewer.javafx.JavaFxDataViewer.<init>(JavaFxDataViewer.java:39)
at eu.akka.ptsw.fleetcommander.view.charts.JavaFxDataViewerFactory.createMapPlot(JavaFxDataViewerFactory.java:197)
at eu.akka.ptsw.dletnt.javafx.plotly.factory.TestMapPlot.showVehicleMapPlot(TestMapPlot.java:123)
at eu.akka.ptsw.dletnt.javafx.plotly.factory.TestMapPlot.lambda$0(TestMapPlot.java:60)
at com.sun.javafx.event.CompositeEventHandler.dispatchBubblingEvent(CompositeEventHandler.java:86)
at com.sun.javafx.event.EventHandlerManager.dispatchBubblingEvent(EventHandlerManager.java:238)
at com.sun.javafx.event.EventHandlerManager.dispatchBubblingEvent(EventHandlerManager.java:191)
at com.sun.javafx.event.CompositeEventDispatcher.dispatchBubblingEvent(CompositeEventDispatcher.java:59)
at com.sun.javafx.event.BasicEventDispatcher.dispatchEvent(BasicEventDispatcher.java:58)
at com.sun.javafx.event.EventDispatchChainImpl.dispatchEvent(EventDispatchChainImpl.java:114)
at com.sun.javafx.event.BasicEventDispatcher.dispatchEvent(BasicEventDispatcher.java:56)
at com.sun.javafx.event.EventDispatchChainImpl.dispatchEvent(EventDispatchChainImpl.java:114)
at com.sun.javafx.event.BasicEventDispatcher.dispatchEvent(BasicEventDispatcher.java:56)
at com.sun.javafx.event.EventDispatchChainImpl.dispatchEvent(EventDispatchChainImpl.java:114)
at com.sun.javafx.event.BasicEventDispatcher.dispatchEvent(BasicEventDispatcher.java:56)
at com.sun.javafx.event.EventDispatchChainImpl.dispatchEvent(EventDispatchChainImpl.java:114)
at com.sun.javafx.event.BasicEventDispatcher.dispatchEvent(BasicEventDispatcher.java:56)
at com.sun.javafx.event.EventDispatchChainImpl.dispatchEvent(EventDispatchChainImpl.java:114)
at com.sun.javafx.event.EventUtil.fireEventImpl(EventUtil.java:74)
at com.sun.javafx.event.EventUtil.fireEvent(EventUtil.java:49)
at javafx.event.Event.fireEvent(Event.java:198)
at javafx.scene.Node.fireEvent(Node.java:8411)
at javafx.scene.control.Button.fire(Button.java:185)
at com.sun.javafx.scene.control.behavior.ButtonBehavior.mouseReleased(ButtonBehavior.java:182)
at com.sun.javafx.scene.control.skin.BehaviorSkinBase$1.handle(BehaviorSkinBase.java:96)
at com.sun.javafx.scene.control.skin.BehaviorSkinBase$1.handle(BehaviorSkinBase.java:89)
at com.sun.javafx.event.CompositeEventHandler$NormalEventHandlerRecord.handleBubblingEvent(CompositeEventHandler.java:218)
at com.sun.javafx.event.CompositeEventHandler.dispatchBubblingEvent(CompositeEventHandler.java:80)
at com.sun.javafx.event.EventHandlerManager.dispatchBubblingEvent(EventHandlerManager.java:238)
at com.sun.javafx.event.EventHandlerManager.dispatchBubblingEvent(EventHandlerManager.java:191)
at com.sun.javafx.event.CompositeEventDispatcher.dispatchBubblingEvent(CompositeEventDispatcher.java:59)
at com.sun.javafx.event.BasicEventDispatcher.dispatchEvent(BasicEventDispatcher.java:58)
at com.sun.javafx.event.EventDispatchChainImpl.dispatchEvent(EventDispatchChainImpl.java:114)
at com.sun.javafx.event.BasicEventDispatcher.dispatchEvent(BasicEventDispatcher.java:56)
at com.sun.javafx.event.EventDispatchChainImpl.dispatchEvent(EventDispatchChainImpl.java:114)
at com.sun.javafx.event.BasicEventDispatcher.dispatchEvent(BasicEventDispatcher.java:56)
at com.sun.javafx.event.EventDispatchChainImpl.dispatchEvent(EventDispatchChainImpl.java:114)
at com.sun.javafx.event.BasicEventDispatcher.dispatchEvent(BasicEventDispatcher.java:56)
at com.sun.javafx.event.EventDispatchChainImpl.dispatchEvent(EventDispatchChainImpl.java:114)
at com.sun.javafx.event.BasicEventDispatcher.dispatchEvent(BasicEventDispatcher.java:56)
at com.sun.javafx.event.EventDispatchChainImpl.dispatchEvent(EventDispatchChainImpl.java:114)
at com.sun.javafx.event.EventUtil.fireEventImpl(EventUtil.java:74)
at com.sun.javafx.event.EventUtil.fireEvent(EventUtil.java:54)
at javafx.event.Event.fireEvent(Event.java:198)
at javafx.scene.Scene$MouseHandler.process(Scene.java:3757)
at javafx.scene.Scene$MouseHandler.access$1500(Scene.java:3485)
at javafx.scene.Scene.impl_processMouseEvent(Scene.java:1762)
at javafx.scene.Scene$ScenePeerListener.mouseEvent(Scene.java:2494)
at com.sun.javafx.tk.quantum.GlassViewEventHandler$MouseEventNotification.run(GlassViewEventHandler.java:394)
at com.sun.javafx.tk.quantum.GlassViewEventHandler$MouseEventNotification.run(GlassViewEventHandler.java:295)
at java.security.AccessController.doPrivileged(Native Method)
at com.sun.javafx.tk.quantum.GlassViewEventHandler.lambda$handleMouseEvent$2(GlassViewEventHandler.java:432)
at com.sun.javafx.tk.quantum.QuantumToolkit.runWithoutRenderLock(QuantumToolkit.java:410)
at com.sun.javafx.tk.quantum.GlassViewEventHandler.handleMouseEvent(GlassViewEventHandler.java:431)
at com.sun.glass.ui.View.handleMouseEvent(View.java:555)
at com.sun.glass.ui.View.notifyMouse(View.java:937)
at com.sun.glass.ui.win.WinApplication._runLoop(Native Method)
at com.sun.glass.ui.win.WinApplication.lambda$null$3(WinApplication.java:177)
at java.lang.Thread.run(Thread.java:748)
Original comment by Former user (Bitbucket: Former user).
Another idea on ‘GitLab.com’, projects ‘jfx-cef' and working example for Windows10 ‘jfx-cef-sample’.
Original comment by Jacky Guo (Bitbucket: jgcodes, GitHub: jgcodes).
@linasch are you talking about this? https://gitlab.com/linasch/jfx-cef/-/tree/jfx
Feel free to copy your repo to Bitbucket and submit a PR.
Original comment by Former user (Bitbucket: Former user).
@Jacky Guo this link: https://gitlab.com/linasch/jfx-cef (Mirrored from https://bitbucket.org/chromiumembedded/java-cef/src/master/ ). CefBrowserWrFX extends CefBrowserWr
(without offscreen mode). working example: https://gitlab.com/linasch/jfx-cef-sample
Original comment by Thomas Wilde (Bitbucket: Thomas Wilde).
I tried this example but get the following error.
A fatal error has been detected by the Java Runtime Environment:
EXCEPTION_ACCESS_VIOLATION (0xc0000005) at pc=0x00000000714c4f57, pid=22952, tid=0x0000000000004aec
However, I am using the Jcef build from the build provided in the working SwingNode example I previously mentioned: https://github.com/wang9426/FxJCEF.
Perhaps I need to go through the cmake build in the gitlab project?
Original comment by Former user (Bitbucket: Former user).
@{557058:51c10212-0673-4c29-961e-6e6cd8cd250a} https://github.com/wang9426/FxJCEF is another approach that dont fit. The build must be done out of https://gitlab.com/linasch/jfx-cef and then can be used by https://gitlab.com/linasch/jfx-cef-sample.
this works with WebGL and without OSR Mode.
Original comment by Thomas Wilde (Bitbucket: Thomas Wilde).
@linasch Thanks for the info. Would you mind posting your build? I would love to test it and compare the performance to the previous SwingNode with osr solution.
Original comment by Thomas Wilde (Bitbucket: Thomas Wilde).
JCEF in JavaFX Summary:
Method 1: Confirmed working by Thomas Wilde
Working JCEF in JavaFX, CEF already built:
https://github.com/wang9426/FxJCEF
Minor Drawbacks: slightly slow but really not bad. Tabbing inside the browser does not work. I have been using this in my projects for some time (JDK8)
One problem I have with this is if I take the Browser off of a scene, when I bring it back it no longer renders and I have to start a new browser. I made a listener with ReActFX to load a new browser when the browser is brought back to the scene. This isn’t extremely bad except for when I user is logged into a website, they will then have to log in again.
Method 2: Has not been confirmed as far as I’m aware
Unconfirmed method, using PixelBuffer in JDK11+ instead of swingnode
https://gist.github.com/jgcodes2020/e5d99fbf9aa6bfcf7f1f9d53b60d4eb8
Method 3: Confirmed to work by Linasch but I have not personally built it and confirmed. Curious on the performance and if this is prefered to Method 1.
https://gitlab.com/linasch/jfx-cef and then can be used by https://gitlab.com/linasch/jfx-cef-sample.
this works with WebGL and without OSR Mode.
Original report by sebastian klaar (Bitbucket: sebastian klaar).
I'd like to use JCEF with JavaFX. It seems not possible to do this via a SwingNode. The only option I see is to provide a JavaFX node instead of AWT.
JavaFX-WebView is not an option, since there is no WebGL support...