1

I have some code snipped out of a much bigger app, which renders some white text on a black background in a JavaFX WebView. The background colour of the page is set to transparent, using some code from Transparent background in the WebView in JavaFX

import java.lang.reflect.Field;
import org.w3c.dom.Document;
import com.sun.webkit.WebPage;
import javafx.application.Application;
import javafx.beans.value.ChangeListener;
import javafx.beans.value.ObservableValue;
import javafx.scene.Scene;
import javafx.scene.layout.StackPane;
import javafx.scene.paint.Color;
import javafx.scene.web.WebEngine;
import javafx.scene.web.WebView;
import javafx.stage.Stage;

public class TestWebView extends Application {

  public void start(Stage stage) throws Exception {
    StackPane stackpane = new StackPane();
    Scene scene = new Scene(stackpane, stage.getWidth(), stage.getHeight(), Color.BLACK);
    stage.setScene(scene);
    scene.setFill(Color.BLACK);
    stackpane.setStyle("-fx-background-color: BLACK");
    WebView webview = new WebView();
    stackpane.getChildren().add(webview);
    WebEngine webengine = webview.getEngine();
    webengine.documentProperty().addListener(new WebDocumentListener(webengine));
    webengine.loadContent("<p style='color:white'>Hello World</p>");
    stage.show();
  }

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

  protected class WebDocumentListener implements ChangeListener<Document> {
    private final WebEngine wdl_webEngine;

    public WebDocumentListener(WebEngine webEngine) {
      wdl_webEngine = webEngine;
    }

    @Override
    public void changed(ObservableValue<? extends Document> arg0, Document arg1, Document arg2) {
      try {
        Field f = wdl_webEngine.getClass().getDeclaredField("page");
        f.setAccessible(true);
        com.sun.webkit.WebPage page = (WebPage) f.get(wdl_webEngine);
        page.setBackgroundColor((new java.awt.Color(0, 0, 0, 0)).getRGB());
      } catch (Exception e) {
        e.printStackTrace();
      }
    }
  }
}

Testing on MacOS 10.11.6, with Oracle's JDK:

With JDK 1.8.0_152, this code works nicely - I get white text on black. (And the transparency works too when I layer things underneath it in the stackpane)

With JDK 9 (9+181), com.sun.webkit.WebPage is no longer accessible, so I have to compile and run it with --add-exports javafx.web/com.sun.webkit=ALL-UNNAMED - but having done that, I get black text on a black screen. I can tell the text is there by selecting the text and dragging it, which makes the text appear white while being dragged.

Ideally, I'd like to keep a single codebase that works for both JDK 8 and 9. (Java's usually been good to me with backward compatibility). Or as a second best, how do I get the white text I'm expecting in JDK 9?

Can anyone point me in the right direction? Many thanks in advance.

1 Answers1

3

I had the same issue, I solved it by going further in the reflective process :

Field f = webEngine.getClass().getDeclaredField("page");
f.setAccessible(true);
Object page = f.get(webEngine);
Method m = page.getClass().getMethod("setBackgroundColor", int.class);
m.setAccessible(true);
m.invoke(page, (new java.awt.Color(0, 0, 0, 0)).getRGB());
maginth
  • 44
  • 3
  • Have plunged into JDK 11 since posting - but thanks - the above worked for me - if I add these on the VM commandline. `--add-modules javafx.controls,javafx.web --add-opens javafx.web/javafx.scene.web=ALL-UNNAMED --add-opens javafx.web/com.sun.webkit=ALL-UNNAMED` the first argument is to get JavaFX working, having added all the JavaFX JARs to the *Modulepath* in project properties (Eclipse). And the second two bits allow the accessibility to be set. After that, it runs, and I see the white text. – Wes Hinsley Nov 06 '18 at 14:54