How To Create AutoComplete ComboBox Or TextField In Java FX 2

Well, since there is no built-in class that does this functionality, the only solution was to create my own. Here is my version of an auto-complete class that can be used for a TextField or editable ComboBox.

If you want to use this for a TextField node, just change parts of the code to cater to it. It should not be hard.

To use this class, just do

Easy, right?

This class also includes an added feature wherein after you type something in the editable ComboBox and when you press the ENTER key, an action will take place: say, you want to save it to the database or something.

Note: the focus listener is now added to the ComboBox’s TextField component because in the development environment, it works fine. However, when deployed as an Applet, it does not work. Only when I shifted the focus listener to the ComboBox’s editor did it work correctly.

Related Posts Plugin for WordPress, Blogger...

23 comments

  1. This worked. Of all things I have found, this works. The only issue(I am certain it is my code) is that when I try to comboBox.getValue(), it does not seem to load the value.

    But everything else, filter/autocomplete, amazing!

    Thankyou, thankyou, thankyou.

  2. I add a filled observablelist to the combobox, then apply your java file.
    The list populates fine. But when I try to load the combobox’s value into a method as the T object of the observablelist, then use a method on that object, (i.e. getName()), it declares a null pointer.

  3. Is it poosible that the ComboBox’s text is being set, but the value is not being set. I’m not as familiar with Java, especially comboboxes, as you are. Is that possible?

  4. @nicholas: lol, im very lazy checking out someone else’s code. but your problem may be that just because you type something in the editable combobox does not mean that your custom object is linked to it.

    the editable combobox will always return a String. what you can do is when you call getValue() check if it is an instanceof String then do a lookup in your list and return that Object.

    if the combobox is clicked and the list is shown in the combobox popup, once you select an item, it will return that custom object.

  5. class for use =)

    package ejemplo;

    import javafx.application.Application;
    import javafx.collections.FXCollections;
    import javafx.collections.ObservableList;
    import javafx.event.ActionEvent;
    import javafx.event.EventHandler;
    import javafx.scene.Group;
    import javafx.scene.Scene;
    import javafx.scene.control.ComboBox;
    import javafx.stage.Stage;

    public class JavaFx extends Application {
    ComboBox combobox;
    AutoCompleteComboBoxListener aux;
    ObservableList data = FXCollections.observableArrayList(
    “Todos”,
    “alegria”,
    “chilevision”,
    “america”,
    “ana”,
    “chileno”,
    “BCX”
    );

    public static void main(String[] args) {
    //Esto se utiliza para ejecutar la aplicación
    //es como el new Contructor();
    launch(args);
    }

    //Este metodo es obligatorio
    @Override
    public void start( Stage primaryStage ){
    Group root = new Group();
    //El grupo que se desea agregar, y el tamaño ancho y alto
    Scene scene = new Scene( root, 300, 300 );
    //Titulo de la ventana
    primaryStage.setTitle(“JavaFx”);
    //Se agrega la scena
    primaryStage.setScene( scene );

    //Creacion del boton
    combobox = new ComboBox();

    combobox.setLayoutX(105);
    combobox.setLayoutY(110);
    combobox.setItems(data);
    aux = new AutoCompleteComboBoxListener(combobox);
    combobox.setOnAction(actionButton);
    root.getChildren().add(combobox);

    //Para mostrar la visible, semejante al setVisible(true)
    primaryStage.show();
    }

    private final EventHandler actionButton = new EventHandler() {
    @Override
    public void handle(final ActionEvent t) {
    System.out.println(“Accion del combobox ” +combobox.getSelectionModel().selectedItemProperty().getValue());
    // Stage stage = (Stage) boton.getScene().getWindow();
    // stage.close();
    }
    };

    }

  6. Hi, not working in JavaFX 8. Error here:

    KeyEvent ke = KeyEvent.impl_keyEvent(comboBox, KeyCode.ENTER.toString(), KeyCode.ENTER.getName(), KeyCode.ENTER.impl_getCode(), false, false, false, false, KeyEvent.KEY_RELEASED);

    1. if (!inFocus && comboBox.getEditor().getText() != null && comboBox.getEditor().getText().trim().length() > 0) {
      // press enter key programmatically to have this entry added

      Robot robot = com.sun.glass.ui.Application.GetApplication().createRobot();
      robot.keyPress(java.awt.event.KeyEvent.VK_ENTER);
      KeyCode.ENTER.getName(), KeyCode.ENTER.impl_getCode(), false, false, false, false, KeyEvent.KEY_RELEASED);
      }

      1. Edit:
        if (!inFocus && comboBox.getEditor().getText() != null && comboBox.getEditor().getText().trim().length() > 0) {
        // press enter key programmatically to have this entry added

        Robot robot = com.sun.glass.ui.Application.GetApplication().createRobot();
        robot.keyPress(java.awt.event.KeyEvent.VK_ENTER);
        }

  7. hello sorry cant help you with just that. is there an error? or it wont compile

    i have not tried java fx 8 though so cant help you

    1. @padre.cedano:
      1) you do not need Java FX to load data from database to ComboBox. You need Java for that.
      2) what do you mean by show only a column? You probably need to use a Table.
      3) To fill the ComboBox, combobox.setItems(ObservableList);

  8. @blogmeister
    Thanks for your response.

    I need populate combobox with object as:
    private final ObservableList data =
    FXCollections.observableArrayList(
    new Couple(1,”Name1″),
    new Couple(2,”Name2″),
    new Couple(3,”Name3″));

    When i says “show only a column” i says that i only need show in combobox the second column: Name1, Name2…

    After i need to add an event to combobox for get the first column of selected item Couple: 1,2,3

    I can get this value if the user choose one value into the combobox but, in editable combobox i have error NPE if the user write a new value. I read in some forums that the solution is to apply a string converter to editable combo box, but this not works for me.

    1. @padre if you can wait tomorrow ill post my code so you wont get that NPE

      to show the name of the Couple in the combobox just override toString() in your Couple class.

      e.g.
      class Couple { … public String toString() { return name; } }

  9. hi @padre, im not really sure what you mean without seeing a running sample code.

    i also dont get why you get an NPE. make sure from the editable combobox you do not use the combobox item because the value returned is always a String. you only get a combobox value if you click on the dropdown arrow and swlect an item.

    What i did was to check if the value returned is an instance of String or not. if it is, i search the list of Couple to see if there is a matching name, then return it. If there is no match, return null. make sure to add an If statement because maybe the combobox did not return anything.

  10. If you happen to enter the ComboBox by pressing Shift+Tab, the first item in the array is auto-completed. To avoid this add the following code after the line “ObservableList items = comboBox.getItems();”

    if ((comboBox.getEditor().getText().length())>0){

    …(and close the brace after “comboBox.getEditor().selectEnd();
    break;”

  11. Thank you,

    This is a great simple and efficient autocomplete combobox.
    I am looking for an autocomplete combobox which does more than that and surprise !
    I found it in the link above : how-to-go-to-item-in-combobox-on-keypress-in-java-fx-2
    this works great also !

    I would like to mix your two listener:
    AutoCompleteComboBoxListener and SelectKeyComboBoxListener.
    to have both behaviours.

    So when you type the first letter of a word, it finds and displays complement in button cell but also select the first match in the list.

    What happens now is that the first matching word is selected in the listView, the first matching word is displayed in button cell but unfortunately, the caret position is reset at the beginning of the word and no characters are selected.

    Example, i type “J”, and he will Display “|Jack” with cursor before the “J”.
    It means that if I click quickly “Ja” he will display “|aJack”.

    But again thank you, I think it is a good base to find a solution.

  12. added a function for it to be compatible text with accents. Just added a new feature:
    public static String unAccent(String s) {
    String temp = Normalizer.normalize(s, Normalizer.Form.NFD);
    Pattern pattern = Pattern.compile(“\\p{InCombiningDiacriticalMarks}+”);
    return pattern.matcher(temp).replaceAll(“”);
    }

    and used it in handle Override, the segunte way:

    for (Object data1 : this.data) {
    // if (!data1.toString().toLowerCase().contains(comboBox.getEditor().getText().toLowerCase())) continue;
    // list.add(data1);
    if(unAccent(data1.toString().toLowerCase()).contains(unAccent(comboBox.getEditor().getText().toLowerCase())))
    list.add(data1);
    }

    I hope to have contributed to the AutoCompleteComboBox. xD

Leave a Reply

Your email address will not be published. Required fields are marked *