1 Вопрос: Обновление компонента из слушателя событий Vaadin

вопрос создан в Thu, May 2, 2019 12:00 AM

Мне интересно, как я могу обновить компонент в Vaadin при изменении данных из прослушивателя событий. Рассматриваемый код выглядит следующим образом:

Set<Long> identifiers = new LinkedHashSet<>();

Grid<Long> grid = new Grid<>(Long.class);
grid.addColumn((ValueProvider<Long, Long>) value -> value);
grid.setDataProvider(new ListDataProvider<>(identifiers));

TextField identifier = new TextField();
identifier.getElement().addEventListener("keyup", event -> {
  String value = event.getEventData().getString("element.value");
  if (value != null && value.length() > 0) {
    try {
      identifiers.add(Long.parseLong(value));
      identifier.clear();
    } catch (NumberFormatException e) {
      Notification.show("Not a valid identifier: " + value);
    }
  }
}).addEventData("element.value").setFilter("event.key == 'Enter'");

Событие отправляется так, как я ожидал, но сетка не отображается в пользовательском представлении. Как мне сообщить Ваадину, что сетка нуждается в повторной визуализации из обработчика событий?

    
3
1 ответ                              1                         

Повторная визуализация сетки выполняется путем обновления DataProvider. Вы можете сделать это так:

grid.getDataProvider().refreshAll();

Изменить. Мое объяснение основывалось на неверных предположениях

ListDataProvider не копирует предоставленную ему коллекцию, поэтому изменение исходной коллекции элементов повлияет на поставщика данных. Но он не рендерится автоматически, вам все равно придется звонить refreshAll().

refreshAll() будет в основном повторять элементы поставщиков данных, перестраивать строки и повторно применять любые пользовательские определения столбцов (т. е. styleGenerators и другие решения на основе состояния). До тех пор, пока вы сохраняете оригинальную коллекцию в актуальном состоянии с тем, что хотите показать, вызов refreshAll() должен работать.

Если вы хотите полностью изменить отображаемый список элементов, вы можете либо удалить все элементы из исходной коллекции (identifiers) и добавить в нее новые элементы, затем обновить все, либо вы можете просто установить новый поставщик данных с новая коллекция предметов.
(Эта строка также решит проблему OP, но ее следует избегать, если достаточно refreshAll.)

grid.setDataProvider(new ListDataProvider<>(otherIdentifiers));
    
3
2019-05-03 07: 28: 57Z
  1. На самом деле, когда я писал это, я не был уверен, будет ли работать refreshAll() в конце концов, даже показывая только что добавленный элемент. Может ли кто-нибудь любезно подтвердить это утверждение для меня?
    2019-05-02 15: 59: 00Z
  2. Я только что проверил это, и вы совершенно правы. Спасибо за вашу помощь!
    2019-05-02 16: 52: 51Z
  3. Да, refreshAll() должен работать. ListDataProvider не копирует предоставленную ему коллекцию, но использует ту же ссылку на объект. Поэтому при редактировании исходной ссылки редактируется базовая коллекция в ListDataProvider.
    2019-05-03 05: 15: 47Z
  4. ListDataProvider does not copy the collection supplied to it, but uses the same object reference. So editing the original reference edits the underlying collection in the ListDataProviderно это не значит, что последняя часть принятого ответа неверна? Если ListDataProvider не работает с копией списка, но с той же ссылкой, вам не нужно переустанавливать DataProvider при добавлении /удалении элементов, верно?
    2019-05-03 05: 19: 11Z
  5. @ codinghaus Моя последняя часть ответа прямо противоречит этому утверждению. Переустановка поставщика данных потребуется только в том случае, если поставщик данных работал с копией списка элементов, что, очевидно, не так. звонить по номеру refreshAll() достаточно для ОП. Я отредактирую свой ответ в ближайшее время, чтобы отразить это.
    2019-05-03 07: 12: 48Z
источник размещен Вот