Eclipse Community Forums
Forum Search:

Search      Help    Register    Login    Home
Home » Modeling » EMF » [EMF] Inter-model Inheritance viewer in EMF editor
[EMF] Inter-model Inheritance viewer in EMF editor [message #656531] Sat, 26 February 2011 11:39 Go to next message
Christian  is currently offline Christian Friend
Messages: 14
Registered: February 2011
Junior Member
Hi there,

In my UML-like editor i have a MClass which can inherit a from another MClass.

Lets say i created two models with my editor: classes_base.mymodel and classes_localized_DE.mymodel.
MClass "ObjectBase" in classes_base.mymodel inherits from MClass "ObjectLocalized" in classes_localized_DE.mymodel.
When i open classes_localized_DE.mymodel in the EMF editor I want to show an inter-model inheritance tree view of the model.
I want the tree to show both "ObjectLocalized" and "ObjectBase" Elements although the latter isn't part of classes_localized_DE.mymodel. The tree should show their inheritance relation like this:

  • MClass ObjectBase
    • MClass ObjectLocalized
        # MAttribute AttributeBase1
        # MAttribute AttributeBase2
        # MAttribute AttributeLocalized1

Elements from a different model are shown cursively.
Furthermore, because "ObjectLocalized" has an inheritance reference to "ObectBase" in classes_base.mymodel, the viewer should list ALL MClasses from classes_base.mymodel.

I already wrote the code to fetch me the given classes, attributes etc to realise the described behaviour. But I am not sure where to put it.

The EMF editor generated by the .genmodel config file has a MyModelEditor.java which creates different viewers of the model like tree viewer, list viewer, etc. There I added an inheritance viewer with a custom InheritanceAdapterFactoryContentProvider. That provider overrides the getElements(), getChildren(), .. methods to not return the "physical" children, but the modeled/inherited children.
Unfortunately, when i do this, it has some strange sideeffects like changing the other viewers. The inheritance viewer shows the desired view, but when I switch the the selection viewer, suddenly all MClasses are attached to classes_localized_DE.mymodel.

Could you help me out on this matter?

Additionally i would like to add an extension to get an "add Subclass" option in the right-click menu of my inheritance viewer.

Cheers,
Christian
Re: [EMF] Inter-model Inheritance viewer in EMF editor [message #656554 is a reply to message #656531] Sat, 26 February 2011 17:49 Go to previous messageGo to next message
Ed Merks is currently offline Ed MerksFriend
Messages: 26217
Registered: July 2009
Senior Member
Christian,

Comments below.

Christian wrote:
> Hi there,
>
> In my UML-like editor i have a MClass which can inherit a from another
> MClass.
>
> Lets say i created two models with my editor: classes_base.mymodel and
> classes_localized_DE.mymodel.
> MClass "ObjectBase" in classes_base.mymodel inherits from MClass
> "ObjectLocalized" in classes_localized_DE.mymodel.
> When i open classes_localized_DE.mymodel in the EMF editor I want to
> show an inter-model inheritance tree view of the model.
> I want the tree to show both "ObjectLocalized" and "ObjectBase"
> Elements although the latter isn't part of
> classes_localized_DE.mymodel. The tree should show their inheritance
> relation like this:
>
> MClass ObjectBase
> MClass ObjectLocalized
> # MAttribute AttributeBase1
> # MAttribute AttributeBase2
> # MAttribute AttributeLocalized1
Is multiple inheritance supported?
>
> Elements from a different model are shown cursively.
> Furthermore, because "ObjectLocalized" has an inheritance reference to
> "ObectBase" in classes_base.mymodel, the viewer should list ALL
> MClasses from classes_base.mymodel.
>
> I already wrote the code to fetch me the given classes, attributes etc
> to realise the described behaviour. But I am not sure where to put it.
It sounds like you want the children for the item provider to show
differently than the default (which shows only containment references).
>
> The EMF editor generated by the .genmodel config file has a
> MyModelEditor.java which creates different viewers of the model like
> tree viewer, list viewer, etc. There I added an inheritance viewer
> with a custom InheritanceAdapterFactoryContentProvider. That provider
> overrides the getElements(), getChildren(), .. methods to not return
> the "physical" children, but the modeled/inherited children.
> Unfortunately, when i do this, it has some strange sideeffects like
> changing the other viewers.
Yes, the item providers are shared. You'd need to specialize ones used
just in the one view if you only want this in just the one view.
> The inheritance viewer shows the desired view, but when I switch the
> the selection viewer, suddenly all MClasses are attached to
> classes_localized_DE.mymodel.
>
> Could you help me out on this matter?
>
> Additionally i would like to add an extension to get an "add Subclass"
> option in the right-click menu of my inheritance viewer.
It sounds like you want to treat this inheritance reference as a
children reference. You'd do that in the GenFeature by turning on
Children and Notification. But then you want this only in one of your
views, so in the end, you don't want those changes in the basic item
provider that's generated but only in a subclass that's used only in the
inheritance view.

What you want is similar to XSDSemanticItemProviderAdapterFactory which
specialized XSDItemProviderAdapterFactory along with many of the
XSDAbcItemProviders to produce a semantic view different from the basic
concrete syntax view. You might look at how the XSDEditor does that.
>
> Cheers,
> Christian
Re: [EMF] Inter-model Inheritance viewer in EMF editor [message #659391 is a reply to message #656531] Sun, 13 March 2011 14:35 Go to previous messageGo to next message
Christian  is currently offline Christian Friend
Messages: 14
Registered: February 2011
Junior Member
Tanks for the reply.

Multiple inheritance is not supported.

I browsed through the XSDSemanticItemProviderAdapterFactory and built my custom XYZAttributeItemProviderAdapterFactory.

I tried to build a view which shows all Attributes (physical and inherited) of a class:
  • MClass ObjectBase
      # MAttribute AttributeBase1
      # MAttribute AttributeBase2
  • MClass ObjectLocalized extends ObjectBase
      # MAttribute AttributeBase1
      # MAttribute AttributeBase2
      # MAttribute AttributeLocalized1

Now here is what i wrote:
public class XYZAttributeItemProviderAdapterFactory extends XYZItemProviderAdapterFactory {

	@Override
	public Adapter createMClassAdapter() {
		mClassItemProvider = new MClassItemProvider(this) {
			protected List<Object> children;

			@Override
			public Collection<? extends EStructuralFeature> getChildrenFeatures(Object object) {
				//return Collections.emptyList();
				if (childrenFeatures == null) {
					super.getChildrenFeatures(object);
					// Testing the getChildrenFeatures() funtionality..
					//childrenFeatures.add(XYZPackage.Literals.MCLASS__ASSOCIATIONS);
					//childrenFeatures.add(XYZPackage.Literals.MCLASS__SUPERCLASS);
					//childrenFeatures.add(XYZPackage.Literals.MCLASS__ATTRIBUTES);
					//childrenFeatures.add(XYZPackage.Literals.MCLASS__CONSTRAINTS);
					//childrenFeatures.remove(XYZPackage.Literals.MCLASS__SUPERCLASS);
				}
				return childrenFeatures;
			}
			
			@Override
			public Collection<?> getChildren(Object object) {
				Collection result = super.getChildren(object);
									
				if (object instanceof MClass) {
					result.addAll(getInheritedAttributes((MClass)object));
	            	}
				
				return (result == null ? Collections.EMPTY_LIST : result);
			}
		}
		return mClassItemProvider;
	}

	private Collection<MAttribute> getInheritedAttributes (MClass mClass) {
		Collection<MAttribute> list = mClass.getAttributes();
		if (mClass.getSuperclass() != null) {
			list.addAll(getInheritedAttributes(mClass.getSuperclass()));
			return list;
		}
		return list;
	}
}

And in XYZEditor:
protected void initializeEditingDomain() {
	// Create an adapter factory that yields item providers.
	//
	adapterFactory = new ComposedAdapterFactory(ComposedAdapterFactory.Descriptor.Registry.INSTANCE);

	adapterFactory.addAdapterFactory(new ResourceItemProviderAdapterFactory());
	adapterFactory.addAdapterFactory(new GeockItemProviderAdapterFactory());
	adapterFactory.addAdapterFactory(new ReflectiveItemProviderAdapterFactory());

	attributeAdapterFactory = new ComposedAdapterFactory(ComposedAdapterFactory.Descriptor.Registry.INSTANCE);
	attributeAdapterFactory.addAdapterFactory(new ResourceItemProviderAdapterFactory());
	attributeAdapterFactory.addAdapterFactory(new GeockAttributeItemProviderAdapterFactory());
	attributeAdapterFactory.addAdapterFactory(new ReflectiveItemProviderAdapterFactory());
	...
}

public void createPages() {
	...
	parentViewer = (TreeViewer)viewerPane.getViewer();
	parentViewer.setContentProvider(new AdapterFactoryContentProvider(attributeAdapterFactory));

	parentViewer.setLabelProvider(new AdapterFactoryLabelProvider(attributeAdapterFactory));
	parentViewer.setInput(editingDomain.getResourceSet());
	parentViewer.setSelection(new StructuredSelection(editingDomain.getResourceSet().getResources().get(0)), true);
	viewerPane.setTitle(editingDomain.getResourceSet());
	
	new AdapterFactoryTreeEditor(parentViewer.getTree(), attributeAdapterFactory);

	createContextMenuFor(parentViewer);
	int pageIndex = addPage(viewerPane.getControl());
	setPageText(pageIndex, getString("_UI_ParentPage_label"));
}

Overriding the getChildren{} method in XYZAttributeItemProviderAdapterFactory seems to be the wrong approach, because when I open the parent View in the running application, only ONE class shows its inherited attributes. The other classes which (physically) contain those attributes are now empty. It appears, as if the last MClass whose getChildren() is called, "steals" its MAttributes from the other classes.

So,
1 - What am i doing wrong? How can i realise my desierd view? Should i do semothing completely different? Like adding a derived Field to the MClass which calculates the inherited Attributes..?
2 - Is there a way to set the Font of specific MAttributes (e.g. write inherited MAttributes gray and cursive in the viewer)

Cheers,
Christian
Re: [EMF] Inter-model Inheritance viewer in EMF editor [message #659396 is a reply to message #659391] Sun, 13 March 2011 15:30 Go to previous messageGo to next message
Ed Merks is currently offline Ed MerksFriend
Messages: 26217
Registered: July 2009
Senior Member
Christian,

Comments below.

Christian wrote:
> Tanks for the reply.
>
> Multiple inheritance is not supported.
>
> I browsed through the XSDSemanticItemProviderAdapterFactory and built
> my custom XYZAttributeItemProviderAdapterFactory.
>
> I tried to build a view which shows all Attributes (physical and
> inherited) of a class:
> MClass ObjectBase
> # MAttribute AttributeBase1
> # MAttribute AttributeBase2
> MClass ObjectLocalized extends ObjectBase
> # MAttribute AttributeBase1
> # MAttribute AttributeBase2
> # MAttribute AttributeLocalized1
> Now here is what i wrote: public class
> XYZAttributeItemProviderAdapterFactory extends
> XYZItemProviderAdapterFactory {
>
> @Override
> public Adapter createMClassAdapter() {
> mClassItemProvider = new MClassItemProvider(this) {
> protected List<Object> children;
>
> @Override
> public Collection<? extends EStructuralFeature>
> getChildrenFeatures(Object object) {
> //return Collections.emptyList();
> if (childrenFeatures == null) {
> super.getChildrenFeatures(object);
> // Testing the getChildrenFeatures() funtionality..
>
> //childrenFeatures.add(XYZPackage.Literals.MCLASS__ASSOCIATI ONS);
>
> //childrenFeatures.add(XYZPackage.Literals.MCLASS__SUPERCLAS S);
>
> //childrenFeatures.add(XYZPackage.Literals.MCLASS__ATTRIBUTE S);
>
> //childrenFeatures.add(XYZPackage.Literals.MCLASS__CONSTRAIN TS);
>
> //childrenFeatures.remove(XYZPackage.Literals.MCLASS__SUPERC LASS);
> }
> return childrenFeatures;
> }
>
> @Override
> public Collection<?> getChildren(Object object) {
> Collection result = super.getChildren(object);
>
> if (object instanceof MClass) {
>
> result.addAll(getInheritedAttributes((MClass)object));
> }
>
> return (result == null ? Collections.EMPTY_LIST :
> result);
> }
> }
> return mClassItemProvider;
> }
>
> private Collection<MAttribute> getInheritedAttributes (MClass
> mClass) {
> Collection<MAttribute> list = mClass.getAttributes();
> if (mClass.getSuperclass() != null) {
> list.addAll(getInheritedAttributes(mClass.getSuperclass()));
> return list;
> }
> return list;
> }
> }
> And in XYZEditor: protected void initializeEditingDomain() {
> // Create an adapter factory that yields item providers.
> //
> adapterFactory = new
> ComposedAdapterFactory(ComposedAdapterFactory.Descriptor.Reg istry.INSTANCE);
>
>
> adapterFactory.addAdapterFactory(new
> ResourceItemProviderAdapterFactory());
> adapterFactory.addAdapterFactory(new
> GeockItemProviderAdapterFactory());
> adapterFactory.addAdapterFactory(new
> ReflectiveItemProviderAdapterFactory());
>
> attributeAdapterFactory = new
> ComposedAdapterFactory(ComposedAdapterFactory.Descriptor.Reg istry.INSTANCE);
>
> attributeAdapterFactory.addAdapterFactory(new
> ResourceItemProviderAdapterFactory());
> attributeAdapterFactory.addAdapterFactory(new
> GeockAttributeItemProviderAdapterFactory());
> attributeAdapterFactory.addAdapterFactory(new
> ReflectiveItemProviderAdapterFactory());
> ...
> }
>
> public void createPages() {
> ...
> parentViewer = (TreeViewer)viewerPane.getViewer();
> parentViewer.setContentProvider(new
> AdapterFactoryContentProvider(attributeAdapterFactory));
>
> parentViewer.setLabelProvider(new
> AdapterFactoryLabelProvider(attributeAdapterFactory));
> parentViewer.setInput(editingDomain.getResourceSet());
> parentViewer.setSelection(new
> StructuredSelection(editingDomain.getResourceSet().getResour ces().get(0)),
> true);
> viewerPane.setTitle(editingDomain.getResourceSet());
>
> new AdapterFactoryTreeEditor(parentViewer.getTree(),
> attributeAdapterFactory);
>
> createContextMenuFor(parentViewer);
> int pageIndex = addPage(viewerPane.getControl());
> setPageText(pageIndex, getString("_UI_ParentPage_label"));
> }
> Overriding the getChildren{} method in
> XYZAttributeItemProviderAdapterFactory seems to be the wrong approach,
> because when I open the parent View in the running application, only
> ONE class shows its inherited attributes.
You're keeping in mind that the item providers are by default
singletons, i.e., one adapter instance adapts all model instances.
That's only good when you have stateless adapters. If your adapters are
stateful, you'll need to change that in the GenClass's properties so
that an adapter per model instance is created.
> The other classes which (physically) contain those attributes are now
> empty. It appears, as if the last MClass whose getChildren() is
> called, "steals" its MAttributes from the other classes.
>
> So,
> 1 - What am i doing wrong? How can i realise my desierd view? Should i
> do semothing completely different? Like adding a derived Field to the
> MClass which calculates the inherited Attributes..?
Set them to be stateful if that's how you're going to implement it. The
alternative is don't cache any of the result but rather recompute them
each time; that might not perform sufficiently well...
> 2 - Is there a way to set the Font of specific MAttributes (e.g. write
> inherited MAttributes gray and cursive in the viewer)
You can enable Font Providers in the GenModel; note that the edit
project's plugin.xml won't regenerate so you really ought to delete it
and regenerate it.
>
> Cheers,
> Christian
Re: [EMF] Inter-model Inheritance viewer in EMF editor [message #667476 is a reply to message #656531] Fri, 29 April 2011 00:17 Go to previous messageGo to next message
Christian  is currently offline Christian Friend
Messages: 14
Registered: February 2011
Junior Member
Unfortunately i still could not solve this issue.

My custom ItemProviderAdapterFactory still interferes with the standard one.
I took a close look into the XSDsemantic/syntactic implementation but couldn't figure out what i was doing wrong. I suppose i did everyhting right, but whenever i open the "Parent" tab of my editor, the "Selection" tab changes too. Even after setting all the ItemProviders to stateful in the genmodel.

The only real difference between my current project and the XSD project is the usage of a specific XSDSchema in the XSDEditor.java. [for exmaple:
semanticSelectionViewer.setInput(new ItemProvider(Collections.singleton(xsdSchema)));]

Help would be really appreciated since this issue bugs me for about a month now! Sad

I attached the sources of a small testproject together with some testdata. The goal should be to have two different views of the same model. One showing the syntactic data (standard selection window) and one showing all inherited attributes like this:
MClass ObjectBase
# MAttribute AttributeBase1
# MAttribute AttributeBase2
MClass ObjectLocalized extends ObjectBase
# MAttribute AttributeBase1
# MAttribute AttributeBase2
# MAttribute AttributeLocalized1

Unfortunately I can't include attachments to this message.. so the files can be found here:
n/a

I hope someone has the time to take a look into this matter!
Thanks, Christian

[Updated on: Fri, 01 July 2011 12:16]

Report message to a moderator

Re: [EMF] Inter-model Inheritance viewer in EMF editor [message #667531 is a reply to message #667476] Fri, 29 April 2011 11:18 Go to previous message
Ed Merks is currently offline Ed MerksFriend
Messages: 26217
Registered: July 2009
Senior Member
Christian,

comments below.

Christian wrote:
> Unfortunately i still could not solve this issue.
>
> My custom ItemProviderAdapterFactory still interferes with the
> standard one.
> I took a close look into the XSDsemantic/syntactic implementation but
> couldn't figure out what i was doing wrong. I suppose i did everyhting
> right, but whenever i open the "Parent" tab of my editor, the
> "Selection" tab changes too. Even after setting all the ItemProviders
> to stateful in the genmodel.
Are they sharing item providers or are you using different factories for
each; I'd expect the latter if you want to specialize only one of the
views, and not all.
>
> The only real difference between my current project and the XSD
> project is the usage of a specific XSDSchema in the XSDEditor.java.
> [for exmaple:
> semanticSelectionViewer.setInput(new
> ItemProvider(Collections.singleton(xsdSchema)));]
>
> Help would be really appreciated since this issue bugs me for about a
> month now! :(
>
> I attached the sources of a small testproject together with some
> testdata.
I have no time to debugging other people's problems in the next weeks...
> The goal should be to have two different views of the same model. One
> showing the syntactic data (standard selection window) and one showing
> all inherited attributes like this:
> MClass ObjectBase
> # MAttribute AttributeBase1
> # MAttribute AttributeBase2
> MClass ObjectLocalized extends ObjectBase
> # MAttribute AttributeBase1
> # MAttribute AttributeBase2
> # MAttribute AttributeLocalized1
>
> Unfortunately I can't include attachments to this message.. so the
> files can be found here:
> https://rapidshare.com/files/459690891/testplug.zip
>
> I hope someone has the time to take a look into this matter!
> Thanks, Christian
Previous Topic:delete me.
Next Topic:XML serialization try to handle xmlns:... attributes
Goto Forum:
  


Current Time: Mon Nov 24 20:34:21 GMT 2014

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

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