Пример Vaadin @DebouceSettings

Я пытаюсь закодировать TexField, который запускает событие (поиск) при каждом нажатии клавиши.

Но у события должна быть опция противодействия, чтобы оно срабатывало только через заданное время без нажатия клавиши.

Я следую этому документу: https://vaadin.com/docs/v13/flow/creating-components/tutorial-component-events.html

Но мне сложно понять, как добавить @DebouceEvent к моему TextField ...

Событие:

@DomEvent(value = "input",
          debounce = @DebounceSettings(
              timeout = 250,
              phases = DebouncePhase.TRAILING))
public class InputEvent extends ComponentEvent<TextField> {
    private String value;

    public InputEvent(TextField source, boolean fromClient,
            @EventData("element.value") String value) {
        super(source, fromClient);
        this.value = value;
    }

    public String getValue() {
        return value;
    }
}

Текстовое поле:

 TextField searchField= new TextField("my search");

Я пытался:

searchField.addInputListener(new InputEvent(searchField, true, "input"));

ошибка:

Error:(41, 38) java: incompatible types: nc.unc.importparcoursup.view.AdmisDetailView.InputEvent cannot be converted to com.vaadin.flow.component.ComponentEventListener<com.vaadin.flow.component.InputEvent>

person Tyvain    schedule 06.08.2019    source источник


Ответы (2)


С этой строкой есть две проблемы

searchField.addInputListener(new InputEvent(searchField, true, "input"));
  1. addInputListener не для вашего мероприятия, просто он назван так же
  2. Аргументом должен быть слушатель, а не событие.

Решение

Чтобы добавить собственное событие, вам необходимо расширить класс TextField (или создать собственное текстовое поле, расширяющее Component).

Я называю свое поле SearchField

public class SearchField extends TextField {

    public SearchField(String caption) {
        super(caption);
    }
}

Затем мы можем создать класс события. Я изменил имя на SearchEvent, чтобы избежать путаницы. Я также увеличил задержку, чтобы было легче проверить, работает ли она. Наконец, здесь он расширяет ComponentEvent<TextField>, но может также расширять ComponentEvent<SearchField>.

@DomEvent(value = "input",
        debounce = @DebounceSettings(
                timeout = 1000,
                phases = DebouncePhase.TRAILING))
public class SearchEvent extends ComponentEvent<TextField> {
    private String value;

    public SearchEvent(TextField source, boolean fromClient,
                       @EventData("element.value") String value) {
        super(source, fromClient);
        this.value = value;
    }

    public String getValue() {
        return value;
    }
}

Теперь мы можем создать метод для добавления слушателя этого типа события в SearchField class.

public class SearchField extends TextField {

    ...

    public Registration addSearchListener(ComponentEventListener<SearchEvent> listener) {
        return addListener(SearchEvent.class, listener);
    }
}

И, наконец, мы можем попробовать это

@Route
public class SearchView extends VerticalLayout {

    public SearchView() {
        SearchField searchField = new SearchField("Search");
        searchField.addSearchListener(event -> {
            Notification.show("You searched for [" + event.getValue() + "]");
        });
        add(searchField);
    }
}

Примечание

В Vaadin 14, который в настоящее время находится на стадии предварительного выпуска и который должен быть выпущен в ближайшее время, вы можете просто сделать

TextField textField = new TextField();
textField.setValueChangeMode(ValueChangeMode.LAZY);
person Erik Lumme    schedule 06.08.2019

Я думаю, что вы добавляете ненужную сложность в свой подход. TextField имеет методы setValueChangeMode и setValueChangeTimeOut, которые можно использовать для настройки TextField, чтобы он вел себя так, как вы пытаетесь. См. https://vaadin.com/api/platform/14.0.0.rc7/com/vaadin/flow/component/textfield/TextField.html#setValueChangeTimeout-int-

person Tatu Lund    schedule 06.08.2019
comment
Обратите внимание, что ValueChangeMode.LAZY и setValueChangeTimeOut - это новые функции в Vaadin 14, которые в настоящее время доступны только в качестве предварительной версии. В версиях 10-13 вам придется либо использовать подход, описанный @Tazavoo, либо использовать общий низкоуровневый метод addEventListener на searchField.getElement(). - person Leif Åstrand; 06.08.2019