Using JavaFX UI Controls

Previous
Next

19 HTML Editor

In this chapter, you learn how to edit text in your JavaFX applications by using the embedded HTML editor.

The HTMLEditor control is a full functional rich text editor. Its implementation is based on the document editing feature of HTML5 and includes the following editing functions:

  • Text formatting including bold, italic, underline, and strike though styles

  • Paragraph settings such as format, font family, and font size

  • Foreground and background colors

  • Text indent

  • Bulleted and numbered lists

  • Text alignment

  • Adding a horizontal rule

  • Copying and pasting text fragments

Figure 19-1 shows a rich text editor added to a JavaFX application.

The HTMLEditor class presents the editing content in the form of an HTML string. For example, the content typed in the editor in Figure 19-1 is presented by the following string: "<html><head></head><body contenteditable="true"><h1>Heading</h1><div><u>Text</u>, some text</div></body></html>."

Because the HTMLEditor class is an extension of the Node class, you can apply visual effects or transformations to its instances.

Adding an HTML Editor

Like any other UI control, the HTMLEditor component must be added the scene so that it can appear in your application. You can add it directly to the scene as shown in Example 19-1 or through a layout container as done in other examples.

Example 19-1 Adding an HTML Editor to a JavaFX Application

import javafx.application.Application;
import javafx.scene.Scene;
import javafx.scene.web.HTMLEditor;
import javafx.stage.Stage;
 
public class HTMLEditorSample extends Application {
 
    @Override
    public void start(Stage stage) {
        stage.setTitle("HTMLEditor Sample");
        stage.setWidth(400);
        stage.setHeight(300);   
        final HTMLEditor htmlEditor = new HTMLEditor();
        htmlEditor.setPrefHeight(245);
        Scene scene = new Scene(htmlEditor);       
        stage.setScene(scene);
        stage.show();
    }
 
    public static void main(String[] args) {
        launch(args);
    }
}

Compiling and running this code fragment produces the window shown in Figure 19-2.

Figure 19-2 Initial View of the HTMLEditor Component

Description of Figure 19-2 follows
Description of "Figure 19-2 Initial View of the HTMLEditor Component"

The formatting toolbars are provided in the implementation of the component. You cannot toggle their visibility. However, you still can customize the appearance of the editor by applying CSS style, as shown in Example 19-2.

Example 19-2 Styling the HTMLEditor

htmlEditor.setStyle(
    "-fx-font: 12 cambria;"
    + "-fx-border-color: brown; "
    + "-fx-border-style: dotted;"
    + "-fx-border-width: 2;"
);

When this code line is added to Example 19-1, the editor changes, as shown in Figure 19-3.

Figure 19-3 Alternative View of the HTMLEditor Component

Description of Figure 19-3 follows
Description of "Figure 19-3 Alternative View of the HTMLEditor Component"

The applied style changes the border of the component and the font of the formatting toolbars.

The HTMLEditor class provides a method to define the content that appears in the editing area when the application starts. Use the setHtmlText method, as shown in Example 19-3 to set the initial text for the editor.

Example 19-3 Setting the Text Content

private final String INITIAL_TEXT = "<html><body>Lorem ipsum dolor sit "
    + "amet, consectetur adipiscing elit. Nam tortor felis, pulvinar "
    + "in scelerisque cursus, pulvinar at ante. Nulla consequat"
    + "congue lectus in sodales. Nullam eu est a felis ornare "
    + "bibendum et nec tellus. Vivamus non metus tempus augue auctor "
    + "ornare. Duis pulvinar justo ac purus adipiscing pulvinar. "
    + "Integer congue faucibus dapibus. Integer id nisl ut elit "
    + "aliquam sagittis gravida eu dolor. Etiam sit amet ipsum "
    + "sem.</body></html>";

htmlEditor.setHtmlText(INITIAL_TEXT);

Figure 19-4 demonstrates the text editor with the text set by using the setHTMLText method.

Figure 19-4 HTMLEditor with the Predefined Text Content

Description of Figure 19-4 follows
Description of "Figure 19-4 HTMLEditor with the Predefined Text Content"

You can use the HTML tags in this string to apply specific formatting for the initially rendered content.

Using an HTML Editor to Build the User Interface

You can use the HTMLEditor control to implement typical user interfaces (UIs) in your JavaFX applications. For example, you can implement instant messenger services, email clients, or even content management systems.

presents the user interface of a message composing window that you can find in many email client applications.

Example 19-4 HTMLEditor Added to the Email Client UI

import javafx.application.Application;
import javafx.collections.FXCollections;
import javafx.geometry.Insets;
import javafx.geometry.Pos;
import javafx.scene.Group;
import javafx.scene.Scene;
import javafx.scene.control.*;
import javafx.scene.layout.GridPane;
import javafx.scene.layout.VBox;
import javafx.scene.web.HTMLEditor;
import javafx.stage.Stage;
 
public class HTMLEditorSample extends Application {
    
    @Override
    public void start(Stage stage) {
        stage.setTitle("Message Composing");
        stage.setWidth(500);
        stage.setHeight(500);
        Scene scene = new Scene(new Group());
    
        final VBox root = new VBox();        
        root.setPadding(new Insets(8, 8, 8, 8));
        root.setSpacing(5);
        root.setAlignment(Pos.BOTTOM_LEFT);
        
        final GridPane grid = new GridPane();
        grid.setVgap(5);
        grid.setHgap(10);
              
        final ChoiceBox sendTo = 
            new ChoiceBox(FXCollections.observableArrayList(
                "To:", "Cc:", "Bcc:")
        );
        
        sendTo.setPrefWidth(100);                
        GridPane.setConstraints(sendTo, 0, 0);
        grid.getChildren().add(sendTo);
        
        final TextField tbTo = new TextField();
        tbTo.setPrefWidth(400);
        GridPane.setConstraints(tbTo, 1, 0);
        grid.getChildren().add(tbTo);
        
        final Label subjectLabel = new Label("Subject:");
        GridPane.setConstraints(subjectLabel, 0, 1);
        grid.getChildren().add(subjectLabel);        
        
        final TextField tbSubject = new TextField();
        tbTo.setPrefWidth(400);
        GridPane.setConstraints(tbSubject, 1, 1);
        grid.getChildren().add(tbSubject);
        
        root.getChildren().add(grid);
        
        final HTMLEditor htmlEditor = new HTMLEditor();
        htmlEditor.setPrefHeight(370);
 
        root.getChildren().addAll(htmlEditor, new Button("Send"));        
      
        final Label htmlLabel = new Label();
        htmlLabel.setWrapText(true);
                      
        scene.setRoot(root);
        stage.setScene(scene);
        stage.show();
    }
 
    public static void main(String[] args) {
        launch(args);
    }
}

The user interface includes a choice box to select a type of recipient, two text fields to enter the email address and the subject of the message, a label to indicate the subject field, the editor, and the Send button.

The UI controls are arranged on the application scene by using the Grid and VBox layout containers. When you compile and run this application, the window shown in Figure 19-5 shows the output of this application when a user is composing a weekly report.

Figure 19-5 Email Client User Interface

Description of Figure 19-5 follows
Description of "Figure 19-5 Email Client User Interface"

You can set the specific width and height values for the HTMLEditor object by calling the setPrefWidth or setPrefHeight methods, or you can leave its width and height unspecified. Example 19-4 specifies the height of the component. Its width is defined by the VBox layout container. When the text content exceeds the height of the editing area, the vertical scroll bar appears.

Obtaining HTML Content

With the JavaFX HTMLEditor control, you can edit text and set the initial content. In addition, you can obtain the entered and edited text in HTML format. The application shown in Example 19-5 implements this task.

Example 19-5 Retrieving HTML Code

import javafx.application.Application;
import javafx.event.ActionEvent;
import javafx.event.EventHandler;
import javafx.geometry.Insets;
import javafx.geometry.Pos;
import javafx.scene.Group;
import javafx.scene.Scene;
import javafx.scene.control.*;
import javafx.scene.layout.VBox;
import javafx.scene.web.HTMLEditor;
import javafx.stage.Stage;
 
public class HTMLEditorSample extends Application {    
    private final String INITIAL_TEXT = "Lorem ipsum dolor sit "
            + "amet, consectetur adipiscing elit. Nam tortor felis, pulvinar "
            + "in scelerisque cursus, pulvinar at ante. Nulla consequat"
            + "congue lectus in sodales. Nullam eu est a felis ornare "
            + "bibendum et nec tellus. Vivamus non metus tempus augue auctor "
            + "ornare. Duis pulvinar justo ac purus adipiscing pulvinar. "
            + "Integer congue faucibus dapibus. Integer id nisl ut elit "
            + "aliquam sagittis gravida eu dolor. Etiam sit amet ipsum "
            + "sem.";
 
    @Override
    public void start(Stage stage) {
        stage.setTitle("HTMLEditor Sample");
        stage.setWidth(500);
        stage.setHeight(500);
        Scene scene = new Scene(new Group());
    
        VBox root = new VBox();      
        root.setPadding(new Insets(8, 8, 8, 8));
        root.setSpacing(5);
        root.setAlignment(Pos.BOTTOM_LEFT);
              
        final HTMLEditor htmlEditor = new HTMLEditor();
        htmlEditor.setPrefHeight(245);
        htmlEditor.setHtmlText(INITIAL_TEXT);       
 
        final TextArea htmlCode = new TextArea();
        htmlCode.setWrapText(true);
    
        ScrollPane scrollPane = new ScrollPane();
        scrollPane.getStyleClass().add("noborder-scroll-pane");
        scrollPane.setContent(htmlCode);
        scrollPane.setFitToWidth(true);
        scrollPane.setPrefHeight(180);
 
        Button showHTMLButton = new Button("Produce HTML Code");
        root.setAlignment(Pos.CENTER);
        showHTMLButton.setOnAction(new EventHandler<ActionEvent>() {
            @Override public void handle(ActionEvent arg0) {
                htmlCode.setText(htmlEditor.getHtmlText());
            }
        });
        
        root.getChildren().addAll(htmlEditor, showHTMLButton, scrollPane);
        scene.setRoot(root);
 
        stage.setScene(scene);
        stage.show();
    }
 
    public static void main(String[] args) {
        launch(args);
    }
}

The getHTMLText method called on the HTMLEditor object derives the edited content and presents it as an HTML string. This information is passed to the text area, so that you can observe, copy, and paste the produced HTML code. Figure 19-6 shows an HTML code of the text is being edited in the HTMLEditor sample.

Figure 19-6 Obtaining the HTML Content

Description of Figure 19-6 follows
Description of "Figure 19-6 Obtaining the HTML Content"

Similarly, you can obtain HTML code and save it in the file or send it to the WebView object to synchronize content in the editor and the embedded browser. See how this task is implemented in Example 19-6.

Example 19-6 Rendering Edited HTML Content in a Browser

import javafx.application.Application;
import javafx.event.ActionEvent;
import javafx.event.EventHandler;
import javafx.geometry.Insets;
import javafx.geometry.Pos;
import javafx.scene.Group;
import javafx.scene.Scene;
import javafx.scene.control.*;
import javafx.scene.layout.VBox;
import javafx.scene.web.HTMLEditor;
import javafx.scene.web.WebEngine;
import javafx.scene.web.WebView;
import javafx.stage.Stage;
 
public class HTMLEditorSample extends Application {
    private final String INITIAL_TEXT = "Lorem ipsum dolor sit "
            + "amet, consectetur adipiscing elit. Nam tortor felis, pulvinar "
            + "in scelerisque cursus, pulvinar at ante. Nulla consequat"
            + "congue lectus in sodales. Nullam eu est a felis ornare "
            + "bibendum et nec tellus. Vivamus non metus tempus augue auctor "
            + "ornare. Duis pulvinar justo ac purus adipiscing pulvinar. "
            + "Integer congue faucibus dapibus. Integer id nisl ut elit "
            + "aliquam sagittis gravida eu dolor. Etiam sit amet ipsum "
            + "sem.";
 
    @Override
    public void start(Stage stage) {
        stage.setTitle("HTMLEditor Sample");
        stage.setWidth(500);
        stage.setHeight(500);
        Scene scene = new Scene(new Group());
    
        VBox root = new VBox();     
        root.setPadding(new Insets(8, 8, 8, 8));
        root.setSpacing(5);
        root.setAlignment(Pos.BOTTOM_LEFT);
 
        final HTMLEditor htmlEditor = new HTMLEditor();
        htmlEditor.setPrefHeight(245);
        htmlEditor.setHtmlText(INITIAL_TEXT);
        
        final WebView browser = new WebView();
        final WebEngine webEngine = browser.getEngine();
     
        ScrollPane scrollPane = new ScrollPane();
        scrollPane.getStyleClass().add("noborder-scroll-pane");
        scrollPane.setStyle("-fx-background-color: white");
        scrollPane.setContent(browser);
        scrollPane.setFitToWidth(true);
        scrollPane.setPrefHeight(180);
 
        Button showHTMLButton = new Button("Load Content in Browser");
        root.setAlignment(Pos.CENTER);
        showHTMLButton.setOnAction(new EventHandler<ActionEvent>() {
            @Override public void handle(ActionEvent arg0) {                
                webEngine.loadContent(htmlEditor.getHtmlText());
            }
        });
        
        root.getChildren().addAll(htmlEditor, showHTMLButton, scrollPane);
        scene.setRoot(root);
 
        stage.setScene(scene);
        stage.show();
    }
 
    public static void main(String[] args) {
        launch(args);
    }
}

HTML code received from the htmlEditor component is loaded in the WebEngine object that specifies the content for the embedded browser. Each time a user clicks the Load Content in Browser button, the edited content is updated in the browser. Figure 19-7 demonstrates Example 19-6 in action.

Figure 19-7 Loading Content in a Browser

Description of Figure 19-7 follows
Description of "Figure 19-7 Loading Content in a Browser"

You can use the Text component to add non-editing text content to your UI. See Using Text and Text Effects in JavaFX for more information about the Text component.

Related API Documentation 

Previous
Next