Javafx 什么';对于文本区域来说,它是一个很好的可观察的可附加基础?

Javafx 什么';对于文本区域来说,它是一个很好的可观察的可附加基础?,javafx,Javafx,我有一个StringBuffer,偶尔会附加新信息 在一个单独的模块中,我有一个JavaFXTextArea,它显示StringBuffer 现在,每次修改基础数据时,我都必须手动更新TextArea 是否有类似于observeList(我用于TableView)的东西可以用作TextArea的后端数据,这样我就不必手动管理将更改推送到显示器上了 我不喜欢使用StringBuffer。我很乐意使用任何可附加的数据结构来保存文本

我有一个
StringBuffer
,偶尔会附加新信息

在一个单独的模块中,我有一个JavaFX
TextArea
,它显示
StringBuffer

现在,每次修改基础数据时,我都必须手动更新
TextArea

是否有类似于
observeList
(我用于TableView)的东西可以用作
TextArea
的后端数据,这样我就不必手动管理将更改推送到显示器上了


我不喜欢使用
StringBuffer
。我很乐意使用任何可附加的数据结构来保存文本
import javafx.beans.binding.StringBinding;

public class ObservableStringBuffer extends StringBinding {

    private final StringBuffer buffer = new StringBuffer() ;

    @Override
    protected String computeValue() {
        return buffer.toString();
    }


    public void set(String content) {
        buffer.replace(0, buffer.length(), content);
        invalidate();
    }

    public void append(String text) {
        buffer.append(text);
        invalidate();
    }

    // wrap other StringBuffer methods as needed...

}
这使绑定到文本区域的编码变得容易。你可以简单地做

TextArea textArea = new TextArea();
ObservableStringBuffer buffer = new ObservableStringBuffer();
textArea.textProperty().bind(buffer);

// ...

buffer.append("Hello world");
但是,这里需要注意的是,您没有将缓冲区API的效率转移到文本区域:文本区域只是有一个表示其文本的
textProperty()
,它仍然只能通过
set(…)
setValue(…)
进行修改。换句话说,当你附加到缓冲区时,你基本上会得到
textArea.setText(textArea.getText()+“Hello world”)
(而不是
textArea.appendText(“Hello world”)
。如果你只是在寻找一个干净的API,那么这对你来说应该是可行的;如果你在寻找高效的东西,你必须“连线”调用
appendText
您自己,因为文本区域的
textProperty()
根本不支持这种调用

以下是使用上述类的SSCCE:

import javafx.animation.Animation;
import javafx.animation.KeyFrame;
import javafx.animation.Timeline;
import javafx.application.Application;
import javafx.scene.Scene;
import javafx.scene.control.TextArea;
import javafx.scene.layout.StackPane;
import javafx.stage.Stage;
import javafx.util.Duration;

public class ObservableStringBufferTest extends Application {

    private int counter ;

    @Override
    public void start(Stage primaryStage) {
        ObservableStringBuffer buffer = new ObservableStringBuffer();

        TextArea textArea = new TextArea();
        textArea.setEditable(false);
        textArea.textProperty().bind(buffer);

        buffer.set("Item 0");

        Timeline timeline = new Timeline(new KeyFrame(
                Duration.seconds(1), 
                e -> buffer.append("\nItem "+(++counter))));

        timeline.setCycleCount(Animation.INDEFINITE);
        timeline.play();

        primaryStage.setScene(new Scene(new StackPane(textArea)));
        primaryStage.show();
    }

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