简体   繁体   中英

How to pass data from WebView to controller and vice-versa in JavaFX

So I've found this tutorial on how to use google maps API in a Desktop JavaFX application.

The point is that I can't figure out how can I pass data from WebView (javascripts variables, jsons..) to controller and viceversa.

I'd like to make an textfield that on textinput to automaticaly search that address and add an marker there (and viceversa when I move the marker to populate the input). The javascript standalone is no problem for me, but I don't know how to call javascript functions from JavaFX controller or how to send back the variables from javascript (longitude, latitude, etc)

See the JavaFX WebView tutorial sections:

  • Processing JavaScript Commands
  • Making Upcalls from JavaScript to JavaFX

Make sure you use JavaFX 2.1+ when doing this, as JavaFX 2.0 does not have full support for upcalls from javaScript to JavaFX.


How to call javascript functions from JavaFX controller?

Java code to be executed after the document has loaded:

webView.getEngine().executeScript("<write your javascript here>");

How to send back the variables from javascript (longitude, latitude, etc)?

Here is a generic communication sample, replace it with the actual Java and JavaScript logic you want to execute.

Java code:

// Add a Java callback object to a WebEngine document once it has loaded.
webEngine.getLoadWorker().stateProperty().addListener(
  new ChangeListener<State>() {  
    @Override public void changed(ObservableValue<? extends State> ov, State oldState, State newState) {
      if (newState == State.SUCCEEDED) {
        JSObject win = (JSObject) webEngine.executeScript("window");
        win.setMember("app", new JavaApp());
      }
    }
  });
}
...
// JavaScript interface object
private class JavaApp {
  public void exit() {
    Platform.exit();
  }
}

JavaScript code (in this case embedded in an onclick handler for a html href):

<a href="about:blank" onclick="app.exit()">Exit the Application</a>

Before you need sure you can use :

import netscape.javascript.JSObject;
  1. Create a project with JavaFx and Maven

2)check these Files:

在此处输入图像描述

HelloApplicaion.java

package com.example.map;

import javafx.application.Application;
import javafx.fxml.FXMLLoader;
import javafx.scene.Scene;
import javafx.stage.Stage;
import java.io.IOException;

public class HelloApplication extends Application {
    
    @Override
    public void start(Stage stage) throws IOException {
        FXMLLoader fxmlLoader = new FXMLLoader(HelloApplication.class.getResource("hello-view.fxml"));
        Scene scene = new Scene(fxmlLoader.load(), 1100, 500);
        stage.setResizable(false);
        stage.setTitle("Hello!");
        stage.setScene(scene);
        stage.show();
    }
    public static void main(String[] args) {
        launch();
    }
}

HelloController.java

package com.example.map;

import javafx.beans.value.ObservableValue;
import javafx.concurrent.Worker;
import javafx.fxml.FXML;
import javafx.fxml.Initializable;
import javafx.scene.control.Button;
import javafx.scene.web.WebEngine;
import javafx.scene.web.WebView;
import javafx.beans.value.ChangeListener;
import netscape.javascript.JSObject;
import java.net.URL;
import java.util.ResourceBundle;
import  java.lang.*;
import javafx.concurrent.Worker.State;
public class HelloController  implements Initializable {
    @FXML
    private WebView view;
    private WebEngine engine;
    @FXML
    private Button b1, b2, b4 ,b3;
    
//    private String link = "file:///index.html";
    private String link = getClass().getResource("index.html").toExternalForm();
    
    @FXML
    protected void from_pc_to_webview() {
        b3.setText("Welcome to JavaFX Application!");
        String name="sssss";
        engine.setJavaScriptEnabled(true);
        engine.executeScript("me()");
    }

    @Override
    public void initialize(URL url, ResourceBundle rb) {
        engine = view.getEngine();
        engine.load(link);
        Worker<Void> worker = engine.getLoadWorker();

        worker.stateProperty().addListener(new ChangeListener<State>() {
            @Override
            public void changed(ObservableValue<? extends State> observableValue, State state, State t1) {

                if (t1 == Worker.State.SUCCEEDED) {
                    JSObject window = (JSObject) engine.executeScript("window");
                    window.setMember("myObject", new MyObject());

                }

            }
        });

    }//initialize

    public static class MyObject {

        public void doIt() {
            System.out.println("Get data from Html <---------");
        }
    }

    @FXML
    protected void b1() {
//        b4.setText("Welcome to JavaFX Application!");
        engine.setJavaScriptEnabled(true);
        String me="ddddddddddddddddddddddddddddddddddddddddddddd";
        engine.executeScript("me('"+me+"');");
        System.out.println("eeeeeeeeeeeeeeeeeeeeeeeeee");
    }

}//CLASS

hello-view.fxml

<?xml version="1.0" encoding="UTF-8"?>

<?import javafx.scene.control.*?>
<?import javafx.scene.layout.*?>
<?import javafx.scene.web.*?>

<AnchorPane maxHeight="-Infinity" maxWidth="-Infinity" minHeight="-Infinity" minWidth="-Infinity" prefHeight="400.0" prefWidth="600.0" xmlns="http://javafx.com/javafx/16" xmlns:fx="http://javafx.com/fxml/1" fx:controller="com.example.map.HelloController">
    <children>
        <WebView fx:id="view" layoutX="50.0" layoutY="0.0" prefHeight="2.0" prefWidth="3.0" AnchorPane.bottomAnchor="30.0" AnchorPane.leftAnchor="100.0" AnchorPane.rightAnchor="0.0" AnchorPane.topAnchor="60.0" />

        <Button fx:id="b1" layoutX="0.0" layoutY="0.0" mnemonicParsing="false" text="b1"     onAction="#b1"  />
        <Button fx:id="b2" layoutX="55.0" layoutY="0.0" mnemonicParsing="false" text="b2" />
        <Button fx:id="b3" layoutX="165.0" layoutY="0.0" mnemonicParsing="false" text="send_to_web"   onAction="#from_pc_to_webview"/>
    </children>
</AnchorPane>

index.html

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <title>Title</title>
</head>
<body>
<form id="form1" name="form1">
    <input type="text" id="text1">text value</input>
</form>
<button onclick="java.hi()">Submit</button>
<br/>
<div id="fd">fffffffff</div>
<button onclick="me()">me</button>
<button onclick="ddddddddddd()">html--->java</button>
<button onclick="ddddddddddd()">ddddddddddd</button>
<script>
    function  me(me){
        var myDiv = document.getElementById("fd");
        myDiv.innerHTML = me;

    }
    function  ddddddddddd(){
        var myDiv = document.getElementById("fd");
        myDiv.innerHTML = "-------------------";
        window.myObject.doIt();
    }
    
</script>

</body>
</html>

在此处输入图像描述

Maybe you need to update your Maven :

在此处输入图像描述

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM