7

Is there anyway to make a Label text selectable in JavaFx8? I know, there are other simple workaround like using a TextField. But my label needs multiline text with wrapping facility which TextField does not provide. If I use TextArea, the problem is I can't shrink the TextArea based on the text's size like a Label. So I can't use either of them.

Also my use of label text is like below:

<VBox>
    <Label wrapText="true"
           VBox.vgrow="ALWAYS"
           maxHeight="Infinity" minHeight="-Infinity"
           text="Some Random Subject Line With Very Large Text To Test The Wrap Text, Lorem Ipsum Dolor"/>                       
</VBox>

Depending on the VBox width, Label's height resizes to fit the text fully. I can't emulate this kind of behaviour using either TextArea or TextField. But I need to be able to select the text from Label. Any ideas?

Anindya Chatterjee
  • 5,824
  • 13
  • 58
  • 82
  • I don't think that it's possible, or at least that's what [this](https://community.oracle.com/thread/2319231) thread of oracle suggests.Looks like it's a feature requested to be implemented in the future releases. – dumbPotato21 May 25 '17 at 06:41
  • So any open source custom control made by anyone? – Anindya Chatterjee May 25 '17 at 07:02
  • Try this: https://stackoverflow.com/questions/22534067/copiable-label-textfield-labeledtext-in-javafx –  May 25 '17 at 07:30
  • @Developer66 already mentioned in my question, this trick does not work for me as TextField does not support multi line wrapped text. Neither it resizes itself depending on the text length like label does. – Anindya Chatterjee May 25 '17 at 07:40
  • Maybe do the same thing with a `TextArea` instead of a `TextField`? What can't you emulate, exactly, doing that? What did you try? – James_D May 25 '17 at 12:08
  • I can't auto resize TextArea like a label. When the VBox is resized, TextArea is not growing to show the full text. – Anindya Chatterjee May 25 '17 at 13:33
  • 1
    Surely that is just configurable using layout settings from the parent VBox? – James_D May 25 '17 at 13:50

1 Answers1

9

Here is a workaround until someone post something better.

If you double click the label it changes to a TextArea. You can then copy the text. Once you press enter on the TextArea it changes back to the label.

import javafx.application.Application;
import javafx.event.ActionEvent;
import javafx.event.EventHandler;
import javafx.scene.Scene;
import javafx.scene.control.Button;
import javafx.scene.control.Label;
import javafx.scene.control.TextArea;
import javafx.scene.input.MouseButton;
import javafx.scene.input.MouseEvent;
import javafx.scene.layout.Priority;
import javafx.scene.layout.StackPane;
import javafx.scene.layout.VBox;
import javafx.stage.Stage;

/**
 *
 * @author blj0011
 */
public class JavaFXApplication110 extends Application
{

    @Override
    public void start(Stage primaryStage)
    {
        VBox root = new VBox();

        StackPane stackpane = new StackPane();        

        Label label = new Label("Hello world Hello world Hello world Hello world Hello world Hello world Hello world Hello world Hello world");
        VBox.setVgrow(label, Priority.ALWAYS);
        label.wrapTextProperty().set(true);

        label.setOnMouseClicked(new EventHandler<MouseEvent>() {
            @Override
            public void handle(MouseEvent mouseEvent) {
                if(mouseEvent.getButton().equals(MouseButton.PRIMARY)){
                    if(mouseEvent.getClickCount() == 2){
                        label.setVisible(false);
                        TextArea textarea = new TextArea(label.getText());
                        textarea.setPrefHeight(label.getHeight() + 10);
                        stackpane.getChildren().add(textarea);

                        textarea.setOnKeyPressed(event ->{
                            System.out.println(event.getCode());
                            if(event.getCode().toString().equals("ENTER"))
                            {
                                stackpane.getChildren().remove(textarea);
                                label.setVisible(true);                               
                            }
                        });
                    }
                }
            }
        });

        stackpane.getChildren().add(label);   

        root.getChildren().add(stackpane);

        Scene scene = new Scene(root, 300, 250);

        primaryStage.setTitle("Hello World!");
        primaryStage.setScene(scene);
        primaryStage.show();
    }

    /**
     * @param args the command line arguments
     */
    public static void main(String[] args)
    {
        launch(args);
    }

}
SedJ601
  • 12,173
  • 3
  • 41
  • 59