/** * @author Jay Shaughnessy * @author Greg Hinkle * @author Simeon Pinder */ public class DashboardView extends LocatableVLayout { private DashboardContainer dashboardContainer; private Dashboard storedDashboard; boolean editMode = false; PortalLayout portalLayout; LocatableDynamicForm editForm; IMenuButton addPortlet; HashSet<PortletWindow> portletWindows = new HashSet<PortletWindow>(); private static String STOP = MSG.view_dashboards_portlets_refresh_none(); private static String REFRESH1 = MSG.view_dashboards_portlets_refresh_one_min(); private static String REFRESH5 = MSG.view_dashboards_portlets_refresh_multiple_min(String.valueOf(5)); private static String REFRESH10 = MSG.view_dashboards_portlets_refresh_multiple_min(String.valueOf(10)); private static Integer STOP_VALUE = 0; private static Integer REFRESH1_VALUE = 1 * 60000; private static Integer REFRESH5_VALUE = 5 * 60000; private static Integer REFRESH10_VALUE = 10 * 60000; private HashMap<Integer, String> refreshMenuMappings; private MenuItem[] refreshMenuItems; private int refreshInterval = 0; private LocatableIMenuButton refreshMenuButton; private EntityContext context; private ResourceGroupComposite groupComposite = null; private ResourceComposite resourceComposite = null; // this is used to prevent an odd smartgwt problem where onInit() can get called multiple times if // the view is set to a Tab's pane. private boolean isInitialized = false; /** * Convenience constructor for subsystem context. * * @param locatorId * @param dashboardContainer * @param storedDashboard */ public DashboardView( String locatorId, DashboardContainer dashboardContainer, Dashboard storedDashboard) { this(locatorId, dashboardContainer, storedDashboard, EntityContext.forSubsystemView(), null); } /** * @param locatorId * @param dashboardContainer * @param storedDashboard * @param context * @param composite ResourceComposite, ResourceGroupComposite or null depending on context */ public DashboardView( String locatorId, DashboardContainer dashboardContainer, Dashboard storedDashboard, EntityContext context, Object composite) { super(locatorId); this.dashboardContainer = dashboardContainer; this.storedDashboard = storedDashboard; // This is a workaround for the fact that RHQ 4.1 and earlier wrongly allowed the user to save a // dashboard with // 0 columns. if (this.storedDashboard.getColumns() == 0) { this.storedDashboard.setColumns(1); } this.context = context; switch (this.context.getType()) { case Resource: { if (null == composite) { throw new IllegalArgumentException("null composite for resource context"); } this.resourceComposite = (ResourceComposite) composite; break; } case ResourceGroup: { if (null == composite) { throw new IllegalArgumentException("null composite for group context"); } this.groupComposite = (ResourceGroupComposite) composite; break; } } } @Override protected void onInit() { if (!isInitialized) { super.onInit(); this.setWidth100(); this.setHeight100(); this.addMember(buildEditForm()); buildPortlets(); isInitialized = true; } } public void rebuild() { // destroy all of the portlets and recreate from scratch portalLayout.removeFromParent(); portalLayout.destroy(); portalLayout = null; buildPortlets(); } @Override protected void onDraw() { super.onDraw(); setEditMode(editMode); } public void buildPortlets() { this.setBackgroundColor( storedDashboard.getConfiguration().getSimpleValue(Dashboard.CFG_BACKGROUND, "white")); portalLayout = new PortalLayout( extendLocatorId("PortalLayout"), this, storedDashboard.getColumns(), storedDashboard.getColumnWidths()); portalLayout.setOverflow(Overflow.AUTO); portalLayout.setWidth100(); portalLayout.setHeight100(); loadPortletWindows(); addMember(portalLayout); } protected boolean canEditName() { return true; } private DynamicForm buildEditForm() { editForm = new LocatableDynamicForm(extendLocatorId("Editor")); editForm.setMargin(5); editForm.setAutoWidth(); editForm.setNumCols(canEditName() ? 12 : 10); TextItem nameItem = null; if (dashboardContainer.supportsDashboardNameEdit()) { nameItem = new TextItem("name", MSG.common_title_dashboard_name()); nameItem.setValue(storedDashboard.getName()); nameItem.setLength(200); nameItem.setWrapTitle(false); nameItem.addBlurHandler( new BlurHandler() { public void onBlur(BlurEvent blurEvent) { FormItem nameItem = blurEvent.getItem(); String name = (String) nameItem.getValue(); String trimmedName = (name == null) ? "" : name.trim(); if (dashboardContainer.isValidDashboardName(trimmedName)) { storedDashboard.setName(trimmedName); save(); dashboardContainer.updateDashboardNames(); } else { // TODO: i18n Message message = new Message( "There is already a dashboard named '" + trimmedName + "'. Please specify a name that is not already in use.", Message.Severity.Error, EnumSet.of(Message.Option.Transient)); CoreGUI.getMessageCenter().notify(message); nameItem.setValue(storedDashboard.getName()); } } }); } final StaticTextItem numColItem = new StaticTextItem(); numColItem.setTitle(MSG.common_title_columns()); numColItem.setValue(storedDashboard.getColumns()); ButtonItem addColumn = new ButtonItem("addColumn", MSG.common_title_add_column()); addColumn.setAutoFit(true); addColumn.setStartRow(false); addColumn.setEndRow(false); final ButtonItem removeColumn = new ButtonItem("removeColumn", MSG.common_title_remove_column()); removeColumn.setAutoFit(true); removeColumn.setStartRow(false); removeColumn.setEndRow(false); removeColumn.setDisabled(storedDashboard.getColumns() == 1); addColumn.addClickHandler( new com.smartgwt.client.widgets.form.fields.events.ClickHandler() { public void onClick(com.smartgwt.client.widgets.form.fields.events.ClickEvent event) { portalLayout.addMember(new PortalColumn()); numColItem.setValue(storedDashboard.getColumns() + 1); storedDashboard.setColumns(storedDashboard.getColumns() + 1); removeColumn.setDisabled(storedDashboard.getColumns() == 1); save(); } }); removeColumn.addClickHandler( new com.smartgwt.client.widgets.form.fields.events.ClickHandler() { public void onClick(com.smartgwt.client.widgets.form.fields.events.ClickEvent event) { Canvas[] columns = portalLayout.getMembers(); int numColumns = columns.length; if (numColumns > 0) { PortalColumn lastColumn = (PortalColumn) columns[numColumns - 1]; for (Canvas portletWindow : lastColumn.getMembers()) { storedDashboard.removePortlet(((PortletWindow) portletWindow).getStoredPortlet()); } portalLayout.removeMember(lastColumn); numColItem.setValue(numColumns - 1); storedDashboard.setColumns(storedDashboard.getColumns() - 1); removeColumn.setDisabled(storedDashboard.getColumns() == 1); save(); } } }); // build the menu of valid portlets for this context, sorted by portlet name final Menu addPortletMenu = new LocatableMenu(editForm.extendLocatorId("PortletMenu")); LinkedHashMap<String, String> valueMap; switch (context.getType()) { case SubsystemView: valueMap = PortletFactory.getGlobalPortletMenuMap(); break; case ResourceGroup: valueMap = processPortletNameMapForGroup(this.groupComposite); // In addition to the group-specific portlets, make the global portlets available valueMap.putAll(PortletFactory.getGlobalPortletMenuMap()); break; case Resource: valueMap = processPortletNameMapForResource(this.resourceComposite); // In addition to the resource-specific portlets, make the global portlets available valueMap.putAll(PortletFactory.getGlobalPortletMenuMap()); break; default: throw new IllegalStateException("Unsupported context [" + context + "]"); } for (Iterator<String> i = valueMap.keySet().iterator(); i.hasNext(); ) { String portletKey = i.next(); String portletName = valueMap.get(portletKey); MenuItem menuItem = new MenuItem(portletName); menuItem.setAttribute("portletKey", portletKey); addPortletMenu.addItem(menuItem); } addPortlet = new LocatableIMenuButton( editForm.extendLocatorId("AddPortlet"), MSG.common_title_add_portlet(), addPortletMenu); addPortlet.setIcon("[skin]/images/actions/add.png"); addPortlet.setAutoFit(true); addPortletMenu.addItemClickHandler( new ItemClickHandler() { public void onItemClick(ItemClickEvent itemClickEvent) { String key = itemClickEvent.getItem().getAttribute("portletKey"); String name = itemClickEvent.getItem().getTitle(); addPortlet(key, name); } }); CanvasItem addCanvas = new CanvasItem(); addCanvas.setShowTitle(false); addCanvas.setCanvas(addPortlet); addCanvas.setStartRow(false); addCanvas.setEndRow(false); ColorButtonItem picker = new ColorButtonItem("colorButton", MSG.common_title_background()); picker.setStartRow(false); picker.setEndRow(false); picker.setCurrentColor( storedDashboard.getConfiguration().getSimpleValue(Dashboard.CFG_BACKGROUND, "white")); picker.setColorSelectedHandler( new ColorSelectedHandler() { @Override public void onColorSelected(ColorSelectedEvent event) { String selectedColor = event.getColor(); if (selectedColor != null) { setBackgroundColor(selectedColor); storedDashboard .getConfiguration() .put(new PropertySimple(Dashboard.CFG_BACKGROUND, selectedColor)); save(); } } }); // refresh interval LocatableMenu refreshMenu = new LocatableMenu("AutoRefreshMenu"); refreshMenu.setShowShadow(true); refreshMenu.setShadowDepth(10); refreshMenu.setAutoWidth(); refreshMenu.setHeight(15); ClickHandler menuClick = new ClickHandler() { @Override public void onClick(MenuItemClickEvent event) { String selection = event.getItem().getTitle(); refreshInterval = 0; if (selection != null) { if (selection.equals(STOP)) { refreshInterval = STOP_VALUE; } else if (selection.equals(REFRESH1)) { refreshInterval = REFRESH1_VALUE; } else if (selection.equals(REFRESH5)) { refreshInterval = REFRESH5_VALUE; } else if (selection.equals(REFRESH10)) { refreshInterval = REFRESH10_VALUE; } else { // unable to locate value disable refresh refreshInterval = STOP_VALUE; // } UserSessionManager.getUserPreferences() .setPageRefreshInterval(refreshInterval, new UpdatePortletRefreshCallback()); } } }; String[] refreshIntervals = {STOP, REFRESH1, REFRESH5, REFRESH10}; Integer[] refreshValues = {STOP_VALUE, REFRESH1_VALUE, REFRESH5_VALUE, REFRESH10_VALUE}; refreshMenuMappings = new HashMap<Integer, String>(); refreshMenuItems = new MenuItem[refreshIntervals.length]; int retrievedRefreshInterval = REFRESH1_VALUE; if (null != UserSessionManager.getUserPreferences()) { retrievedRefreshInterval = UserSessionManager.getUserPreferences().getPageRefreshInterval(); } for (int i = 0; i < refreshIntervals.length; i++) { MenuItem item = new MenuItem(refreshIntervals[i], ""); item.addClickHandler(menuClick); refreshMenuMappings.put(refreshValues[i], refreshIntervals[i]); if (retrievedRefreshInterval == refreshValues[i]) { item.setIcon(ImageManager.getAvailabilityIcon(true)); } refreshMenuItems[i] = item; } refreshMenu.setItems(refreshMenuItems); refreshMenuButton = new LocatableIMenuButton( "AutoRefreshButton", MSG.common_title_change_refresh_time(), refreshMenu); refreshMenu.setAutoHeight(); refreshMenuButton.getMenu().setItems(refreshMenuItems); refreshMenuButton.setWidth(140); refreshMenuButton.setShowTitle(true); refreshMenuButton.setTop(0); refreshMenuButton.setIconOrientation("left"); CanvasItem refreshCanvas = new CanvasItem(); refreshCanvas.setShowTitle(false); refreshCanvas.setCanvas(refreshMenuButton); refreshCanvas.setStartRow(false); refreshCanvas.setEndRow(false); if (null != nameItem) { editForm.setItems( nameItem, addCanvas, numColItem, addColumn, removeColumn, picker, refreshCanvas); } else { editForm.setItems(addCanvas, numColItem, addColumn, removeColumn, picker, refreshCanvas); } updateRefreshMenu(); this.refreshMenuButton.markForRedraw(); markForRedraw(); // attempt to initialize editForm.markForRedraw(); markForRedraw(); return editForm; } /** Return the relevant sorted value map for the resource */ public static LinkedHashMap<String, String> processPortletNameMapForResource( ResourceComposite composite) { LinkedHashMap<String, String> resourceMenuMap = PortletFactory.getResourcePortletMenuMap(); if ((composite != null) && (composite.getResource() != null)) { resourceMenuMap = new LinkedHashMap<String, String>(resourceMenuMap); // filter out portlets not relevent for facets Set<ResourceTypeFacet> facets = composite.getResourceFacets().getFacets(); if (!facets.isEmpty()) { // Operation related portlets if (!facets.contains(ResourceTypeFacet.OPERATION)) { resourceMenuMap.remove(ResourceOperationsPortlet.KEY); } // MEASUREMENT related portlets(METRICS) if (!facets.contains(ResourceTypeFacet.MEASUREMENT)) { resourceMenuMap.remove(ResourceMetricsPortlet.KEY); resourceMenuMap.remove(ResourceMetricsPortlet.KEY); } // Content related portlets if (!facets.contains(ResourceTypeFacet.CONTENT)) { resourceMenuMap.remove(ResourcePkgHistoryPortlet.KEY); } // Event related portlets if (!facets.contains(ResourceTypeFacet.EVENT)) { resourceMenuMap.remove(ResourceEventsPortlet.KEY); } // Configuration related portlets if (!facets.contains(ResourceTypeFacet.CONFIGURATION)) { resourceMenuMap.remove(ResourceConfigurationUpdatesPortlet.KEY); } // Bundle related portlets if (!facets.contains(ResourceTypeFacet.BUNDLE)) { resourceMenuMap.remove(ResourceBundleDeploymentsPortlet.KEY); } } } return resourceMenuMap; } /** Return the relevant sorted value map for the group */ public static LinkedHashMap<String, String> processPortletNameMapForGroup( ResourceGroupComposite composite) { LinkedHashMap<String, String> groupMenuMap = PortletFactory.getGroupPortletMenuMap(); if ((composite != null) && (composite.getResourceGroup() != null)) { groupMenuMap = new LinkedHashMap<String, String>(groupMenuMap); // filter out portlets not relevent for facets Set<ResourceTypeFacet> facets = composite.getResourceFacets().getFacets(); GroupCategory groupCategory = composite.getResourceGroup().getGroupCategory(); // if not a compatible group do some pruning. if (groupCategory != GroupCategory.COMPATIBLE) { groupMenuMap.remove(GroupOperationsPortlet.KEY); groupMenuMap.remove(GroupMetricsPortlet.KEY); groupMenuMap.remove(GroupOobsPortlet.KEY); groupMenuMap.remove(GroupPkgHistoryPortlet.KEY); groupMenuMap.remove(GroupConfigurationUpdatesPortlet.KEY); groupMenuMap.remove(GroupBundleDeploymentsPortlet.KEY); } else { // for compatible may still need to do some pruning. if (!facets.isEmpty()) { // Operations related portlets(Config,PkgHistory) if (!facets.contains(ResourceTypeFacet.OPERATION)) { groupMenuMap.remove(GroupOperationsPortlet.KEY); } // MEASUREMENT related portlets(METRICS) if (!facets.contains(ResourceTypeFacet.MEASUREMENT)) { groupMenuMap.remove(GroupMetricsPortlet.KEY); groupMenuMap.remove(GroupOobsPortlet.KEY); } // CONTENT related portlets(CONTENT) if (!facets.contains(ResourceTypeFacet.CONTENT)) { groupMenuMap.remove(GroupPkgHistoryPortlet.KEY); } // CONFIGURATION related portlets(CONFIGURATION) if (!facets.contains(ResourceTypeFacet.CONFIGURATION)) { groupMenuMap.remove(GroupConfigurationUpdatesPortlet.KEY); } // BUNDLE related portlets(BUNDLE) if (!facets.contains(ResourceTypeFacet.BUNDLE)) { groupMenuMap.remove(GroupBundleDeploymentsPortlet.KEY); } } } } return groupMenuMap; } private void loadPortletWindows() { for (int i = 0; i < storedDashboard.getColumns(); i++) { for (DashboardPortlet storedPortlet : storedDashboard.getPortlets(i)) { String locatorId = getPortletLocatorId(portalLayout, storedPortlet); PortletWindow portletWindow = new PortletWindow(locatorId, this, storedPortlet, context); portletWindow.setTitle(storedPortlet.getName()); portletWindow.setHeight(storedPortlet.getHeight()); portletWindow.setVisible(true); portletWindows.add(portletWindow); portalLayout.addPortletWindow(portletWindow, i); } } } /** * LocatorIds need to be repeatable and non-duplicated. The natural key for a portlet is the Id * but the Id is not a good locatorId as it may change (it's a sequence generated id) on * subsequent test runs. A portlet has an internal identifier (portletKey) and a name, but the * key-name tuple is not guaranteed to be unique as multiple instances of the same portlet type * may be present on the same, or across multiple dashboards. There is one tuple that is * guaranteed unique and useful for a repeatable locator Id: DashBoard-Position. This means that * the on a single dashboard each portlet has a unique column-columnIndex pair. Although portlets * can move, and the positions can change at runtime, it's still valid for a locatorId because it * is unique and repeatable for test purposes. We also add the portletKey for an easier visual * cue. The portalLayout's locatorId already incorporates the dashboardName, so we need only * extend it with the positioning information. * * @param portalLayout * @param dashboardPortlet * @return The locatorId for the portlet. Form PortleyKey_DashboardId_Column_ColumnIndex */ private String getPortletLocatorId(PortalLayout portalLayout, DashboardPortlet dashboardPortlet) { StringBuilder locatorId = new StringBuilder(dashboardPortlet.getPortletKey()); locatorId.append("_"); locatorId.append(dashboardPortlet.getColumn()); locatorId.append("_"); locatorId.append(dashboardPortlet.getIndex()); return portalLayout.extendLocatorId(locatorId.toString()); } protected void addPortlet(String portletKey, String portletName) { DashboardPortlet storedPortlet = new DashboardPortlet(portletName, portletKey, 250); storedDashboard.addPortlet(storedPortlet); String locatorId = getPortletLocatorId(portalLayout, storedPortlet); final PortletWindow newPortletWindow = new PortletWindow(locatorId, this, storedPortlet, context); newPortletWindow.setTitle(portletName); newPortletWindow.setHeight(350); newPortletWindow.setVisible(false); portletWindows.add(newPortletWindow); portalLayout.addPortletWindow(newPortletWindow, storedPortlet.getColumn()); PortalColumn portalColumn = portalLayout.getPortalColumn(storedPortlet.getColumn()); // also insert a blank spacer element, which will trigger the built-in // animateMembers layout animation final LayoutSpacer placeHolder = new LayoutSpacer(); // placeHolder.setRect(newPortlet.getRect()); portalColumn.addMember(placeHolder); // add to top // create an outline around the clicked button final Canvas outline = new Canvas(); outline.setLeft(editForm.getAbsoluteLeft() + addPortlet.getLeft()); outline.setTop(editForm.getAbsoluteTop()); outline.setWidth(addPortlet.getWidth()); outline.setHeight(addPortlet.getHeight()); outline.setBorder("2px solid 8289A6"); outline.draw(); outline.bringToFront(); outline.animateRect( newPortletWindow.getPageLeft(), newPortletWindow.getPageTop(), newPortletWindow.getVisibleWidth(), newPortletWindow.getViewportHeight(), new AnimationCallback() { public void execute(boolean earlyFinish) { // callback at end of animation - destroy placeholder and outline; show the new portlet placeHolder.destroy(); outline.destroy(); newPortletWindow.show(); } }, 750); save(); } public void removePortlet(DashboardPortlet portlet) { storedDashboard.removePortlet(portlet); // portlet remove means the portlet locations may have changed. The selenium testing locators // include // positioning info. So, in this case we have to take the hit and completely refresh the dash. AsyncCallback<Dashboard> callback = SeleniumUtility.getUseDefaultIds() ? null : new AsyncCallback<Dashboard>() { @Override public void onFailure(Throwable caught) { rebuild(); } @Override public void onSuccess(Dashboard result) { rebuild(); } }; save(callback); } public void save(Dashboard dashboard) { if (null != dashboard) { storedDashboard = dashboard; save(); } } public void save() { save((AsyncCallback<Dashboard>) null); } public String[] updatePortalColumnWidths() { int numColumns = storedDashboard.getColumns(); int totalPixelWidth = 0; int[] columnPixelWidths = new int[numColumns]; for (int i = 0; i < numColumns; ++i) { PortalColumn col = portalLayout.getPortalColumn(i); totalPixelWidth += col.getWidth(); columnPixelWidths[i] = col.getWidth(); } String[] columnWidths = new String[numColumns]; columnWidths[numColumns - 1] = "*"; for (int i = 0; i < numColumns - 1; ++i) { columnWidths[i] = String.valueOf(((int) columnPixelWidths[i] * 100 / totalPixelWidth)) + "%"; } storedDashboard.setColumnWidths(columnWidths); return columnWidths; } public void save(final AsyncCallback<Dashboard> callback) { // a variety of edits (dragResize, add/remove column, etc) can cause column width changes. // Update them // prior to every save. updatePortalColumnWidths(); // since we reset storedDashboard after the async update completes, block modification of the // dashboard // during that interval. DashboardView.this.disable(); GWTServiceLookup.getDashboardService() .storeDashboard( storedDashboard, new AsyncCallback<Dashboard>() { public void onFailure(Throwable caught) { CoreGUI.getErrorHandler().handleError(MSG.view_dashboardManager_error(), caught); DashboardView.this.enable(); if (null != callback) { callback.onFailure(caught); } } public void onSuccess(Dashboard result) { CoreGUI.getMessageCenter() .notify( new Message( MSG.view_dashboardManager_saved(result.getName()), Message.Severity.Info)); // The portlet definitions have been merged and updated, reset the portlet windows // with the // up to date portlets. updatePortletWindows(result); storedDashboard = result; if (null != callback) { callback.onSuccess(result); } DashboardView.this.enable(); } }); } private void updatePortletWindows(Dashboard result) { if (result != null) { for (PortletWindow portletWindow : portletWindows) { for (DashboardPortlet updatedPortlet : result.getPortlets()) { if (equalsDashboardPortlet(portletWindow.getStoredPortlet(), updatedPortlet)) { portletWindow.setStoredPortlet(updatedPortlet); // restarting portlet auto-refresh with newest settings Portlet view = portletWindow.getView(); if (view instanceof AutoRefreshPortlet) { ((AutoRefreshPortlet) view).startRefreshCycle(); } break; } } } } } /** * This is an enhanced equals for portlets that allows equality for unpersisted portlets. At times (like addPortlet) * a portlet may have been associated with its window prior to being persisted. In this case we can consider * it equal if it is associated with the same dashboard(1) and has the same positioning. Note that key-name pairing * can not be used for equality as a dashboard is allowed to have the same portlet multiple times, with a default * name. But they can not hold the same position. * <pre> * (1) Even the dashboard comparison has been made flexible. To allow for lazy persist of the dashboard (to * allow for the default group or resource dashboard to not be persisted) we allow the dash comparison * to be done by name if an entity id is 0. This should be safe as dashboard names are set prior to * persist, and should be unique for the session user. * * @param storedPortlet * @param updatedPortlet * @return */ private boolean equalsDashboardPortlet( DashboardPortlet storedPortlet, DashboardPortlet updatedPortlet) { if (storedPortlet.equals(updatedPortlet)) { return true; } // make sure at least one portlet is not persisted for pseudo-equality if (storedPortlet.getId() > 0 && updatedPortlet.getId() > 0) { return false; } // must match position for pseudo-equality if (storedPortlet.getColumn() != updatedPortlet.getColumn()) { return false; } if (storedPortlet.getIndex() != updatedPortlet.getIndex()) { return false; } // must match dash (ids if persisted, otherwise name) for pseudo-equality boolean unpersistedDash = (storedPortlet.getDashboard().getId() == 0 || updatedPortlet.getDashboard().getId() == 0); boolean dashMatchId = (!unpersistedDash && (storedPortlet.getDashboard().getId() == updatedPortlet.getDashboard().getId())); boolean dashMatchName = (unpersistedDash && storedPortlet .getDashboard() .getName() .equals(updatedPortlet.getDashboard().getName())); if (!(dashMatchId || dashMatchName)) { return false; } return true; } public void delete() { if (null != this.storedDashboard && this.storedDashboard.getId() > 0) { GWTServiceLookup.getDashboardService() .removeDashboard( this.storedDashboard.getId(), new AsyncCallback<Void>() { public void onFailure(Throwable caught) { CoreGUI.getErrorHandler() .handleError(MSG.view_dashboardManager_deleteFail(), caught); } public void onSuccess(Void result) { CoreGUI.getMessageCenter() .notify( new Message( MSG.view_dashboardManager_deleted(storedDashboard.getName()), Message.Severity.Info)); } }); } } public void resize() { portalLayout.resize(); } public Dashboard getDashboard() { return storedDashboard; } public Set<Permission> getGlobalPermissions() { return dashboardContainer.getGlobalPermissions(); } public void setEditMode(boolean editMode) { this.editMode = editMode; if (editMode) { this.editForm.show(); // } else { this.editForm.hide(); } this.editForm.markForRedraw(); this.portalLayout.show(); this.portalLayout.markForRedraw(); } public class UpdatePortletRefreshCallback implements AsyncCallback<Subject> { public void onSuccess(Subject subject) { String m; if (refreshInterval > 0) { m = MSG.view_dashboards_portlets_refresh_success1(); } else { m = MSG.view_dashboards_portlets_refresh_success2(); } CoreGUI.getMessageCenter().notify(new Message(m, Message.Severity.Info)); updateRefreshMenu(); save(); } public void onFailure(Throwable throwable) { String m; if (refreshInterval > 0) { m = MSG.view_dashboards_portlets_refresh_fail1(); } else { m = MSG.view_dashboards_portlets_refresh_fail2(); } CoreGUI.getMessageCenter().notify(new Message(m, Message.Severity.Error)); // Revert back to our original favorite status, since the server update failed. updateRefreshMenu(); } } public void updateRefreshMenu() { if (refreshMenuItems != null) { int retrievedRefreshInterval = REFRESH1_VALUE; if (null != UserSessionManager.getUserPreferences()) { retrievedRefreshInterval = UserSessionManager.getUserPreferences().getPageRefreshInterval(); } String currentSelection = refreshMenuMappings.get(retrievedRefreshInterval); if (currentSelection != null) { // iterate over menu items and update icon details for (int i = 0; i < refreshMenuItems.length; i++) { MenuItem menu = refreshMenuItems[i]; if (currentSelection.equals(menu.getTitle())) { menu.setIcon(ImageManager.getAvailabilityIcon(true)); } else { menu.setIcon(""); } refreshMenuItems[i] = menu; } // update the menu refreshMenuButton.getMenu().setItems(refreshMenuItems); } } if (this.refreshMenuButton != null) { this.refreshMenuButton.markForRedraw(); } } public Dashboard getStoredDashboard() { return storedDashboard; } public EntityContext getContext() { return context; } public ResourceGroupComposite getGroupComposite() { return groupComposite; } public ResourceComposite getResourceComposite() { return resourceComposite; } }