5.5.2.1.22. LookupField

Компонент для выбора значения из выпадающего списка. Выпадающий список реализует фильтрацию значений по мере ввода пользователя и постраничный вывод доступных значений.

gui lookupField

XML-имя компонента: lookupField.

Компонент LookupField реализован для блоков Web Client и Desktop Client.

  • Простейший вариант использования LookupField - выбор значения перечисления (enum) для атрибута сущности. Например, сущность Role имеет атрибут type типа RoleType, который является перечислением. Тогда для редактирования этого атрибута можно использовать LookupField следующим образом:

    <dsContext>
        <datasource id="roleDs" class="com.haulmont.cuba.security.entity.Role" view="_local"/>
    </dsContext>
    <layout>
        <lookupField datasource="roleDs" property="type"/>

    Как видно из примера, в экране описывается источник данных roleDs для сущности Role. В компоненте lookupField в атрибуте datasource указывается ссылка на источник данных, а в атрибуте property − название атрибута сущности, значение которого должно быть отображено. В данном случае атрибут является перечислением, и в выпадающем списке будут отображены локализованные названия всех значений этого перечисления.

  • Аналогично можно использовать LookupField для выбора экземпляра связанной сущности. Для формирования списка опций используется атрибут optionsDatasource:

    <dsContext>
        <datasource id="carDs" class="com.company.sample.entity.Car" view="_local"/>
        <collectionDatasource id="coloursDs" class="com.company.sample.entity.Colour" view="_local">
            <query>select c from sample$Colour c</query>
        </collectionDatasource>
    </dsContext>
    <layout>
        <lookupField datasource="carDs" property="colour" optionsDatasource="coloursDs"/>

    В данном случае компонент отобразит отобразит имена экземпляров сущности Colour, находящихся в источнике данных colorsDs, а выбранное значение подставится в атрибут colour сущности Car, находящейся в источнике данных carDs.

    С помощью атрибута captionProperty можно указать, какой атрибут сущности использовать вместо имени экземпляра для строковых названий опций.

  • Список опций компонента может быть задан произвольно с помощью методов setOptionsList(), setOptionsMap() и setOptionsEnum(), либо с помощью XML-атрибута optionsDatasource.

  • Метод setOptionsList() позволяет программно задать список опций компонента. Для этого объявляем компонент в XML-дескрипторе:

    <lookupField id="numberOfSeatsField" datasource="modelDs" property="numberOfSeats"/>

    Затем инжектируем компонент в контроллер и в методе init() задаем ему список опций:

    @Inject
    protected LookupField numberOfSeatsField;
    
    @Override
    public void init(Map<String, Object> params) {
        List<Integer> list = new ArrayList<>();
        list.add(2);
        list.add(4);
        list.add(5);
        list.add(7);
        numberOfSeatsField.setOptionsList(list);
    }

    В выпадающем списке компонента отобразятся числа 2, 4, 5, 7. Выбранное число подставится в атрибут numberOfSeats сущности, находящейся в источнике данных modelDs.

  • Метод setOptionsMap() позволяет задать строковые названия и значения опций по отдельности. Например, для описанного в XML-дескрипторе компонента numberOfSeatsField в методе init() контроллера задаем мэп опций:

    @Inject
    protected LookupField numberOfSeatsField;
    
    @Override
    public void init(Map<String, Object> params) {
        Map<String, Object> map = new LinkedHashMap<>();
        map.put("two", 2);
        map.put("four", 4);
        map.put("five", 5);
        map.put("seven", 7);
        numberOfSeatsField.setOptionsMap(map);
    }

    В выпадающем списке компонента отобразятся строки two, four, five, seven. Однако значением компонента будет число, соответствующее выбранной строке. Оно и подставится в атрибут numberOfSeats сущности, находящейся в источнике данных modelDs.

  • setOptionsEnum() принимает в качестве параметра класс перечисления. Выпадающий список будет содержать локализованные названия значений перечисления, значением компонента будет являться выбранное значение перечисления.

  • Каждый элемент выпадающего списка может иметь значок слева. Создайте реализацию интерфейса LookupField.OptionIconProvider в контроллере экрана и установите ее для компонента lookupField:

    lookupField.setOptionIconProvider(new LookupField.OptionIconProvider<Customer>(){
        @Override
        public String getItemIcon(Customer c){
            if(c.getType()== LegalStatus.LEGAL)
                return"icons/icon-office.png";
            return"icons/icon-user.png";
        }
    });
    gui lookupField 2
  • С помощью атрибута filterMode можно задать тип фильтрации опций при вводе пользователя:

    • NO − нет фильтрации.

    • STARTS_WITH − по началу фразы.

    • CONTAINS − по любому вхождению (используется по умолчанию).

  • Если у компонента LookupField не установлен атрибут required, и если связанный атрибут сущности не объявлен как обязательный, то в списке опций компонента присутствует пустая строка, при выборе которой компонент возвращает значение null. Атрибут nullName позволяет задать строку, отображаемую в этом случае вместо пустой. Пример использования:

    <lookupField datasource="carDs" property="colour" optionsDatasource="coloursDs" nullName="(none)"/>

    В данном случае вместо пустой строки отобразится строка (none), при выборе которой в связанный атрибут сущности подставится значение null.

    При программном задании списка опций методом setOptionsList() можно одну из опций передать в метод setNullOption(). Тогда при ее выборе пользователем значением компонента будет null.

  • Компонент LookupField способен обрабатывать ввод пользователя при отсутствии подходящей опции в списке. Для этого используются методы setNewOptionAllowed() и setNewOptionHandler(). Например:

    @Inject
    protected LookupField colourField;
    
    @Inject
    protected CollectionDatasource<Colour, UUID> coloursDs;
    
    @Override
    public void init(Map<String, Object> params) {
        colourField.setNewOptionAllowed(true);
        colourField.setNewOptionHandler(new LookupField.NewOptionHandler() {
            @Override
            public void addNewOption(String caption) {
                Colour colour = new Colour();
                colour.setName(caption);
                coloursDs.addItem(colour);
                colourField.setValue(colour);
            }
        });
    }

    Обработчик NewOptionHandler вызывается, если пользователь ввел некоторое значение, не совпадающее ни с одной из опций, и нажал Enter. В данном случае в обработчике создается новый экземпляр сущности Colour, его атрибут name устанавливается в значение, введенное пользователем, этот экземпляр добавляется в источник данных опций и выбирается в компоненте.

    Вместо имплементации интерфейса LookupField.NewOptionHandler для обработки ввода пользователя можно использовать XML-атрибут newOptionHandler с указанным в нем методом контроллера. Данный метод должен иметь два параметра - первый типа LookupField, второй типа String. В них будут переданы соответственно экзампляр компонента и введенное пользователем значение. Атрибут newOptionAllowed используется вместо метода setNewOptionAllowed() для того, чтобы разрешить добавление новых опций.

  • XML-атрибут nullOptionVisible устанавливает видимость элемента со значением null в списке опций. Может работать только если атрибут required имеет значение false.

  • XML-атрибут textInputAllowed используется для отключения возможности фильтрации опций с клавиатуры. Это бывает удобно для коротких списков. Значение по умолчанию - true.

  • XML-атрибут pageLength позволяет переопределить количество опций на одной странице выпадающего списка, заданное свойством приложения cuba.gui.lookupFieldPageLength.

  • В веб-клиенте с темой, основанной на Halo, к компоненту LookupField можно применить предопределенные стили. Стили задаются в XML-дексрипторе или контроллере экрана с помощью атрибута stylename:

    <lookupField id="lookupField"
                 stylename="borderless"/>

    Чтобы применить стиль программно, выберите одну из констант класса HaloTheme с префиксом компонента LOOKUPFIELD_:

    lookupField.setStyleName(HaloTheme.LOOKUPFIELD_BORDERLESS);

    Стили компонента LookupField:

    • align-center - align the text inside the field to center.

    • align-right - align the text inside the field to the right.

    • borderless - removes the border and background from the text field.