Table with generated SuggestionPickerField is using same value over and over

Hello all:

Running on v7.1.5 right now. I have a generated cell in a table where I create a SuggestionPickerField. I expect that each row’s generated cell would be a unique field connected to the corresponding value for the entity in the table, but somehow they are all connected together and pulling the same data item.

My table looks like this:

        <table id="pinTable" dataContainer="updtransDc" width="100%" editable="true">
          <actions>
            <action id="create" shortcut="CTRL-ARROW_DOWN"/>
            <action id="save"/>
            <action id="remove"/>
          </actions>
          <columns>
            <column id="mailfile" editable="true" generator="generateMailfileCell"/>
            <column id="amount" editable="true"/>
            <column id="name" editable="false"/>
            <column id="address2" editable="false"/>
            <column id="city" editable="false"/>
            <column id="province" caption="State" editable="false"/>
            <column id="postalcode" caption="ZIP" editable="false"/>
            <column id="source.sourcecode" caption="Keycode" editable="false"/>
            <column id="source.mlg.mlgcode" caption="Mlg Code" editable="false"/>
            <column id="source.mlg.offer.offercode" caption="Offer" editable="false"/>
            <column id="source.lst.listname" caption="List" editable="false"/>
          </columns>
          <buttonsPanel>
            <button id="btnAddPin" action="pinTable.create" caption="Create Response"
              icon="icons/create.png"/>
            <button id="btnSavePin" action="pinTable.save" caption="Save Responses"
              icon="icons/save.png"/>
            <button id="btnRemovePin" action="pinTable.remove" caption="Delete Response"
              icon="icons/remove.png"/>
          </buttonsPanel>
        </table>

My generateMailfileCell code looks like this:

    public Component generateMailfileCell(Updtrans updtrans) {

        SuggestionPickerField<Mailfile> picker = uiComponents.create(SuggestionPickerField.of(Mailfile.class));
        picker.setValueSource(new ContainerValueSource<>(updtransDc,"mailfile"));
        picker.setSearchExecutor((searchString, searchParams) -> {
            searchString = QueryUtils.escapeForLike(searchString);
            return dataManager.loadList(LoadContext.create(Mailfile.class).setQuery(
                LoadContext.createQuery("select e from rade$Mailfile e where e.pin like:pin escape '\\' order by e.pin")
                .setParameter("pin", searchString + "%")
            ));
        });
        picker.setWidth("100%");
        picker.setEnterActionHandler(searchString -> {
            Mailfile mailfile = dataManager.load(LoadContext.create(Mailfile.class).setQuery(
                LoadContext.createQuery("select e from rade$Mailfile e where e.pin = :pin ")
                    .setParameter("pin", searchString))
                    .setView("mailfile-browse-view")
            );
            if (mailfile == null) {
                notifications.create(NotificationType.ERROR)
                    .withCaption("PIN could not be found - please try again")
                    .show();
                return;
            }
            selectMailfile(updtrans, mailfile);
        });

        // actionLookup.setShortcut("ENTER");
        picker.removeAllActions();
        if (updtrans == null || updtrans.getUpdatedate() == null) {
            picker.addAction(actionLookup);
            picker.addAction(actionClear);
        } else {
            picker.addAction(actionOpen);
        }
        picker.setCaption("PIN");
        picker.addAction(actionEdit);
        return picker;
    }

My pinTable.create looks like this:

    @Subscribe("pinTable.create")
    public void onPinTableCreate(ActionPerformedEvent event) {
        if (batchhdrDc.getItem() == null) {
            notifications.create()
                    .withCaption("Please open an existing batch or create a new batch first")
                    .withType(NotificationType.ERROR)
                    .show();

            return;
        }
        if (paymentRadioButtonGroup.getValue() == null) {
            notifications.create()
                    .withCaption("Please set a default payment type first")
                    .withType(NotificationType.ERROR)
                    .show();
            return;
        }

        Updtrans updtrans = metadata.create(Updtrans.class);
        updtrans.setTraynumber(batchhdrDc.getItem());
        updtrans.setPurchdate(batchhdrDc.getItem().getBatchdate());
        updtrans.setPaymentcode((PaymentCodeEnum) paymentRadioButtonGroup.getValue());
        updtrans.setAmount(BigDecimal.ZERO);
        updtrans = dataContext.merge(updtrans);
        updtransDc.getMutableItems().add(0,updtrans);
        pinTable.requestFocus(updtrans,"mailfile");
    }

I create a row and all is good. I create a second row (top row) and I get this:

image

As you can see, the contents of the pin cell in the created row (top row) is the same as the previously created row. They actually seem to contain the same picker field. If I change the pin in the top row, the value in the second row changes as well. If I select the top row instead, I get this:

image

As you can see, the pin field in BOTH rows is now empty.

What am I doing wrong? Why are these cells connected?

Of course, right after posting I found the solution here:

https://www.cuba-platform.com/discuss/t/create-editable-table-with-lookupfields-insted-of-pickerfields-for-entities/9334/3

My mistake was this code:

picker.setValueSource(new ContainerValueSource<>(updtransDc,"mailfile"));

must be

picker.setValueSource(new ContainerValueSource<>(pinTable.getInstanceContainer(updtrans),"mailfile"));

You have to get the value source for the table row, not for the entire collection.

Suggestion - could this be explained in the table or LookupField/PickerField/SuggestionPickerField documentation?

1 Like