/***************************************************************************** * Copyright (c) 2009 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: * Patrick Tessier (CEA LIST) Patrick.tessier@cea.fr - Initial API and implementation * *****************************************************************************/ package org.eclipse.papyrus.uml.diagram.common.editpolicies; import java.util.ArrayList; import java.util.List; import org.eclipse.emf.common.notify.Notification; import org.eclipse.emf.ecore.EAnnotation; import org.eclipse.emf.ecore.EObject; import org.eclipse.emf.ecore.EReference; import org.eclipse.emf.transaction.TransactionalEditingDomain; import org.eclipse.gef.editpolicies.GraphicalEditPolicy; import org.eclipse.gmf.runtime.diagram.core.listener.DiagramEventBroker; import org.eclipse.gmf.runtime.diagram.core.listener.NotificationListener; import org.eclipse.gmf.runtime.diagram.ui.editparts.IGraphicalEditPart; import org.eclipse.gmf.runtime.notation.View; import org.eclipse.papyrus.infra.core.listenerservice.IPapyrusListener; import org.eclipse.papyrus.infra.emf.appearance.helper.QualifiedNameHelper; import org.eclipse.papyrus.infra.gmfdiag.common.editpart.IPapyrusEditPart; import org.eclipse.papyrus.uml.diagram.common.figure.node.IPapyrusNodeNamedElementFigure; import org.eclipse.papyrus.uml.diagram.common.figure.node.NodeNamedElementFigure; import org.eclipse.uml2.uml.NamedElement; import org.eclipse.uml2.uml.UMLPackage; /** * this edit policy has in charge to display the qualified name of an element. * To display it, the editpart must be a {@link IPapyrusEditPart} and the * associated figure has to be a {@link NodeNamedElementFigure} */ public class QualifiedNameDisplayEditPolicy extends GraphicalEditPolicy implements NotificationListener, IPapyrusListener { /** key for this edit policy */ public final static String QUALIFIED_NAME_POLICY = "Qualified_name_editpolicy"; /** host semantic element */ protected NamedElement hostSemanticNamedElement; /** * The parent listeners list */ protected List<Object> parentListeners; /** * Creates a new QualifiedNameDisplayEditPolicy */ public QualifiedNameDisplayEditPolicy() { super(); } /** * * {@inheritDoc} */ public void activate() { // retrieve the view and the element managed by the edit part View view = (View)getHost().getModel(); if(view == null) { return; } hostSemanticNamedElement = getNamedElement(); if(hostSemanticNamedElement != null) { // adds a listener on the view and the element controlled by the // editpart getDiagramEventBroker().addNotificationListener(view, this); if(hostSemanticNamedElement == null) { return; } getDiagramEventBroker().addNotificationListener(hostSemanticNamedElement, this); refreshQualifiedNameDisplay(); } addParentListeners(); } /** * refresh the qualified name */ protected void refreshQualifiedNameDisplay() { if(getHost() instanceof IPapyrusEditPart) { if(((IPapyrusEditPart)getHost()).getPrimaryShape() instanceof NodeNamedElementFigure) { NodeNamedElementFigure nodeNamedElementFigure = (NodeNamedElementFigure)((IPapyrusEditPart)getHost()).getPrimaryShape(); refreshQualifiedNameDepth(nodeNamedElementFigure); refreshQualifiedName(nodeNamedElementFigure); } } } /** * set the qualified name to display * * @param nodeNamedElementFigure * the associated figure to the editpart */ protected void refreshQualifiedName(IPapyrusNodeNamedElementFigure nodeNamedElementFigure) { nodeNamedElementFigure.setQualifiedName(hostSemanticNamedElement.getQualifiedName()); } /** * refresh the editpart with a depth for the qualified name * * @param nodeNamedElementFigure * the associated figure to the editpart */ protected void refreshQualifiedNameDepth(NodeNamedElementFigure nodeNamedElementFigure) { nodeNamedElementFigure.setDepth(QualifiedNameHelper.getQualifiedNameDepth((View)getHost().getModel())); } /** * * {@inheritDoc} */ public void deactivate() { // retrieve the view and the element managed by the edit part View view = (View)getHost().getModel(); if(view == null) { return; } if(hostSemanticNamedElement != null) { // remove notification on element and view getDiagramEventBroker().removeNotificationListener(view, this); getDiagramEventBroker().removeNotificationListener(hostSemanticNamedElement, this); } // removes the reference to the semantic element hostSemanticNamedElement = null; removeParentListeners(); } /** * * @return the associated named element to the editpart. it can return null * if this not a named element */ protected NamedElement getNamedElement() { View view = (View)getHost().getModel(); if(view == null) { return null; } if(view.getElement() != null && view.getElement() instanceof NamedElement) { return (NamedElement)view.getElement(); } return null; } /** * Gets the diagram event broker from the editing domain. * * @return the diagram event broker */ protected DiagramEventBroker getDiagramEventBroker() { TransactionalEditingDomain theEditingDomain = ((IGraphicalEditPart)getHost()).getEditingDomain(); if(theEditingDomain != null) { return DiagramEventBroker.getInstance(theEditingDomain); } return null; } /** * * {@inheritDoc} */ public void notifyChanged(Notification notification) { if(UMLPackage.eINSTANCE.getNamedElement_Name().equals(notification.getFeatureID(NamedElement.class)) || notification.getNotifier() instanceof EAnnotation) { refreshQualifiedNameDisplay(); } else if(UMLPackage.eINSTANCE.getNamedElement_Name().equals(notification.getFeature())) { if(parentListeners.contains(notification.getNotifier()) || getNamedElement().equals(notification.getNotifier())) { refreshQualifiedNameDisplay(); } } else if(notification.getFeature() instanceof EReference) { EReference ref = (EReference)notification.getFeature(); if(ref.isContainment()) { if(parentListeners.contains(notification.getNotifier())) removeParentListeners(); addParentListeners(); refreshQualifiedNameDisplay(); } } } /** * Add listeners for all parents */ private void addParentListeners() { DiagramEventBroker diagramEventBroker = getDiagramEventBroker(); if(diagramEventBroker != null) { if(parentListeners == null) { parentListeners = new ArrayList<Object>(); } if(getNamedElement() != null) { EObject parentEOBject = getNamedElement().eContainer(); while(parentEOBject != null) { diagramEventBroker.addNotificationListener(parentEOBject, this); parentListeners.add(parentEOBject); parentEOBject = parentEOBject.eContainer(); } } } } /** * Remove all parents listeners */ public void removeParentListeners() { for(Object listener : parentListeners) { getDiagramEventBroker().removeNotificationListener((EObject)listener, this); } } }