package pl.net.bluesoft.rnd.processtool.ui.activity; import static org.aperteworkflow.util.vaadin.VaadinUtility.verticalLayout; import static pl.net.bluesoft.util.lang.Formats.nvl; import java.util.ArrayList; import java.util.Calendar; import java.util.Collections; import java.util.HashMap; import java.util.List; import java.util.Map; import org.aperteworkflow.ui.view.ViewCallback; import org.aperteworkflow.ui.view.ViewRegistry; import org.aperteworkflow.ui.view.ViewRenderer; import org.aperteworkflow.util.vaadin.EventHandler; import org.aperteworkflow.util.vaadin.GenericVaadinPortlet2BpmApplication; import org.aperteworkflow.util.vaadin.ResourceCache; import org.aperteworkflow.util.vaadin.UriChangedCallback; import org.aperteworkflow.util.vaadin.VaadinUtility; import pl.net.bluesoft.rnd.processtool.ProcessToolContext; import pl.net.bluesoft.rnd.processtool.bpm.ProcessToolBpmSession; import pl.net.bluesoft.rnd.processtool.model.BpmTask; import pl.net.bluesoft.rnd.processtool.model.ProcessInstanceFilter; import pl.net.bluesoft.rnd.processtool.model.UserData; import pl.net.bluesoft.rnd.processtool.model.nonpersistent.ProcessQueue; import pl.net.bluesoft.rnd.processtool.ui.newprocess.NewProcessExtendedPane; import pl.net.bluesoft.rnd.processtool.ui.process.ProcessDataPane; import pl.net.bluesoft.rnd.processtool.ui.process.ProcessDataViewComponent; import pl.net.bluesoft.rnd.processtool.view.impl.BasicViewController; import pl.net.bluesoft.rnd.processtool.view.impl.ComponentPaneRenderer; import pl.net.bluesoft.rnd.util.i18n.I18NSource; import pl.net.bluesoft.util.lang.Strings; import com.vaadin.Application; import com.vaadin.terminal.Sizeable; import com.vaadin.ui.Button; import com.vaadin.ui.Button.ClickEvent; import com.vaadin.ui.Button.ClickListener; import com.vaadin.ui.Component; import com.vaadin.ui.ComponentContainer; import com.vaadin.ui.CssLayout; import com.vaadin.ui.HorizontalLayout; import com.vaadin.ui.UriFragmentUtility; import com.vaadin.ui.UriFragmentUtility.FragmentChangedEvent; import com.vaadin.ui.UriFragmentUtility.FragmentChangedListener; import com.vaadin.ui.VerticalLayout; import com.vaadin.ui.themes.BaseTheme; public class ActivityMainPane extends VerticalLayout implements ViewCallback { private Application application; private I18NSource i18NSource; private ProcessToolBpmSession bpmSession; private UriFragmentUtility uriFragmentUtility = new UriFragmentUtility(); private List<UriChangedCallback> uriCallbacks = new ArrayList<UriChangedCallback>(); private BasicViewController viewController; private Button showHideButton1; private LeftPanelVisibilityTrigger leftPanelTrigger; private Button showHideButton2; private HorizontalLayout horizontalLayout; private Button showHideButton0; private ResourceCache resourceCache; private ActivityQueuesPane activityQueuesPane; private ProcessDataViewComponent pdvc; public ActivityMainPane(Application application, I18NSource i18NSource, ProcessToolBpmSession bpmSession) { this.application = application; this.i18NSource = i18NSource; this.bpmSession = bpmSession; this.resourceCache = new ResourceCache(application); setWidth(100, Sizeable.UNITS_PERCENTAGE); initLayout(); } private void initLayout() { horizontalLayout = new HorizontalLayout(); uriFragmentUtility.addListener(new FragmentChangedListener() { @Override public void fragmentChanged(FragmentChangedEvent source) { String fragment = uriFragmentUtility.getFragment(); if(!uriCallbacks.isEmpty() && Strings.hasText(fragment)) { for(UriChangedCallback callback: uriCallbacks) { callback.handle(fragment); } } } }); activityQueuesPane = new ActivityQueuesPane(this); initViewController(); activityQueuesPane.refreshData(); viewController.displayCurrentView(); removeAllComponents(); showHideButton0 = new Button(); showHideButton0.setStyleName(BaseTheme.BUTTON_LINK); showHideButton0.setIcon(resourceCache.getImage("/img/guzik_1.png")); showHideButton0.setSizeFull(); showHideButton1 = new Button(); showHideButton1.setStyleName(BaseTheme.BUTTON_LINK); showHideButton1.setIcon(resourceCache.getImage("/img/guzik_2.png")); showHideButton2 = new Button(); showHideButton2.setStyleName(BaseTheme.BUTTON_LINK); showHideButton2.setIcon(resourceCache.getImage("/img/guzik_2.png")); final VerticalLayout leftPanel = verticalLayout(showHideButton1,new NewProcessExtendedPane(bpmSession, i18NSource, this),activityQueuesPane,new ActivityFiltersPane(this), showHideButton2); leftPanelTrigger = new LeftPanelVisibilityTrigger(leftPanel, true); leftPanel.setWidth(300, Sizeable.UNITS_PIXELS); showHideButton0.addListener(leftPanelTrigger); showHideButton1.addListener(leftPanelTrigger); showHideButton2.addListener(leftPanelTrigger); ComponentContainer viewContainer = viewController.getViewContainer(); horizontalLayout.setWidth(100,Sizeable.UNITS_PERCENTAGE); horizontalLayout.addComponent(leftPanel); horizontalLayout.addComponent(viewContainer); horizontalLayout.setExpandRatio(viewContainer,1.0f); addComponent(showHideButton0); addComponent(horizontalLayout); addComponent(uriFragmentUtility); } private void initViewController() { viewController = new BasicViewController(new ComponentPaneRenderer<MyProcessesListPane>(new MyProcessesListPane(this, i18NSource.getMessage("activity.assigned.tasks"))) { @Override public Component render(Map<String,?> viewData) { ProcessInstanceFilter filter = (ProcessInstanceFilter)viewData.get("filter"); if(filter != null) { pane.setTitle(filter.getName()); pane.setFilter(filter); } if(leftPanelTrigger != null) leftPanelTrigger.show(); return pane.init(); } }); viewController.addView(new ComponentPaneRenderer<ProcessDataViewComponent>(new ProcessDataViewComponent(application, i18NSource, viewController)) { @Override public String getViewId() { return ProcessDataViewComponent.class.getName(); } @Override public Component render(Map<String,?> viewData) { ProcessToolBpmSession bpmSession = (ProcessToolBpmSession)viewData.get("bpmSession"); BpmTask task = (BpmTask)viewData.get("task"); pane.attachProcessDataPane(task,bpmSession); ActivityMainPane.this.pdvc = pane; return pane; } }); viewController.addView(new ComponentPaneRenderer<OtherUserProcessesListPane>(new OtherUserProcessesListPane(this, i18NSource .getMessage("activity.user.tasks"))) { @Override public Component render(Map<String,?> viewData) { ProcessInstanceFilter filter = (ProcessInstanceFilter)viewData.get("filter"); if(filter != null) { pane.setTitle(filter.getName()); } pane.setFilter(filter); if (filter != null) { pane.setUserData(filter.getFilterOwner()); } leftPanelTrigger.show(); return pane.init(); } }); viewController.addView(new ComponentPaneRenderer<QueueListPane>(new QueueListPane(this)) { @Override public Component render(Map<String,?> viewData) { ProcessQueue q = (ProcessQueue)viewData.get("queue"); ProcessInstanceFilter filter = (ProcessInstanceFilter)viewData.get("filter"); pane.setFilter(filter); pane.setQueue(q); leftPanelTrigger.show(); return pane.init(); } }); viewController.addView(new ComponentPaneRenderer<OtherUserQueueListPane>(new OtherUserQueueListPane(this)) { @Override public Component render(Map<String,?> viewData) { ProcessQueue queue = (ProcessQueue)viewData.get("queue"); UserData user = (UserData)viewData.get("user"); ProcessInstanceFilter filter = (ProcessInstanceFilter)viewData.get("filter"); pane.setFilter(filter); pane.setUserData(user); pane.setQueue(queue); leftPanelTrigger.show(); return pane.init(); } }); viewController.addView(new ComponentPaneRenderer<RecentProcessesListPane>(new RecentProcessesListPane(this, i18NSource .getMessage("activity.recent.tasks"))) { @Override public Component render(Map<String,?> viewData) { Calendar minDate = (Calendar)viewData.get("minDate"); pane.setMinDate(minDate); leftPanelTrigger.show(); return pane.init(); } }); // to remove "strange" views, depending on external addons. Such // approach also gives us much greater flexibility ViewRegistry registeredService = ProcessToolContext.Util.getThreadProcessToolContext().getRegistry().getRegisteredService(ViewRegistry.class); if(registeredService != null) { for(final ViewRenderer viewRenderer: registeredService.getViews()) { viewRenderer.setBpmSession(getBpmSession()); viewRenderer.setUp(application); viewRenderer.setViewCallback(this); viewController.addView(viewRenderer); activityQueuesPane.addButton(viewRenderer.getTitle(),new Runnable() { @Override public void run() { viewRenderer.handleDisplayAction(); viewController.displayView(viewRenderer.getViewId(),null); } }); } } } public void addUriCallback(UriChangedCallback callback) { uriCallbacks.add(callback); } @Override public Application getApplication() { return application; } public I18NSource getI18NSource() { return i18NSource; } public ProcessToolBpmSession getBpmSession() { return bpmSession; } public void displayMyTasksPane() { confirmTaskClosing(new EventHandler() { @Override public void onEvent() { setShowExitWarning(application,false); VaadinUtility.unregisterClosingWarning(application.getMainWindow()); viewController.displayView(MyProcessesListPane.class); } }); } public void displayFilterPane(final ProcessInstanceFilter filter) { confirmTaskClosing(new EventHandler() { @Override public void onEvent() { setShowExitWarning(application,false); VaadinUtility.unregisterClosingWarning(application.getMainWindow()); viewController.displayView(MyProcessesListPane.class,Collections.singletonMap("filter",filter)); } }); } public void displayOtherUserTasksPane(final ProcessInstanceFilter filter) { confirmTaskClosing(new EventHandler() { @Override public void onEvent() { setShowExitWarning(application,false); VaadinUtility.unregisterClosingWarning(application.getMainWindow()); viewController.displayView(OtherUserProcessesListPane.class,Collections.singletonMap("filter",filter)); } }); } public void displayQueue(final ProcessQueue q) { confirmTaskClosing(new EventHandler() { @Override public void onEvent() { setShowExitWarning(application,false); VaadinUtility.unregisterClosingWarning(application.getMainWindow()); viewController.displayView(QueueListPane.class,Collections.singletonMap("queue",q)); } }); } public void displayOtherUserQueue(final ProcessQueue q, final UserData user) { confirmTaskClosing(new EventHandler() { @Override public void onEvent() { setShowExitWarning(application,false); VaadinUtility.unregisterClosingWarning(application.getMainWindow()); viewController.displayView(OtherUserQueueListPane.class,new HashMap<String,Object>() { { put("queue",q); put("user",user); } }); } }); } public void displayRecentTasksPane(final Calendar minDate) { confirmTaskClosing(new EventHandler() { @Override public void onEvent() { setShowExitWarning(application,false); VaadinUtility.unregisterClosingWarning(application.getMainWindow()); viewController.displayView(RecentProcessesListPane.class,Collections.singletonMap("minDate",minDate)); } }); } public void displayProcessData(BpmTask task) { displayProcessData(task,null); } public void displayProcessData(final BpmTask task, final ProcessToolBpmSession bpmSession) { displayProcessData(task,bpmSession,false); } public void displayProcessData(BpmTask task, boolean forward) { displayProcessData(task,null,forward); } public void displayProcessData(final BpmTask task, final ProcessToolBpmSession bpmSession, boolean forward) { displayProcessDataInPane(task,bpmSession,forward); } private void confirmTaskClosing(final EventHandler eventHandler) { BpmTask task; final ProcessToolContext processToolContextFromThread = ProcessToolContext.Util.getThreadProcessToolContext(); if(viewController.getCurrentViewId() != null && viewController.getCurrentViewId().equals(ProcessDataViewComponent.class.getName()) && (task = (BpmTask)viewController.getCurrentViewData().get("task")) != null && getBpmSession().isProcessRunning(task.getProcessInstance().getInternalId(),processToolContextFromThread)) { final ProcessDataPane pdp = pdvc != null && pdvc.getProcessDataPane() != null ? pdvc.getProcessDataPane() : null; VaadinUtility.displayConfirmationWindow( application,getI18NSource(), i18NSource.getMessage("activity.close.process.confirmation.title"), i18NSource.getMessage("activity.close.process.confirmation.question"), new String[] { "activity.close.process.confirmation.ok", pdp != null && pdp.canSaveProcessData() ? "activity.close.process.confirmation.save" : null, "activity.close.process.confirmation.cancel" }, new EventHandler[] { eventHandler, pdp != null && pdp.canSaveProcessData() ? new EventHandler() { @Override public void onEvent() { if (pdp.saveProcessDataButtonAction()) { eventHandler.onEvent(); } } } : null, null, }, null); } else { eventHandler.onEvent(); } } private void displayProcessDataInPane(final BpmTask task, final ProcessToolBpmSession bpmSession, boolean forward) { viewController.displayView(ProcessDataViewComponent.class,new HashMap<String,Object>() { { put("bpmSession",nvl(bpmSession,ActivityMainPane.this.bpmSession)); put("task",task); } },forward); } public void reloadCurrentViewData() { viewController.refreshCurrentView(); } public final class LeftPanelVisibilityTrigger implements ClickListener { private final VerticalLayout leftPanel; private boolean leftPanelVisible = true; public LeftPanelVisibilityTrigger(VerticalLayout leftPanel, boolean leftPanelVisible) { this.leftPanel = leftPanel; this.leftPanelVisible = leftPanelVisible; trigger(leftPanelVisible); } @Override public void buttonClick(ClickEvent event) { trigger(!leftPanelVisible); } public void trigger(boolean showPanel) { if(showPanel) { show(); } else { hide(); } } public void hide() { /* Fix for tab sheet - without those line, it doesn't expand */ leftPanel.setWidth(0, Sizeable.UNITS_PIXELS); leftPanel.setVisible(false); leftPanelVisible = false; showHideButton0.setVisible(true); horizontalLayout.setSizeFull(); horizontalLayout.requestRepaintAll(); } public void show() { /* Fix for tab sheet - without those line, it doesn't expand */ leftPanel.setWidth(300, Sizeable.UNITS_PIXELS); leftPanel.setVisible(true); leftPanelVisible = true; showHideButton0.setVisible(false); horizontalLayout.setSizeFull(); horizontalLayout.requestRepaintAll(); } } private void setShowExitWarning(Application application, boolean show) { if(application instanceof GenericVaadinPortlet2BpmApplication) ((GenericVaadinPortlet2BpmApplication)application).setShowExitWarning(show); } public void displayTaskById(String taskId) { BpmTask task = bpmSession.getTaskData(taskId,ProcessToolContext.Util.getThreadProcessToolContext()); if(task != null) { displayProcessData(task); } else { application.getMainWindow().showNotification(i18NSource.getMessage("process.data.task-notfound").replaceFirst("%s",taskId)); } } }