代码之家  ›  专栏  ›  技术社区  ›  lapots

将新记录添加到数据库时更新vaadin网格

  •  1
  • lapots  · 技术社区  · 6 年前

    我想将元素添加到数据库中的表中,并用新数据更新网格(可能我应该直接将UI上的记录添加到表中,但无论如何)。

    我的 grid 组件看起来像这样

    @SpringComponent
    public class PlayersGrid extends Grid<Player> {
    
        @PostConstruct
        public void afterInit() {
            addColumn(Player::getId).setHeader("ID");
            addColumn(Player::getName).setHeader("Name");
            addColumn(Player::getCharacterClass).setHeader("Class");
            addColumn(Player::getLevel).setHeader("Level");
        }
    
        public class GridContentObserver implements ContentObserver {
    
            @Override
            public void refreshContent() {
                PlayersGrid.this.getDataProvider().refreshAll();
            }
        }
    }
    

    我加 players 像这样的表格

    @SpringComponent
    public class CharacterCreationForm extends FormLayout {
        private static final Logger LOGGER = LoggerFactory.getLogger(CharacterCreationForm.class);
    
        private List<ContentObserver> boundObservers = new ArrayList<>();
    
        private TextField name;
        private TextField characterClass;
        private TextField level;
    
        @Autowired
        private PlayerRepository repository;
    
        @PostConstruct
        public void create() {
            name = new TextField();
            characterClass = new TextField();
            level = new TextField();
    
            addFormItem(name, "Name");
            addFormItem(characterClass, "Class");
            addFormItem(level, "Level");
    
            Binder<Player> binder = new Binder<>(Player.class);
    
            binder
                .forField(level)
                .withConverter(new StringToIntegerConverter(0, ""))
                .bind(Player::getLevel, Player::setLevel);
    
            binder.bindInstanceFields(this);
    
            Button button = new Button("Save");
            button.addClickListener(buttonClickEvent -> {
                try {
                    Player newPlayer = new Player();
                    binder.writeBean(newPlayer);
                    LOGGER.info("Attempt to write object: {}", newPlayer);
    
                    repository.save(newPlayer);
                    // notify observers
                    boundObservers.forEach(ContentObserver::refreshContent);
                } catch (ValidationException e) {
                    e.printStackTrace();
                }
            });
    
            add(button);
        }
    
        public void addObserver(ContentObserver observer) {
            boundObservers.add(observer);
        }
    
    }
    

    应用程序中的主视图如下

    public MainView(PlayerRepository repository, PlayersGrid grid, CharacterCreationForm form) {
        form.addObserver(grid.new GridContentObserver());
        form.setWidth("30%");
    
        // find the way to set items in the component
        grid.setItems(repository.findAll());
    
        HorizontalLayout horizontalLayout = new HorizontalLayout();
        horizontalLayout.add(form);
    
        VerticalLayout verticalLayout = new VerticalLayout();
        verticalLayout.add(grid, form);
        verticalLayout.setHeight("100%");
        add(verticalLayout);
    
        setClassName("main-layout");
    }
    

    启动时,我的所有存储播放器都在网格中。但当我使用表单保存新记录时,它会在数据库中添加新记录,但不会更新网格。

    怎么了?

    1 回复  |  直到 6 年前
        1
  •  0
  •   nabeel    6 年前

    尝试以下更改,我认为这些更改将使代码更清晰,并使用ContentObserver解决问题

    (没有运行代码,因此我不确定是否存在编译问题!)

    更改1:PlayersGrid实现ContentObserver而不是具有内部类

    @SpringComponent
    public class PlayersGrid extends Grid<Player> implements ContentObserver {
    
        @PostConstruct
        public void afterInit() {
            addColumn(Player::getId).setHeader("ID");
            addColumn(Player::getName).setHeader("Name");
            addColumn(Player::getCharacterClass).setHeader("Class");
            addColumn(Player::getLevel).setHeader("Level");
        }
    
        @Override
        public void refreshContent() {
            this.getDataProvider().refreshAll();
        }
    }
    

    更改2:boundoServers.foreach

    @SpringComponent
    public class CharacterCreationForm extends FormLayout {
        private static final Logger LOGGER = 
                LoggerFactory.getLogger(CharacterCreationForm.class);
    
        private List<ContentObserver> boundObservers = new ArrayList<>();
    
        private TextField name;
        private TextField characterClass;
        private TextField level;
    
        @Autowired
        private PlayerRepository repository;
    
        @PostConstruct
        public void create() {
            name = new TextField();
            characterClass = new TextField();
            level = new TextField();
    
            addFormItem(name, "Name");
            addFormItem(characterClass, "Class");
            addFormItem(level, "Level");
    
            Binder<Player> binder = new Binder<>(Player.class);
    
            binder
                .forField(level)
                .withConverter(new StringToIntegerConverter(0, ""))
                .bind(Player::getLevel, Player::setLevel);
    
            binder.bindInstanceFields(this);
    
            Button button = new Button("Save");
            button.addClickListener(buttonClickEvent -> {
                try {
                    Player newPlayer = new Player();
                    binder.writeBean(newPlayer);
                    LOGGER.info("Attempt to write object: {}", newPlayer);
    
                    repository.save(newPlayer);
                    // notify observers
    
                    // updated
                    boundObservers.forEach( observer -> observer.refreshContent() );
    
                } catch (ValidationException e) {
                    e.printStackTrace();
                }
            });
    
            add(button);
        }
    
        public void addObserver(ContentObserver observer) {
            boundObservers.add(observer);
        }
    
    }
    

    更改3:网格现在也是ContentObserver,因此更容易管理和理解。

    public MainView(PlayerRepository repository, PlayersGrid grid, CharacterCreationForm form) {
        // updated
        form.addObserver(grid);
        form.setWidth("30%");
    
        // find the way to set items in the component
        grid.setItems(repository.findAll());
    
        HorizontalLayout horizontalLayout = new HorizontalLayout();
        horizontalLayout.add(form);
    
        VerticalLayout verticalLayout = new VerticalLayout();
        verticalLayout.add(grid, form);
        verticalLayout.setHeight("100%");
        add(verticalLayout);
    
        setClassName("main-layout");
    }