// $Id: UMLUtil.java 18220 2010-04-08 20:37:15Z tfmorris $ /******************************************************************************* * Copyright (c) 2007,2010 Bogdan Pistol and other contributors * 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: * Bogdan Pistol - initial API and implementation *******************************************************************************/ package org.argouml.model.euml; import org.eclipse.emf.common.command.Command; import org.eclipse.emf.common.command.StrictCompoundCommand; import org.eclipse.emf.common.util.EList; import org.eclipse.emf.common.util.URI; import org.eclipse.emf.ecore.resource.Resource; import org.eclipse.emf.edit.command.CopyToClipboardCommand; import org.eclipse.emf.edit.command.PasteFromClipboardCommand; import org.eclipse.uml2.uml.Association; import org.eclipse.uml2.uml.AssociationClass; import org.eclipse.uml2.uml.Element; import org.eclipse.uml2.uml.NamedElement; import org.eclipse.uml2.uml.Operation; import org.eclipse.uml2.uml.Property; import org.eclipse.uml2.uml.Type; /** * This class exposes protected methods from * {@link org.eclipse.uml2.uml.UMLUtil} and adds additional util methods * * @author Bogdan Pistol */ public class UMLUtil extends org.eclipse.uml2.uml.util.UMLUtil { /** * The default URI used for eUML */ public static final URI DEFAULT_URI = URI.createURI("http://argouml.tigris.org/euml/resource/default_uri.xmi"); //$NON-NLS-1$ /** * Getter for the attributes of a Type * * @param type * The Type that owns the attributes * @return the attributes or null */ public static EList<Property> getOwnedAttributes(Type type) { if (type instanceof AssociationClass) { return ((AssociationClass) type).getOwnedAttributes(); } else if (type instanceof Association) { return ((Association) type).getOwnedEnds(); } else { return org.eclipse.uml2.uml.util.UMLUtil.getOwnedAttributes(type); } } /** * Getter for the operations of a Type * * @param type * The Type that owns the operations * @return the operations or null */ public static EList<Operation> getOwnedOperations(Type type) { return org.eclipse.uml2.uml.util.UMLUtil.getOwnedOperations(type); } /** * Copy a tree of UML elements into a destination location * * @param modelImplementation * the eUML model implementation * @param source * the tree of UML elements to be copied * @param destination * the destination container * @return the root of the newly copied tree of UML elements or null */ public static Element copy(EUMLModelImplementation modelImplementation, Element source, Element destination) { Command copyToClipboard = CopyToClipboardCommand.create( modelImplementation.getEditingDomain(), source); Command pasteFromClipboard = PasteFromClipboardCommand.create( modelImplementation.getEditingDomain(), destination, null); StrictCompoundCommand copyCommand = new StrictCompoundCommand() { { isPessimistic = true; } }; copyCommand.append(copyToClipboard); copyCommand.append(pasteFromClipboard); copyCommand.setLabel("Copy a tree of UML elements to a destination"); //$NON-NLS-1$ if (copyCommand.canExecute()) { modelImplementation.getModelEventPump().getRootContainer().setHoldEvents( true); modelImplementation.getEditingDomain().getCommandStack().execute( copyCommand); if (modelImplementation.getEditingDomain().getCommandStack().getMostRecentCommand().getAffectedObjects().size() == 1) { modelImplementation.getModelEventPump().getRootContainer().setHoldEvents( false); return (Element) modelImplementation.getEditingDomain().getCommandStack().getMostRecentCommand().getAffectedObjects().iterator().next(); } else { modelImplementation.getEditingDomain().getCommandStack().undo(); modelImplementation.getModelEventPump().getRootContainer().clearHeldEvents(); modelImplementation.getModelEventPump().getRootContainer().setHoldEvents( false); } } return null; } /** * Returns information about an Object. * <p> * If it's an Element it returns its metaclass name, and if it's a * NamedElement it appends its name. * * @param o * The object * @return the String description */ public static String toString(Object o) { if (o == null) { return "null"; //$NON-NLS-1$ } if (!(o instanceof Element)) { return o.toString(); } StringBuilder sb = new StringBuilder("'"); //$NON-NLS-1$ boolean named = false; if (o instanceof NamedElement && ((NamedElement) o).getName() != null && !((NamedElement) o).getName().equals("")) { //$NON-NLS-1$ named = true; sb.append(((NamedElement) o).getName() + " ["); //$NON-NLS-1$ } sb.append(((Element) o).eClass().getName()); if (named) { sb.append("]"); //$NON-NLS-1$ } sb.append("'"); //$NON-NLS-1$ return sb.toString(); } /** * Returns the Resource associated with an URI or creates the resource if it * does not exist * * @param modelImplementation * the eUML implementation * @param uri * the URI which identifies the resource * @return the retrieved or created resource */ static Resource getResource( EUMLModelImplementation modelImplementation, URI uri, boolean readOnly) { if (!"xmi".equals(uri.fileExtension())) { //$NON-NLS-1$ // Make sure we have a recognized file extension uri = uri.appendFileExtension("xmi"); //$NON-NLS-1$ } Resource r = modelImplementation.getEditingDomain().getResourceSet() .getResource(uri, false); if (r == null) { r = modelImplementation.getEditingDomain().getResourceSet() .createResource(uri); } if (r == null) { throw new NullPointerException("Failed to create resource for URI " //$NON-NLS-1$ + uri); } modelImplementation.getReadOnlyMap().put(r, Boolean.valueOf(readOnly)); return r; } @SuppressWarnings("unchecked") static void checkArgs(Object[] args, Class[] types) { if (args.length != types.length) { throw new IllegalArgumentException( "Mismatched array lengths for args and types"); //$NON-NLS-1$ } for (int i = 0; i < args.length; i++) { if (!types[i].isAssignableFrom(args[i].getClass())) { throw new IllegalArgumentException( "Parameter " + i + " must be of type " + types[i]); //$NON-NLS-1$//$NON-NLS-2$ } } } }