我创建了一个vaadin表。当我right-click
时,它显示带有+New...
文本的上下文菜单,当我点击它时 - 它显示带有两个表的模态窗口。每张桌子都有相同的功能。
问题在于,每次打开和关闭模态窗口时,它都会在模态表上添加上下文菜单项的重复项(在主页面上它可以正常工作)。此外 - 当我点击模态表上下文菜单时,它会添加几个模态窗口(例如,如果我打开窗口5次 - 它会为点击的模态上下文菜单添加5个上下文菜单项和5个模态窗口)
返回一个项目的唯一方法 - 重启整个应用程序。 有什么问题?
我的每张桌子都是这样的
@Component("taskTable")
@Scope("prototype")
public class TaskTable extends AbstractObjectTable {
@Autowired
private TaskService taskService;
@Autowired
private NewTaskWindow taskWindow;
@Autowired
private ShowTaskDetailsWindow detailsWindow;
private Action[] action = new Action[] { new Action("+New...") };
@Override
public Table createTable() {
caption = "Tasks";
headers = new String[] { "Description", "Project", "Status", "Weight", "Developer", "ID" };
this.addActionHandler(new Handler() {
@Override
public Action[] getActions(Object target, Object sender) {
return action;
}
@Override
public void handleAction(Action action, Object sender, Object target) {
switch(action.getCaption()) {
case "+New...": {
PmcUi.getCurrent().addWindow(taskWindow.createWindow());
break;
}
}
//what to do for action
}
});
this.addItemClickListener(new ItemClickListener(){
@Override
public void itemClick(ItemClickEvent event) {
if (event.isDoubleClick()) {
PmcUi.getCurrent().addWindow(detailsWindow.createWindow());
}
return;
}
});
return super.createTable();
}
@Override
protected IndexedContainer projectDatasource() {
IndexedContainer indexedContainer = new IndexedContainer();
for(String header: headers) {
indexedContainer.addContainerProperty(header, String.class, "");
}
List<Task> tasks = taskService.findAllTasks();
for(int i = 0; i < tasks.size(); i++) {
Object id = indexedContainer.addItem();
Task item = tasks.get(i);
indexedContainer.getContainerProperty(id, headers[0]).setValue(item.getDescription());
indexedContainer.getContainerProperty(id, headers[1]).setValue(item.getTaskProject());
indexedContainer.getContainerProperty(id, headers[2]).setValue(item.getStatus());
indexedContainer.getContainerProperty(id, headers[3]).setValue(item.getWeight());
indexedContainer.getContainerProperty(id, headers[4]).setValue(item.getTaskDeveloper());
indexedContainer.getContainerProperty(id, headers[5]).setValue(item.getTaskId());
}
return indexedContainer;
}
}
AbstractObjectTable
public abstract class AbstractObjectTable extends Table {
protected String caption;
protected String[] headers = null;
protected Table createTable() {
this.setContainerDataSource(projectDatasource());
this.setVisibleColumns(headers);
this.setSelectable(true);
this.setImmediate(true);
return this;
}
protected abstract IndexedContainer projectDatasource();
}
我的+New...
模态窗口与
@Component("newTaskWindow")
public class NewTaskWindow {
private Window createTaskWindow;
@Autowired
private TaskService taskService;
public Window createWindow() {
createTaskWindow = new Window("New Task");
initWindow();
fillWindow();
return createTaskWindow;
}
private void initWindow() {
createTaskWindow.setSizeUndefined();
createTaskWindow.setResizable(false);
createTaskWindow.setModal(true);
createTaskWindow.addCloseListener(new CloseListener() {
@Override
public void windowClose(CloseEvent e) {
Notification.show("Closed");
}
});
}
private void fillWindow() {
final TextField taskDescription = new TextField("Description");
final ComboBox taskProject = new ComboBox("Select project");
final ComboBox taskDeveloper = new ComboBox("Select developer");
final TextField taskWeight = new TextField("Task weight");
final TextField taskStatus = new TextField("Task status");
Button create = new Button("Create");
create.addClickListener(new Button.ClickListener() {
@Override
public void buttonClick(ClickEvent event) {
Task task = new Task();
task.setTaskId(UUID.randomUUID().toString());
task.setStatus(taskStatus.getValue());
task.setTaskDeveloper(taskDeveloper.getValue().toString());
task.setTaskProject(taskProject.getValue().toString());
task.setWeight(taskWeight.getValue());
task.setDescription(taskDescription.getValue());
taskService.insertTask(task);
createTaskWindow.close();
}
});
Button close = new Button("Cancel");
close.addClickListener(new Button.ClickListener() {
@Override
public void buttonClick(ClickEvent event) {
createTaskWindow.close();
}
});
HorizontalLayout layout = new HorizontalLayout(create, close);
FormLayout formLayout = new FormLayout(taskProject, taskDeveloper, taskWeight, taskStatus,
taskDescription, layout);
formLayout.setMargin(true);
createTaskWindow.setContent(formLayout);
}
}
我的details
窗口也有类似的架构。
@Component("showTaskDetailsWindow")
public class ShowTaskDetailsWindow {
private Window showDetailsWindow;
@Autowired
private TaskService taskService;
public Window createWindow() {
showDetailsWindow = new Window("Show details");
initWindow();
fillWindow();
return showDetailsWindow;
}
private void initWindow() {
showDetailsWindow.setSizeUndefined();
showDetailsWindow.setResizable(false);
showDetailsWindow.setModal(true);
showDetailsWindow.addCloseListener(new CloseListener() {
@Override
public void windowClose(CloseEvent e) {
Notification.show("Closed");
}
});
}
private void fillWindow() {
final TextField taskDescription = new TextField("Description");
final TextField taskProject = new TextField("Task project");
final TextField taskDeveloper = new TextField("Task developer");
final TextField taskWeight = new TextField("Task weight");
final TextField taskStatus = new TextField("Task status");
FormLayout formLayout = new FormLayout(taskProject, taskDeveloper, taskWeight, taskStatus, taskDescription);
formLayout.setMargin(true);
showDetailsWindow.setContent(formLayout);
}
}
有什么问题?为什么它会不断增加?
答案 0 :(得分:0)
问题是你的getActions实现
@Override
public Action[] getActions(Object target, Object sender) {
return new Action[] { new Action("+New...")};
}
您应该创建一个“new Action(”+ New ...“)”项的实例,并将其存储在例如TaskTable对象中。 getActions(..)应该返回相同的实例。
如果您始终创建新操作,则只需将其添加到现有操作中。
答案 1 :(得分:0)
看起来createTable()
类的TaskTable
方法被调用的次数太多,但提供的代码并未显示该方法的调用位置。这会导致将多个操作处理程序和项目单击侦听器添加到表中。