Skip to main content


Eclipse Community Forums
Forum Search:

Search      Help    Register    Login    Home
Home » Modeling » Graphiti » How to replace or remove the diagram's root object
How to replace or remove the diagram's root object [message #1785864] Sat, 21 April 2018 00:22 Go to next message
David G. is currently offline David G.Friend
Messages: 9
Registered: April 2015
Location: Madrid, Spain
Junior Member
I'm trying to replace the diagram's root object (the eObject associated with my diagram, it contains every other eObject).

I have a feature where I create multiple clones of my root object (Graph class) and do some calculations on them. Then I can choose one of the clones and I want to replace it in my diagram.

I've been trying to do this, but the contained objects seem to be left behind, and I'm getting errors on save due to unreferenced elements (I guess I'm removing the root element, but not the child elements):

	public static void setRootGraph(Diagram diagram, Graph graph) {

		PictogramLink link = diagram.getLink();

		if (link == null) {

			// Create the pictogram link object
			link = PictogramsFactory.eINSTANCE.createPictogramLink();
		}

		EditingDomain editingDomain = AdapterFactoryEditingDomain.getEditingDomainFor(diagram);
		Command command;

		// Remove the Graph from the diagram resource
		command = new RemoveCommand(editingDomain, diagram.eResource().getContents(), link.getBusinessObjects());
		editingDomain.getCommandStack().execute(command);

		// Add the Graph to the diagram resource
		link.getBusinessObjects().clear();
		link.getBusinessObjects().add(graph);

		command = new AddCommand(editingDomain, diagram.eResource().getContents(), graph);
		editingDomain.getCommandStack().execute(command);

		// Set the pictogram link object for the diagram object
		command = new SetCommand(editingDomain, diagram,
				PictogramsPackage.eINSTANCE.getDiagram().getEStructuralFeature(PictogramsPackage.DIAGRAM__LINK), link);
		editingDomain.getCommandStack().execute(command);
	}


Any tip on how to accomplish this?

Thanks!
Re: How to replace or remove the diagram's root object [message #1785922 is a reply to message #1785864] Mon, 23 April 2018 07:36 Go to previous messageGo to next message
Michael Wenz is currently offline Michael WenzFriend
Messages: 1899
Registered: July 2009
Location: Walldorf, Germany
Senior Member
David,

not sure, especially as you do not provide details on the left over contained objects. From a first glance it could be that it is the PictogramLink object you create that's causing this. You just create it and set it to the diagramLink association of the diagram. I think you would also need to add the new object to the EMF resource (probably you diagram file) to make that work.

Michael
Re: How to replace or remove the diagram's root object [message #1785993 is a reply to message #1785922] Mon, 23 April 2018 23:34 Go to previous messageGo to next message
David G. is currently offline David G.Friend
Messages: 9
Registered: April 2015
Location: Madrid, Spain
Junior Member
Thanks for the feedback!
I've gone back and tried doing it in a custom feature, but the result is simmilar...

This is the execute method of the custom feature:
	@Override
	public void execute(ICustomContext context) {

		hasDoneChanges = true;

		// Access the graph
		Graph theGraph = GraphUtil.getRootGraph(getDiagram());

		// Add every node from the new graph
		theGraph.getNodes().clear();
		theGraph.getNodes().addAll(newGraph.getNodes());

		// Add every edge from the new graph
		theGraph.getEdges().clear();
		theGraph.getEdges().addAll(newGraph.getEdges());

		// Model is modified now, with new or different edges
		updateAllEdges();
		updateGraph(theGraph);

	}


The feature runs ok, but when I try to save the diagram I get this:

Quote:

org.eclipse.emf.ecore.resource.Resource$IOWrappedException: The object 'graphdom.impl.EdgeImpl@360a3106 (marked: false, guid: null, weight: 0)' is not contained in a resource.
at org.eclipse.emf.ecore.xmi.impl.XMLSaveImpl.endSave(XMLSaveImpl.java:301)
at org.eclipse.emf.ecore.xmi.impl.XMLSaveImpl.save(XMLSaveImpl.java:265)
at org.eclipse.emf.ecore.xmi.impl.XMLResourceImpl.doSave(XMLResourceImpl.java:389)
at org.eclipse.emf.ecore.resource.impl.ResourceImpl.save(ResourceImpl.java:1430)
at org.eclipse.emf.ecore.resource.impl.ResourceImpl.saveOnlyIfChangedWithMemoryBuffer(ResourceImpl.java:1144)
at org.eclipse.emf.ecore.resource.impl.ResourceImpl.save(ResourceImpl.java:985)
at org.eclipse.graphiti.ui.editor.DefaultPersistencyBehavior$1$1.run(DefaultPersistencyBehavior.java:342)
at org.eclipse.emf.transaction.impl.TransactionalEditingDomainImpl.runExclusive(TransactionalEditingDomainImpl.java:328)
at org.eclipse.graphiti.ui.editor.DefaultPersistencyBehavior$1.run(DefaultPersistencyBehavior.java:353)
at org.eclipse.core.internal.resources.Workspace.run(Workspace.java:2240)
at org.eclipse.core.internal.resources.Workspace.run(Workspace.java:2262)
at org.eclipse.graphiti.ui.editor.DefaultPersistencyBehavior.save(DefaultPersistencyBehavior.java:360)
at org.eclipse.graphiti.ui.editor.DefaultPersistencyBehavior$SaveOperation.run(DefaultPersistencyBehavior.java:470)
at org.eclipse.jface.operation.ModalContext$ModalContextThread.run(ModalContext.java:119)
Caused by: org.eclipse.emf.ecore.xmi.DanglingHREFException: The object 'graphdom.impl.EdgeImpl@360a3106 (marked: false, guid: null, weight: 0)' is not contained in a resource.
at org.eclipse.emf.ecore.xmi.impl.XMLHelperImpl.handleDanglingHREF(XMLHelperImpl.java:754)
at org.eclipse.emf.ecore.xmi.impl.XMLHelperImpl.getURIFragment(XMLHelperImpl.java:725)
at org.eclipse.emf.ecore.xmi.impl.XMLHelperImpl.getIDREF(XMLHelperImpl.java:747)
at org.eclipse.emf.ecore.xmi.impl.XMLSaveImpl.saveIDRefMany(XMLSaveImpl.java:2023)
at org.eclipse.emf.ecore.xmi.impl.XMLSaveImpl.saveFeatures(XMLSaveImpl.java:1370)
at org.eclipse.emf.ecore.xmi.impl.XMLSaveImpl.saveFeatures(XMLSaveImpl.java:1224)
at org.eclipse.emf.ecore.xmi.impl.XMLSaveImpl.saveElementID(XMLSaveImpl.java:2716)


It seems like the previous Edges are not really being removed from the model when I clear the list of their containing EObject...

As I write this, I tried again wtih EcoreUtil.deleteAll and it seemed to work, but now I realize that, even if the EObject gets updated, the diagram doesn't seem to notice, as the graphical representations are not affected...

Is there some quick way in Graphiti, to remove each EObject from these lists and their associated pictogram elements? Maybe instead of dealing with EObjects I should be trying to call delete and add features for each of the objects? :-m

[Updated on: Mon, 23 April 2018 23:35]

Report message to a moderator

Re: How to replace or remove the diagram's root object [message #1786068 is a reply to message #1785993] Wed, 25 April 2018 07:14 Go to previous messageGo to next message
Michael Wenz is currently offline Michael WenzFriend
Messages: 1899
Registered: July 2009
Location: Walldorf, Germany
Senior Member
David,

the call to EcoreUtil.deleteAll is definitely the way to use for the domain objects, otherwise they will only be removed from the list of references and stay around without parent.

Regarding the Graphiti objects, there is a refresh method on the DiagramEditor class but that will probably not help unless you auto refresh on. In that case it might (if the object linking between shape and domain object is correct) remove the graphical representation. Otherwise you would have to loop over your domain objects and collect all root shapes to delete. You could then trigger their deletion also via the EcoreUtil.deleteAll call, but depending on your graphical representation you might need to delete more. The cleaner way would indeed be to trigger either the remove feature for each of the objects and then delete the domain objects or trigger the delete feature for each object right away.

Michael
Re: How to replace or remove the diagram's root object [message #1786207 is a reply to message #1786068] Thu, 26 April 2018 22:47 Go to previous message
David G. is currently offline David G.Friend
Messages: 9
Registered: April 2015
Location: Madrid, Spain
Junior Member
Thanks for your guidance! :-)

Finally I got it through: First iterating over the domain objects in the collections and invoking the delete feature and then iterating over the new objects and triggering the add feature.

The most tricky parts were:
* Instantiating the DeleteContext, as I had to 'traverse' from the domain object to the pictogram element to instantiate it with the constructor (it needs the PE, can't work with the object). Also I had to 'tune' the MultiDeleteInfo to prevent multiple Yes/No popups.
* Instantiating the AddContext (and AddConnectionContext, which are different), as I had to programmatically set the target container or the objects would be 'lost' without a parent.

Also, I had to 'clone' the domain objects (really I EcoreUtil.clone'd the whole parent object) before adding them to the 'active' one, as when I added them to the active object they would get removed from the other one (preventing me from switching them back and forth). I guess this has to do with my model and EMF enforcing that the objects have a single parent, but was unknown for me (I'm an EMF newbie after all :-))

A few snippets, should it be handy for someone:

The delete part (inside a loop in my code):
			Node node = theGraph.getNodes().get(i);
			PictogramElement pictogramElement = Graphiti.getLinkService().getPictogramElements(diagram, node)
					.get(0);
			DeleteContext delContext = new DeleteContext(pictogramElement);
			delContext.setMultiDeleteInfo(new MultiDeleteInfo(false, false, 0));
			getFeatureProvider().getDeleteFeature(delContext).execute(delContext);

The add part (in a loop as well):
			Node node = newGraph.getNodes().get(i);
			theGraph.getNodes().add(node);
			AddContext addContext = new AddContext();
			addContext.setNewObject(node);
			addContext.setLocation(node.getXCoord(), node.getYCoord());
			addContext.setTargetContainer(diagram);
			getFeatureProvider().getAddFeature(addContext).add(addContext);

Previous Topic:Multi Level Diagram
Next Topic:Double Post
Goto Forum:
  


Current Time: Sat Nov 17 21:24:24 GMT 2018

Powered by FUDForum. Page generated in 0.03037 seconds
.:: Contact :: Home ::.

Powered by: FUDforum 3.0.2.
Copyright ©2001-2010 FUDforum Bulletin Board Software

Back to the top