Delete rows from Nattable

后端 未结 2 1586
佛祖请我去吃肉
佛祖请我去吃肉 2020-12-21 21:30

I want to implement a row deletion logic in a Nebula Nattable. This is what I plan to do:

  1. Add context menu to the Nattable which is described in http://blog.v
相关标签:
2条回答
  • 2020-12-21 22:19

    In our application we do the following:

    1. Get selected row objects:

      SelectionLayer selectionLayer = body.getSelectionLayer();
      int[] selectedRowPositions = selectionLayer.getFullySelectedRowPositions();
      Vector<Your Model Objects> rowObjectsToRemove = new Vector<Your Model Objects>();
      
      for (int rowPosition : selectedRowPositions) {
          int rowIndex = selectionLayer.getRowIndexByPosition(rowPosition);
          rowObjectsToRemove .add(listDataProvider.getRowObject(rowIndex));
      }
      
    2. Remove them from the data provider

    3. call natTable.refresh()
    0 讨论(0)
  • 2020-12-21 22:23

    In NatTable you would typically do the following:

    1. Create a command for deleting a row

      public class DeleteRowCommand extends AbstractRowCommand {
      
          public DeleteRowCommand(ILayer layer, int rowPosition) {
              super(layer, rowPosition);
          }
      
          protected DeleteRowCommand(DeleteRowCommand command) {
              super(command);
          }
      
          @Override
          public ILayerCommand cloneCommand() {
              return new DeleteRowCommand(this);
          }
      
      }
      
    2. Create a command handler for that command

      public class DeleteRowCommandHandler<T> implements ILayerCommandHandler<DeleteRowCommand> {
      
          private List<T> bodyData;
      
          public DeleteRowCommandHandler(List<T> bodyData) {
              this.bodyData = bodyData;
          }
      
          @Override
          public Class<DeleteRowCommand> getCommandClass() {
              return DeleteRowCommand.class;
          }
      
          @Override
          public boolean doCommand(ILayer targetLayer, DeleteRowCommand command) {
              //convert the transported position to the target layer
              if (command.convertToTargetLayer(targetLayer)) {
                  //remove the element
                  this.bodyData.remove(command.getRowPosition());
                  //fire the event to refresh
                  targetLayer.fireLayerEvent(new RowDeleteEvent(targetLayer, command.getRowPosition()));
                  return true;
              }
              return false;
          }
      
      }
      
    3. Register the command handler to the body DataLayer

      bodyDataLayer.registerCommandHandler(
              new DeleteRowCommandHandler<your type>(bodyDataProvider.getList()));
      
    4. Add a menu item to your menu configuration that fires the command

      new PopupMenuBuilder(natTable)
              .withMenuItemProvider(new IMenuItemProvider() {
      
                  @Override
                  public void addMenuItem(NatTable natTable, Menu popupMenu) {
                      MenuItem deleteRow = new MenuItem(popupMenu, SWT.PUSH);
                      deleteRow.setText("Delete");
                      deleteRow.setEnabled(true);
      
                      deleteRow.addSelectionListener(new SelectionAdapter() {
                          @Override
                          public void widgetSelected(SelectionEvent event) {
                              int rowPosition = MenuItemProviders.getNatEventData(event).getRowPosition();
                              natTable.doCommand(new DeleteRowCommand(natTable, rowPosition));
                          }
                      });
                  }
              })
              .build();
      

    Using this you don't need to call NatTable#refresh() because the command handler fires a RowDeleteEvent. I also don't suggest to call NatTable#refresh() in such a case, as it might change and refresh more than it should and would not update other states correctly, which is done correctly by firing the RowDeleteEvent.

    Note that the shown example deletes the row for which the context menu is opened. If all selected rows should be deleted, you should create a command handler that knows the SelectionLayer and retrieve the selected rows as shown in the other answer.

    0 讨论(0)
提交回复
热议问题