2
import javafx.application.Application;
import javafx.geometry.Insets;
import javafx.geometry.Pos;
import javafx.scene.Scene;
import javafx.scene.control.Label;
import javafx.scene.control.OverrunStyle;
import javafx.scene.control.PasswordField;
import javafx.scene.control.TextField;
import javafx.scene.control.Tooltip;
import javafx.scene.layout.GridPane;
import javafx.stage.Stage;

public class BindTooltipToFocusEvent extends Application {
  @Override
  public void start(Stage stage) throws Exception {
    stage.setTitle("How to bind tooltip to focus event?");
    GridPane grid = new GridPane();
    grid.setAlignment(Pos.CENTER);
    grid.setHgap(10);
    grid.setVgap(5);
    grid.setPadding(new Insets(25, 25, 25, 25));
    grid.add(new Label("Email"), 0, 0);
    grid.add(new TextField(), 0, 1);
    grid.add(new Label("Password"), 0, 2);

    Tooltip tooltip = new Tooltip("Paswords must contain 1-50 characters, etc...");
    tooltip.setWrapText(true);
    tooltip.setTextOverrun(OverrunStyle.ELLIPSIS);
    PasswordField pf = new PasswordField();
    pf.setPromptText("Password");
    pf.setTooltip(tooltip);
    grid.add(pf, 0, 3);

    stage.setScene(new Scene(grid, 300, 275));
    stage.sizeToScene();
    stage.show();
  }
  public static void main(String[] args) { launch(); }
}

运行提供的示例应用程序演示了 Java FX 中的默认工具提示行为,以在鼠标悬停事件上显示工具提示。在密码字段上悬停一两秒将导致显示工具提示。我宁愿在用户输入密码时显示工具提示,而不是在他们(可能)用鼠标悬停在字段上时。

如何更改此行为,以便在密码字段具有焦点时显示工具提示?

我知道可以向用户界面添加另一个标签,并根据密码字段何时获得焦点来修改其可见性属性。这个问题不是要求解决示例用例的方法。我想具体了解如何在父字段具有焦点时使工具提示可见。

4

1 回答 1

6

为此,您应该管理工具提示的可见性并定位自己:

@Override
public void start(Stage stage) throws Exception {
    stage.setTitle("How to bind tooltip to focus event?");
    GridPane grid = new GridPane();
    grid.setAlignment(Pos.CENTER);
    grid.setHgap(10);
    grid.setVgap(5);
    grid.setPadding(new Insets(25, 25, 25, 25));
    grid.add(new Label("Email"), 0, 0);
    grid.add(new TextField(), 0, 1);
    grid.add(new Label("Password"), 0, 2);

    final Tooltip tooltip = new Tooltip("Paswords must contain 1-50 characters, etc...");
    tooltip.setWrapText(true);
    tooltip.setTextOverrun(OverrunStyle.ELLIPSIS);
    final PasswordField pf = new PasswordField();
    pf.setPromptText("Password");
    //pf.setTooltip(tooltip);
    pf.focusedProperty().addListener(new ChangeListener<Boolean>() {
        @Override
        public void changed(ObservableValue<? extends Boolean> observable, Boolean oldValue, Boolean newValue) {
            if (newValue) {
                tooltip.show(pf, //
                        // popup tooltip on the right, you can adjust these values for different positions
                        pf.getScene().getWindow().getX() + pf.getLayoutX() + pf.getWidth() + 10, //
                        pf.getScene().getWindow().getY() + pf.getLayoutY() + pf.getHeight());
            } else {
                tooltip.hide();
            }
        }
    });
    grid.add(pf, 0, 3);

    stage.setScene(new Scene(grid, 300, 275));
    stage.sizeToScene();
    stage.show();
}

这种方法的一个缺点是即使将窗口移动/拖动到不同的位置,工具提示也会保留在屏幕上。

于 2013-08-13T20:45:22.440 回答