/***************************************************************************** * Copyright (c) 2010 CEA LIST. * * * All rights reserved. This program and the accompanying materials * are made available under the terms of the Eclipse Public License v1.0 * which accompanies this distribution, and is available at * http://www.eclipse.org/legal/epl-v10.html * * Contributors: * Vincent Lorenzo (CEA LIST) vincent.lorenzo@cea.fr - Initial API and implementation * Tatiana Fesenko (CEA LIST) - Bug 331102 - Allow to configure visibility of name of the compartment in the Filter Compartment dialog * *****************************************************************************/ package org.eclipse.papyrus.uml.diagram.menu.actions; import java.util.ArrayList; import java.util.Collections; import java.util.List; import org.eclipse.core.runtime.IAdaptable; import org.eclipse.core.runtime.IProgressMonitor; import org.eclipse.emf.ecore.EObject; import org.eclipse.emf.transaction.TransactionalEditingDomain; import org.eclipse.gef.EditPart; import org.eclipse.gef.commands.Command; import org.eclipse.gef.commands.CompoundCommand; import org.eclipse.gmf.runtime.common.core.command.CommandResult; import org.eclipse.gmf.runtime.common.ui.util.DisplayUtils; import org.eclipse.gmf.runtime.diagram.ui.commands.ICommandProxy; import org.eclipse.gmf.runtime.diagram.ui.editparts.IGraphicalEditPart; import org.eclipse.gmf.runtime.diagram.ui.editparts.IResizableCompartmentEditPart; import org.eclipse.gmf.runtime.diagram.ui.services.editpart.EditPartService; import org.eclipse.gmf.runtime.emf.commands.core.command.AbstractTransactionalCommand; import org.eclipse.gmf.runtime.notation.NotationPackage; import org.eclipse.gmf.runtime.notation.Style; import org.eclipse.gmf.runtime.notation.TitleStyle; import org.eclipse.gmf.runtime.notation.View; import org.eclipse.jface.viewers.ITreeContentProvider; import org.eclipse.jface.viewers.Viewer; import org.eclipse.papyrus.uml.diagram.common.Activator; import org.eclipse.papyrus.uml.diagram.common.actions.AbstractShowHideAction; import org.eclipse.papyrus.uml.diagram.common.commands.ShowHideCompartmentRequest; import org.eclipse.papyrus.uml.diagram.common.commands.ShowHideTitleOfCompartmentCommand; import org.eclipse.papyrus.uml.diagram.common.editpolicies.ShowHideCompartmentEditPolicy; import org.eclipse.papyrus.uml.diagram.common.util.CompartmentUtils; import org.eclipse.papyrus.uml.diagram.common.util.DiagramEditPartsUtil; import org.eclipse.papyrus.uml.diagram.common.util.ViewServiceUtil; import org.eclipse.papyrus.uml.diagram.menu.dialogs.ShowHideCompartmentSelectionDialog; import org.eclipse.papyrus.uml.diagram.menu.messages.Messages; import org.eclipse.ui.dialogs.SelectionDialog; /** * * This class provides the Action Show/Hide compartments. * This action allows to choose the compartment to display for each EditPart owning CompartmentEditPart * */ public class ShowHideCompartmentAction extends AbstractShowHideAction { /** the transactional editing domain */ //protected TransactionalEditingDomain domain; /** list of visible titles */ protected List<CompartmentEditPartRepresentation> visibleTitle; /** the list of the visible views after selection in the dialog, to set title visiblity */ protected List<CompartmentEditPartRepresentation> visibleRepresentations; /** * Constructor. */ public ShowHideCompartmentAction() { super(Messages.ShowHideCompartmentAction_Title, Messages.ShowHideCompartmentAction_Messages, ShowHideCompartmentEditPolicy.SHOW_HIDE_COMPARTMENT_POLICY); } /** * Edit part representation used as a main element in the tree */ public class RootEditPartRepresentation extends EditPartRepresentation { /** * Constructor. * @param representedEditPart * the represented EditPart * @param eObject * the semantic element represented by EditPartRepresentation */ public RootEditPartRepresentation(IGraphicalEditPart representedEditPart, EObject eObject) { super(representedEditPart, eObject); } /** * {@inheritDoc} */ @Override protected void initRepresentation() { super.initRepresentation(); List<View> compartmentViews = CompartmentUtils.getAllCompartments(getRepresentedEditPart(), false); List<View> visibleCompartments = CompartmentUtils.getAllVisibleCompartments(getRepresentedEditPart(), false); for(View currentView : compartmentViews) { CompartmentEditPartRepresentation representation = new CompartmentEditPartRepresentation(null, currentView, getSemanticElement(), this); elementsToSelect.add(representation); if(visibleCompartments.contains(currentView)) { initialSelection.add(representation); } } } } /** * Edit Part Representation for the compartments. * Warning: if the compartment notation view is not visible, the edit part is not created. So we need to manipulate the view, not the edit part in * this representation */ public class CompartmentEditPartRepresentation extends EditPartRepresentation { /** boolean that indicates if the title should be visible or not */ private boolean isTitleVisible; /** notation view of the compartment */ final private View compartmentView; /** * Constructor. * * @param representedEditPart * the represented EditPart. this can be <code>null</code> if the compartment is not visible when the dialog is opened * @param compartmentView * notation view for this compartment. this should never be <code>null</code>. * @param eObject * the semantic element represented by EditPartRepresentation * @param parentRepresentation * parent representation of this edit part representation */ public CompartmentEditPartRepresentation(IResizableCompartmentEditPart representedEditPart, View compartmentView, EObject eObject, EditPartRepresentation parentRepresentation) { super(representedEditPart, eObject, parentRepresentation); isTitleVisible = CompartmentUtils.isCompartmentTitleVisible(compartmentView); this.compartmentView = compartmentView; assert compartmentView != null : "The compartment view should not be null"; } /** * {@inheritDoc} */ @Override public IResizableCompartmentEditPart getRepresentedEditPart() { return (IResizableCompartmentEditPart)super.getRepresentedEditPart(); } /** * * @return <code>true</code> if the title of the compartment is displayed * and <code>false</code> if not */ public boolean isTitleVisible() { return isTitleVisible; } /** * {@inheritDoc} */ @Override public String getLabel() { if(getRepresentedEditPart() != null) { return getRepresentedEditPart().getCompartmentName(); } else { EditPart dummyEP = EditPartService.getInstance().createGraphicEditPart(getCompartmentView()); if(dummyEP instanceof IResizableCompartmentEditPart) { return ((IResizableCompartmentEditPart)dummyEP).getCompartmentName(); } } return getEditorLabelProvider().getText(getCompartmentView()); } /** * Sets the visibility of the title of the compartment * * @param value * the value to set */ public void setTitleVisible(boolean value) { isTitleVisible = value; } /** * Returns the view associated to the compartment * * @return the view associated to the compartment */ public View getCompartmentView() { return compartmentView; } } // /** // * {@inheritDoc} // */ // @Override // protected void buildInitialSelection() { // this.initialSelection = new ArrayList<Object>(); // rep = new ArrayList<CompartmentEditPartRepresentation>(); // visibleTitle = new ArrayList<CompartmentEditPartRepresentation>(); // for(EditPart current : this.selectedElements) { // // initialSelection.add(current); // initialSelection.addAll(CompartmentUtils.getAllVisibleCompartments(current, false)); // // initialSelection.addAll(getAllVisibleCompartmentName(current)); // for(View view : CompartmentUtils.getAllCompartments(current, false)) { // CompartmentTitleRepresentation localRep = new CompartmentTitleRepresentation(current, view); // if(localRep.isTitleVisible()) { // // visibleTitle.add(localRep); // } // rep.add(localRep); // } // } // // initialSelection.addAll(visibleTitle); // } /** * * @see org.eclipse.papyrus.diagram.common.actions.AbstractShowHideAction#getSelectionDialog() * * @return */ @Override protected SelectionDialog getSelectionDialog() { ShowHideCompartmentSelectionDialog selectionDialog = new ShowHideCompartmentSelectionDialog(DisplayUtils.getDisplay().getActiveShell(), getEditorLabelProvider(), getContentProvider()); selectionDialog.setTitle(Messages.ShowHideCompartmentAction_Title); selectionDialog.setMessage(Messages.ShowHideCompartmentAction_Messages); selectionDialog.setContainerMode(true); selectionDialog.setInput(getInput()); selectionDialog.setExpandedElements(selectedElements.toArray()); selectionDialog.setInitialElementSelections(getInitialSelection()); // selectionDialog.setTitleRepresentation(rep); return selectionDialog; } /** * * @see org.eclipse.papyrus.diagram.common.actions.AbstractShowHideAction#buildShowHideElementsList(java.lang.Object[]) * * @param results */ @Override protected void buildShowHideElementsList(Object[] results) { super.buildShowHideElementsList(results); List<Object> result = new ArrayList<Object>(); //we remove the EditPart from the result for(int i = 0; i < results.length; i++) { if(results[i] instanceof EditPart) { continue; } else { result.add(results[i]); } } //we are looking for the object to show for(Object node : result) { if(initialSelection.contains(node)) { //we do nothing continue; } else if(node instanceof EditPartRepresentation) { viewsToCreate.add((EditPartRepresentation)node); } } //we are looking for the view to destroy for(Object current : this.initialSelection) { if(!result.contains(current) && (current instanceof EditPartRepresentation)) { viewsToDestroy.add((EditPartRepresentation)current); } } // we are looking for visible elements, to set the shown title or hidden title for(Object node : result) { if(node instanceof CompartmentEditPartRepresentation) { visibleRepresentations.add((CompartmentEditPartRepresentation)node); } } } // @Override // public void run(IAction action) { // initAction(); // super.run(action); // } /** * {@inheritDoc} */ @Override protected void initAction() { super.initAction(); visibleRepresentations = new ArrayList<CompartmentEditPartRepresentation>(); for(IGraphicalEditPart current : this.selectedElements) { if(((View)current.getModel()).getElement() != null) { this.representations.add(new RootEditPartRepresentation(current, ((View)current.getModel()).getElement())); } } setContentProvider(new ContentProvider()); // setEditorLabelProvider(new EditorLabelProvider()); // this.domain = ((IGraphicalEditPart)this.selectedElements.get(0)).getEditingDomain(); // this.initialSelection = getInitialSelection(); } /** * {@inheritDoc} */ @Override protected List<Object> getInput() { return new ArrayList<Object>(representations); } /** * {@inheritDoc} */ @Override protected Command getActionCommand() { /* for further information, see bug 302555 */ ViewServiceUtil.forceLoad(); ShowHideCompartmentRequest req = null; CompoundCommand completeCmd = new CompoundCommand("Destroy and Create Compartment Command"); //$NON-NLS-1$ //the commands to hide compartment for(EditPartRepresentation current : this.viewsToDestroy) { if(current instanceof CompartmentEditPartRepresentation) { CompartmentEditPartRepresentation currentRepresentation = (CompartmentEditPartRepresentation)current; View currentView = currentRepresentation.getCompartmentView(); EditPart currentEditPart = currentRepresentation.getRepresentedEditPart(); // should not be null, because a view to delete should be visible, and so have an existing associated edit part. // if null, try to find it using gmf methods from the view if(currentEditPart == null) { Activator.log.debug("Warning! An edit part representation wished to destroy a view, but no edit part exists currently!" + current); currentEditPart = DiagramEditPartsUtil.getEditPartFromView(currentView, selectedElements.get(0)).getParent(); } if(currentEditPart != null) { req = new ShowHideCompartmentRequest(ShowHideCompartmentRequest.HIDE, currentView); req.setType(ShowHideCompartmentRequest.SHOW_HIDE_COMPARTMENT); Command tmp = currentEditPart.getCommand(req); if(tmp != null && tmp.canExecute()) { completeCmd.add(tmp); } } else { Activator.log.debug("Impossible to find an edit part for the given representation: " + current); } } // if(current instanceof View) { // EditPart ep = DiagramEditPartsUtil.getEditPartFromView((View)current, selectedElements.get(0)).getParent(); // req = new ShowHideCompartmentRequest(ShowHideCompartmentRequest.HIDE, ((View)current).getType()); // req.setType(ShowHideCompartmentRequest.SHOW_HIDE_COMPARTMENT); // Command tmp = ep.getCommand(req); // if(tmp != null && tmp.canExecute()) { // completeCmd.add(tmp); // } // } else if(current instanceof CompartmentTitleRepresentation) { // ShowHideTitleOfCompartmentCommand tmp = new ShowHideTitleOfCompartmentCommand(this.domain, (View)((CompartmentTitleRepresentation)current).getRealObject(), false); // if(tmp != null && tmp.canExecute()) { // completeCmd.add(new ICommandProxy(tmp)); // } // } } //the command to show compartment for(EditPartRepresentation current : this.viewsToCreate) { if(current instanceof CompartmentEditPartRepresentation) { CompartmentEditPartRepresentation currentRepresentation = (CompartmentEditPartRepresentation)current; View currentView = currentRepresentation.getCompartmentView(); EditPartRepresentation parentRepresentation = currentRepresentation.getParentRepresentation(); IGraphicalEditPart parentEditPart = parentRepresentation.getRepresentedEditPart(); if(currentView != null && parentEditPart != null) { req = new ShowHideCompartmentRequest(ShowHideCompartmentRequest.SHOW, currentView); req.setType(ShowHideCompartmentRequest.SHOW_HIDE_COMPARTMENT); Command tmp = parentEditPart.getCommand(req); if(tmp != null && tmp.canExecute()) { completeCmd.add(tmp); } } } // if(current instanceof View) { // EditPart ep = CompartmentUtils.getCompartmentTitleRepresentation(rep, (View)current).getParent(); // req = new ShowHideCompartmentRequest(ShowHideCompartmentRequest.SHOW, ((View)current).getType()); // req.setType(ShowHideCompartmentRequest.SHOW_HIDE_COMPARTMENT); // Command tmp = ep.getCommand(req); // if(tmp != null && tmp.canExecute()) { // completeCmd.add(tmp); // } // } else if(current instanceof CompartmentTitleRepresentation) { // CompartmentTitleRepresentation compartmentTitleRep = (CompartmentTitleRepresentation)current; // final View view = (View)compartmentTitleRep.getRealObject(); // Style style = view.getStyle(NotationPackage.eINSTANCE.getTitleStyle()); // if(style == null) { // // style is not existing yet (true for models created with Papyrus 0.7.x) => create now // // See bug 351084 // completeCmd.add(new ICommandProxy(new AbstractTransactionalCommand(domain, "Create title style", Collections.EMPTY_LIST) { //$NON-NLS-1$ // // public CommandResult doExecuteWithResult(IProgressMonitor dummy, IAdaptable info) { // TitleStyle style = (TitleStyle)view.createStyle(NotationPackage.eINSTANCE.getTitleStyle()); // style.setShowTitle(false); // return CommandResult.newOKCommandResult(); // } // })); // } // ShowHideTitleOfCompartmentCommand tmp = new ShowHideTitleOfCompartmentCommand(this.domain, view, true); // if(tmp != null && tmp.canExecute()) { // completeCmd.add(new ICommandProxy(tmp)); // } // } } // now sets the visibility for all shown views for(CompartmentEditPartRepresentation currentRepresentation : visibleRepresentations) { final View currentView = currentRepresentation.getCompartmentView(); boolean newVisibility = currentRepresentation.isTitleVisible(); boolean oldVisibility = CompartmentUtils.isCompartmentTitleVisible(currentView); IGraphicalEditPart parentEditPart = currentRepresentation.getParentRepresentation().getRepresentedEditPart(); final TransactionalEditingDomain domain = parentEditPart.getEditingDomain(); // visibility has changed => change the model if(newVisibility != oldVisibility) { Style style = currentView.getStyle(NotationPackage.eINSTANCE.getTitleStyle()); if(style == null) { // style is not existing yet (true for models created with Papyrus 0.7.x) => create now // See bug 351084 completeCmd.add(new ICommandProxy(new AbstractTransactionalCommand(domain, "Create title style", Collections.EMPTY_LIST) { //$NON-NLS-1$ @Override public CommandResult doExecuteWithResult(IProgressMonitor dummy, IAdaptable info) { TitleStyle style = (TitleStyle)currentView.createStyle(NotationPackage.eINSTANCE.getTitleStyle()); style.setShowTitle(false); return CommandResult.newOKCommandResult(); } })); } ShowHideTitleOfCompartmentCommand tmp = new ShowHideTitleOfCompartmentCommand(domain, currentView, newVisibility); if(tmp != null && tmp.canExecute()) { completeCmd.add(new ICommandProxy(tmp)); } } } return completeCmd; } /** * Provide the element to fill the tree */ protected class ContentProvider implements ITreeContentProvider { /** * {@inheritDoc} */ public void dispose() { //nothing to do } /** * {@inheritDoc} */ public void inputChanged(Viewer viewer, Object oldInput, Object newInput) { //nothing to do } /** * {@inheritDoc} */ public Object[] getElements(Object inputElement) { if(inputElement instanceof List) { return ((List<?>)inputElement).toArray(); } return new Object[0]; } /** * {@inheritDoc} */ public Object[] getChildren(Object parentElement) { if(parentElement instanceof EditPartRepresentation) { return ((EditPartRepresentation)parentElement).getPossibleElement().toArray(); } return new Object[0]; } /** * {@inheritDoc} */ public Object getParent(Object element) { if(element instanceof EditPartRepresentation) { EditPartRepresentation editPartRepresentation = (EditPartRepresentation)element; return editPartRepresentation.getParentRepresentation(); } return null; } /** * {@inheritDoc} */ public boolean hasChildren(Object element) { Object[] children = getChildren(element); return children != null && children.length != 0; } } }