Skip to main content


Eclipse Community Forums
Forum Search:

Search      Help    Register    Login    Home
Home » Modeling » EMF » Using Model Listeners / Adapters in AbstractPropertySections
Using Model Listeners / Adapters in AbstractPropertySections [message #417056] Mon, 25 February 2008 14:17 Go to next message
Tobias is currently offline TobiasFriend
Messages: 18
Registered: July 2009
Junior Member
Hello,

I have to admid that I'm still quite inexperienced in the use of the
Adapters-Framework. I know that this is one of the core components of
the EMF framework and that it's of great help, but it's also quite
complicated...

However, I have a GMF editor for which I've created a set of
AdvancedPropertySections following the guide at [1]. In section "Model
Listeners" it is written where to register and deregister Listeners for
the model elements. After a quick research on the Adapters framework
I've implemented the methods as shown in [2] in the parent class of all
my PropertySections. This seems to work quite well, in that I can set a
property, hit the undo-Button (changing the property outside of the
view, which was the major motivation for trying this) and the change is
also undone in the property section.

1.: Honestly I have no clue when to return true in the
isAdapterForType-methods, since the type is always the same, namely my
ItemProviderAdapterFactory. However, returning false seems to have no
effect anyway...
2.: I think aboutToBeShown is not the best place for registering the
listeners, since it is not called again when switching to another node
of the same type. Maybe this sould (also) be done in the setInput method?
3.: Most time it works fine, but occasionally it crashes [3]. This can
occur when making a change and changing the selection, when making no
changes and changing the text field (I'm using focusListeners), and
possible a number of other occasions -- I have not found a pattern yet.
But it's always the refresh method being called by notifyChanged which
crashes.

So obviously this is not a very clean implementation, so I would
appreciate any hints or comments or links to (understandable ^^;)
tutorials on this topic, if you know any.

Regards,
Tobias

[1]
< http://www.eclipse.org/articles/Article-Tabbed-Properties/ta bbed_properties_view.html>


[2] private Adapter myAdapter= new Adapter() {
EObject target= null;
public Notifier getTarget() {
return target;
}
public boolean isAdapterForType(Object type) {
return false;
}
public void notifyChanged(Notification notification) {
refresh();
}
public void setTarget(Notifier newTarget) {
if (newTarget instanceof EObject) {
target= (EObject) newTarget;
}
}
};

@Override
public void aboutToBeShown() {
super.aboutToBeShown();
myAdapter.setTarget(eObject);
eObject.eAdapters().add(myAdapter);
}

@Override
public void aboutToBeHidden() {
super.aboutToBeHidden();
eObject.eAdapters().remove(myAdapter);
}


[3] org.eclipse.swt.SWTException: Widget is disposed
at org.eclipse.swt.SWT.error(SWT.java:3563)
at org.eclipse.swt.SWT.error(SWT.java:3481)
at org.eclipse.swt.SWT.error(SWT.java:3452)
at org.eclipse.swt.widgets.Widget.error(Widget.java:432)
at org.eclipse.swt.widgets.Widget.checkWidget(Widget.java:325)
at org.eclipse.swt.widgets.Text.setText(Text.java:1793)
at
XXX.diagram.properties.sections.IdObjectSection.refresh(IdOb jectSection.java:50)
at
XXX.diagram.properties.sections.AbstractVsdtPropertySection$ 1.notifyChanged(AbstractVsdtPropertySection.java:117)
at
org.eclipse.emf.common.notify.impl.BasicNotifierImpl$EAdapte rList.didRemove(BasicNotifierImpl.java:95)
at org.eclipse.emf.common.util.BasicEList.didClear(BasicEList.j ava:260)
at org.eclipse.emf.common.util.BasicEList.clear(BasicEList.java :1000)
at
org.eclipse.emf.common.notify.impl.BasicNotifierImpl$EAdapte rList.clear(BasicNotifierImpl.java:171)
at
org.eclipse.emf.ecore.resource.impl.ResourceImpl.unloaded(Re sourceImpl.java:1420)
at
org.eclipse.emf.ecore.resource.impl.ResourceImpl.doUnload(Re sourceImpl.java:1479)
at
org.eclipse.emf.ecore.xmi.impl.XMLResourceImpl.doUnload(XMLR esourceImpl.java:505)
at
org.eclipse.emf.ecore.resource.impl.ResourceImpl.unload(Reso urceImpl.java:1494)
at
de.dailab.sercho.vsdt.diagram.part.VsdtDocumentProvider$Reso urceSetInfo.dispose(VsdtDocumentProvider.java:877)
at
de.dailab.sercho.vsdt.diagram.part.VsdtDocumentProvider.disp oseElementInfo(VsdtDocumentProvider.java:328)
at
org.eclipse.gmf.runtime.diagram.ui.resources.editor.document .AbstractDocumentProvider.disconnect(AbstractDocumentProvide r.java:425)
at
org.eclipse.gmf.runtime.diagram.ui.resources.editor.parts.Di agramDocumentEditor.disposeDocumentProvider(DiagramDocumentE ditor.java:481)
at
org.eclipse.gmf.runtime.diagram.ui.resources.editor.parts.Di agramDocumentEditor.dispose(DiagramDocumentEditor.java:177)
at
org.eclipse.ui.internal.WorkbenchPartReference.doDisposePart (WorkbenchPartReference.java:720)
at
org.eclipse.ui.internal.EditorReference.doDisposePart(Editor Reference.java:306)
at
org.eclipse.ui.internal.WorkbenchPartReference.dispose(Workb enchPartReference.java:671)
at
org.eclipse.ui.internal.WorkbenchPage.disposePart(WorkbenchP age.java:1604)
at
org.eclipse.ui.internal.WorkbenchPage.handleDeferredEvents(W orkbenchPage.java:1354)
at
org.eclipse.ui.internal.WorkbenchPage.deferUpdates(Workbench Page.java:1338)
at
org.eclipse.ui.internal.WorkbenchPage.closeEditors(Workbench Page.java:1312)
at
org.eclipse.ui.internal.WorkbenchPage.closeEditor(WorkbenchP age.java:1367)
at org.eclipse.ui.internal.EditorPane.doHide(EditorPane.java:61 )
at org.eclipse.ui.internal.PartStack.close(PartStack.java:543)
at org.eclipse.ui.internal.EditorStack.close(EditorStack.java:2 06)
at org.eclipse.ui.internal.PartStack$1.close(PartStack.java:122 )
at
org.eclipse.ui.internal.presentations.util.TabbedStackPresen tation$1.handleEvent(TabbedStackPresentation.java:81)
at
org.eclipse.ui.internal.presentations.util.AbstractTabFolder .fireEvent(AbstractTabFolder.java:267)
at
org.eclipse.ui.internal.presentations.util.AbstractTabFolder .fireEvent(AbstractTabFolder.java:276)
at
org.eclipse.ui.internal.presentations.defaultpresentation.De faultTabFolder.access$1(DefaultTabFolder.java:1)
at
org.eclipse.ui.internal.presentations.defaultpresentation.De faultTabFolder$1.closeButtonPressed(DefaultTabFolder.java:67 )
at
org.eclipse.ui.internal.presentations.PaneFolder.notifyClose Listeners(PaneFolder.java:596)
at
org.eclipse.ui.internal.presentations.PaneFolder$3.close(Pan eFolder.java:189)
at org.eclipse.swt.custom.CTabFolder.onMouse(CTabFolder.java:21 59)
at org.eclipse.swt.custom.CTabFolder$1.handleEvent(CTabFolder.j ava:320)
at org.eclipse.swt.widgets.EventTable.sendEvent(EventTable.java :66)
at org.eclipse.swt.widgets.Widget.sendEvent(Widget.java:938)
at org.eclipse.swt.widgets.Display.runDeferredEvents(Display.ja va:3682)
at org.eclipse.swt.widgets.Display.readAndDispatch(Display.java :3293)
at org.eclipse.ui.internal.Workbench.runEventLoop(Workbench.jav a:2389)
at org.eclipse.ui.internal.Workbench.runUI(Workbench.java:2353)
at org.eclipse.ui.internal.Workbench.access$4(Workbench.java:22 19)
at org.eclipse.ui.internal.Workbench$4.run(Workbench.java:466)
at
org.eclipse.core.databinding.observable.Realm.runWithDefault (Realm.java:289)
at
org.eclipse.ui.internal.Workbench.createAndRunWorkbench(Work bench.java:461)
at org.eclipse.ui.PlatformUI.createAndRunWorkbench(PlatformUI.j ava:149)
at
org.eclipse.ui.internal.ide.application.IDEApplication.start (IDEApplication.java:106)
at
org.eclipse.equinox.internal.app.EclipseAppHandle.run(Eclips eAppHandle.java:169)
at
org.eclipse.core.runtime.internal.adaptor.EclipseAppLauncher .runApplication(EclipseAppLauncher.java:106)
at
org.eclipse.core.runtime.internal.adaptor.EclipseAppLauncher .start(EclipseAppLauncher.java:76)
at
org.eclipse.core.runtime.adaptor.EclipseStarter.run(EclipseS tarter.java:363)
at
org.eclipse.core.runtime.adaptor.EclipseStarter.run(EclipseS tarter.java:176)
at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
at sun.reflect.NativeMethodAccessorImpl.invoke(Unknown Source)
at sun.reflect.DelegatingMethodAccessorImpl.invoke(Unknown Source)
at java.lang.reflect.Method.invoke(Unknown Source)
at org.eclipse.equinox.launcher.Main.invokeFramework(Main.java: 508)
at org.eclipse.equinox.launcher.Main.basicRun(Main.java:447)
at org.eclipse.equinox.launcher.Main.run(Main.java:1173)
at org.eclipse.equinox.launcher.Main.main(Main.java:1148)
Re: Using Model Listeners / Adapters in AbstractPropertySections [message #417057 is a reply to message #417056] Mon, 25 February 2008 15:00 Go to previous messageGo to next message
Ed Merks is currently offline Ed MerksFriend
Messages: 33113
Registered: July 2009
Senior Member
This is a multi-part message in MIME format.
--------------090308090800060102030608
Content-Type: text/plain; charset=ISO-8859-15; format=flowed
Content-Transfer-Encoding: 7bit

Tobias,

Comments below.

Tobias wrote:
> Hello,
>
> I have to admid that I'm still quite inexperienced in the use of the
> Adapters-Framework. I know that this is one of the core components of
> the EMF framework and that it's of great help, but it's also quite
> complicated...
Complexity is always a relative thing. New things will always appear to
be complex and often more complex than necessary. Once you learn they,
they typically appear simple and intuitive...
>
> However, I have a GMF editor for which I've created a set of
> AdvancedPropertySections following the guide at [1]. In section "Model
> Listeners" it is written where to register and deregister Listeners
> for the model elements. After a quick research on the Adapters
> framework I've implemented the methods as shown in [2] in the parent
> class of all my PropertySections. This seems to work quite well, in
> that I can set a property, hit the undo-Button (changing the property
> outside of the view, which was the major motivation for trying this)
> and the change is also undone in the property section.
>
> 1.: Honestly I have no clue when to return true in the
> isAdapterForType-methods, since the type is always the same, namely my
> ItemProviderAdapterFactory. However, returning false seems to have no
> effect anyway...
Some places you'll see it being used are in AdapterFactoryImpl

| *public *Adapter adapt(Notifier target, Object type)
{
*for *(Adapter adapter : target.eAdapters())
{
*if *(adapter.isAdapterForType(type))
{
*return *adapter;
}
}
*return *adaptNew(target, type);
}|

And EcoreUtil:

| /**
* Returns the adapter of the specified type.
* @param adapters list of adapters to search.
* @param type the type of adapter.
* @return an adapter from the list or null.
*/
*public static *Adapter getAdapter(List<Adapter> adapters, Object type)
{
*for *(*int *i = 0, size = adapters.size(); i < size; ++i)
{
Adapter adapter = adapters.get(i);
*if *(adapter.isAdapterForType(type))
{
*return *adapter;
}
}
*return null*;
}|

If you aren't using a factory and aren't looking up your adapter by
type, it doesn't matter that you always return false.
> 2.: I think aboutToBeShown is not the best place for registering the
> listeners, since it is not called again when switching to another node
> of the same type. Maybe this sould (also) be done in the setInput method?
I'm not sure where the best hooks are. I imagine you should clean them
up whenever a new input is set or when the section itself is disposed.
The basic EMF properties view is always just refreshed whenever a
command is executed. I.e., there are no fine-grained notifications to
keep it up to date. Perhaps that approach would be simpler...
> 3.: Most time it works fine, but occasionally it crashes [3]. This can
> occur when making a change and changing the selection, when making no
> changes and changing the text field (I'm using focusListeners), and
> possible a number of other occasions -- I have not found a pattern
> yet. But it's always the refresh method being called by notifyChanged
> which crashes.
Sounds likely the result of not cleaning up the adapters.
>
> So obviously this is not a very clean implementation, so I would
> appreciate any hints or comments or links to (understandable ^^;)
> tutorials on this topic, if you know any.
>
> Regards,
> Tobias
>
> [1]
> < http://www.eclipse.org/articles/Article-Tabbed-Properties/ta bbed_properties_view.html>
>
>
>
> [2] private Adapter myAdapter= new Adapter() {
> EObject target= null;
> public Notifier getTarget() {
> return target;
> }
> public boolean isAdapterForType(Object type) {
> return false;
> }
> public void notifyChanged(Notification notification) {
> refresh();
> }
> public void setTarget(Notifier newTarget) {
> if (newTarget instanceof EObject) {
> target= (EObject) newTarget;
> }
> }
> };
>
> @Override
> public void aboutToBeShown() {
> super.aboutToBeShown();
> myAdapter.setTarget(eObject);
> eObject.eAdapters().add(myAdapter);
> }
>
> @Override
> public void aboutToBeHidden() {
> super.aboutToBeHidden();
> eObject.eAdapters().remove(myAdapter);
> }
>
>
> [3] org.eclipse.swt.SWTException: Widget is disposed
> at org.eclipse.swt.SWT.error(SWT.java:3563)
> at org.eclipse.swt.SWT.error(SWT.java:3481)
> at org.eclipse.swt.SWT.error(SWT.java:3452)
> at org.eclipse.swt.widgets.Widget.error(Widget.java:432)
> at org.eclipse.swt.widgets.Widget.checkWidget(Widget.java:325)
> at org.eclipse.swt.widgets.Text.setText(Text.java:1793)
> at
> XXX.diagram.properties.sections.IdObjectSection.refresh(IdOb jectSection.java:50)
>
> at
> XXX.diagram.properties.sections.AbstractVsdtPropertySection$ 1.notifyChanged(AbstractVsdtPropertySection.java:117)
>
> at
> org.eclipse.emf.common.notify.impl.BasicNotifierImpl$EAdapte rList.didRemove(BasicNotifierImpl.java:95)
>
> at
> org.eclipse.emf.common.util.BasicEList.didClear(BasicEList.j ava:260)
> at org.eclipse.emf.common.util.BasicEList.clear(BasicEList.java :1000)
> at
> org.eclipse.emf.common.notify.impl.BasicNotifierImpl$EAdapte rList.clear(BasicNotifierImpl.java:171)
>
> at
> org.eclipse.emf.ecore.resource.impl.ResourceImpl.unloaded(Re sourceImpl.java:1420)
>
> at
> org.eclipse.emf.ecore.resource.impl.ResourceImpl.doUnload(Re sourceImpl.java:1479)
>
> at
> org.eclipse.emf.ecore.xmi.impl.XMLResourceImpl.doUnload(XMLR esourceImpl.java:505)
>
> at
> org.eclipse.emf.ecore.resource.impl.ResourceImpl.unload(Reso urceImpl.java:1494)
>
> at
> de.dailab.sercho.vsdt.diagram.part.VsdtDocumentProvider$Reso urceSetInfo.dispose(VsdtDocumentProvider.java:877)
>
> at
> de.dailab.sercho.vsdt.diagram.part.VsdtDocumentProvider.disp oseElementInfo(VsdtDocumentProvider.java:328)
>
> at
> org.eclipse.gmf.runtime.diagram.ui.resources.editor.document .AbstractDocumentProvider.disconnect(AbstractDocumentProvide r.java:425)
>
> at
> org.eclipse.gmf.runtime.diagram.ui.resources.editor.parts.Di agramDocumentEditor.disposeDocumentProvider(DiagramDocumentE ditor.java:481)
>
> at
> org.eclipse.gmf.runtime.diagram.ui.resources.editor.parts.Di agramDocumentEditor.dispose(DiagramDocumentEditor.java:177)
>
> at
> org.eclipse.ui.internal.WorkbenchPartReference.doDisposePart (WorkbenchPartReference.java:720)
>
> at
> org.eclipse.ui.internal.EditorReference.doDisposePart(Editor Reference.java:306)
>
> at
> org.eclipse.ui.internal.WorkbenchPartReference.dispose(Workb enchPartReference.java:671)
>
> at
> org.eclipse.ui.internal.WorkbenchPage.disposePart(WorkbenchP age.java:1604)
>
> at
> org.eclipse.ui.internal.WorkbenchPage.handleDeferredEvents(W orkbenchPage.java:1354)
>
> at
> org.eclipse.ui.internal.WorkbenchPage.deferUpdates(Workbench Page.java:1338)
>
> at
> org.eclipse.ui.internal.WorkbenchPage.closeEditors(Workbench Page.java:1312)
>
> at
> org.eclipse.ui.internal.WorkbenchPage.closeEditor(WorkbenchP age.java:1367)
>
> at org.eclipse.ui.internal.EditorPane.doHide(EditorPane.java:61 )
> at org.eclipse.ui.internal.PartStack.close(PartStack.java:543)
> at org.eclipse.ui.internal.EditorStack.close(EditorStack.java:2 06)
> at org.eclipse.ui.internal.PartStack$1.close(PartStack.java:122 )
> at
> org.eclipse.ui.internal.presentations.util.TabbedStackPresen tation$1.handleEvent(TabbedStackPresentation.java:81)
>
> at
> org.eclipse.ui.internal.presentations.util.AbstractTabFolder .fireEvent(AbstractTabFolder.java:267)
>
> at
> org.eclipse.ui.internal.presentations.util.AbstractTabFolder .fireEvent(AbstractTabFolder.java:276)
>
> at
> org.eclipse.ui.internal.presentations.defaultpresentation.De faultTabFolder.access$1(DefaultTabFolder.java:1)
>
> at
> org.eclipse.ui.internal.presentations.defaultpresentation.De faultTabFolder$1.closeButtonPressed(DefaultTabFolder.java:67 )
>
> at
> org.eclipse.ui.internal.presentations.PaneFolder.notifyClose Listeners(PaneFolder.java:596)
>
> at
> org.eclipse.ui.internal.presentations.PaneFolder$3.close(Pan eFolder.java:189)
>
> at org.eclipse.swt.custom.CTabFolder.onMouse(CTabFolder.java:21 59)
> at
> org.eclipse.swt.custom.CTabFolder$1.handleEvent(CTabFolder.j ava:320)
> at org.eclipse.swt.widgets.EventTable.sendEvent(EventTable.java :66)
> at org.eclipse.swt.widgets.Widget.sendEvent(Widget.java:938)
> at
> org.eclipse.swt.widgets.Display.runDeferredEvents(Display.ja va:3682)
> at org.eclipse.swt.widgets.Display.readAndDispatch(Display.java :3293)
> at
> org.eclipse.ui.internal.Workbench.runEventLoop(Workbench.jav a:2389)
> at org.eclipse.ui.internal.Workbench.runUI(Workbench.java:2353)
> at org.eclipse.ui.internal.Workbench.access$4(Workbench.java:22 19)
> at org.eclipse.ui.internal.Workbench$4.run(Workbench.java:466)
> at
> org.eclipse.core.databinding.observable.Realm.runWithDefault (Realm.java:289)
>
> at
> org.eclipse.ui.internal.Workbench.createAndRunWorkbench(Work bench.java:461)
>
> at
> org.eclipse.ui.PlatformUI.createAndRunWorkbench(PlatformUI.j ava:149)
> at
> org.eclipse.ui.internal.ide.application.IDEApplication.start (IDEApplication.java:106)
>
> at
> org.eclipse.equinox.internal.app.EclipseAppHandle.run(Eclips eAppHandle.java:169)
>
> at
> org.eclipse.core.runtime.internal.adaptor.EclipseAppLauncher .runApplication(EclipseAppLauncher.java:106)
>
> at
> org.eclipse.core.runtime.internal.adaptor.EclipseAppLauncher .start(EclipseAppLauncher.java:76)
>
> at
> org.eclipse.core.runtime.adaptor.EclipseStarter.run(EclipseS tarter.java:363)
>
> at
> org.eclipse.core.runtime.adaptor.EclipseStarter.run(EclipseS tarter.java:176)
>
> at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
> at sun.reflect.NativeMethodAccessorImpl.invoke(Unknown Source)
> at sun.reflect.DelegatingMethodAccessorImpl.invoke(Unknown Source)
> at java.lang.reflect.Method.invoke(Unknown Source)
> at org.eclipse.equinox.launcher.Main.invokeFramework(Main.java: 508)
> at org.eclipse.equinox.launcher.Main.basicRun(Main.java:447)
> at org.eclipse.equinox.launcher.Main.run(Main.java:1173)
> at org.eclipse.equinox.launcher.Main.main(Main.java:1148)


--------------090308090800060102030608
Content-Type: text/html; charset=ISO-8859-15
Content-Transfer-Encoding: 8bit

<!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN">
<html>
<head>
<meta content="text/html;charset=ISO-8859-15"
http-equiv="Content-Type">
</head>
<body bgcolor="#ffffff" text="#000000">
<div class="moz-text-html" lang="x-western"> Tobias,<br>
<br>
Comments below.<br>
<br>
Tobias wrote:
<blockquote cite="mid:fpuim7$t4j$1@build.eclipse.org" type="cite">Hello,
<br>
<br>
I have to admid that I'm still quite inexperienced in the use of the
Adapters-Framework. I know that this is one of the core components of
the EMF framework and that it's of great help, but it's also quite
complicated... <br>
</blockquote>
Complexity is always a relative thing.


Ed Merks
Professional Support: https://www.macromodeling.com/
Re: Using Model Listeners / Adapters in AbstractPropertySections [message #417059 is a reply to message #417057] Mon, 25 February 2008 16:22 Go to previous messageGo to next message
Tobias is currently offline TobiasFriend
Messages: 18
Registered: July 2009
Junior Member
Thank you Ed, you just saved my day (again). ^^;;

So the problem realy was that - as I assumed - the aboutToBeShown/Hidden
methods are not enough. Now that I'm updating the adapter in setInput
(and dispose, just to be sure), too, everything seems to work fine. Not
one crash so far and no mysteriously multiplying adapters. Maybe the
article [1] should be extended in this direction.

I'll try to look into whether there's a difference in returning true or
false in the isAdapterForType method in my case.

Concerning the 'big-big-framework'-problem: I think what's making parts
of EMF/GMF so hard to understand is the high potion of generated code
you have to hook your stuff into along with the numerous super classes
doing all kinds fo stuff "behind your back" (which, of course, is a good
thing, generally spoken). Do you know of any good book on this topic? I
do not mean a book how to create a EMF-based editor from scratch, like
the famous 'red book', but more the cook-book type, offering solutions
for all kinds of problems (possibly even specific for GMF).

Tobias


Ed Merks schrieb:
> Tobias,
>
> Comments below.
>
> Tobias wrote:
>> Hello,
>>
>> I have to admid that I'm still quite inexperienced in the use of the
>> Adapters-Framework. I know that this is one of the core components of
>> the EMF framework and that it's of great help, but it's also quite
>> complicated...
> Complexity is always a relative thing. New things will always appear to
> be complex and often more complex than necessary. Once you learn they,
> they typically appear simple and intuitive...
>>
>> However, I have a GMF editor for which I've created a set of
>> AdvancedPropertySections following the guide at [1]. In section "Model
>> Listeners" it is written where to register and deregister Listeners
>> for the model elements. After a quick research on the Adapters
>> framework I've implemented the methods as shown in [2] in the parent
>> class of all my PropertySections. This seems to work quite well, in
>> that I can set a property, hit the undo-Button (changing the property
>> outside of the view, which was the major motivation for trying this)
>> and the change is also undone in the property section.
>>
>> 1.: Honestly I have no clue when to return true in the
>> isAdapterForType-methods, since the type is always the same, namely my
>> ItemProviderAdapterFactory. However, returning false seems to have no
>> effect anyway...
> Some places you'll see it being used are in AdapterFactoryImpl
>
> | *public *Adapter adapt(Notifier target, Object type)
> {
> *for *(Adapter adapter : target.eAdapters())
> {
> *if *(adapter.isAdapterForType(type))
> {
> *return *adapter;
> }
> }
> *return *adaptNew(target, type);
> }|
>
> And EcoreUtil:
>
> | /**
> * Returns the adapter of the specified type.
> * @param adapters list of adapters to search.
> * @param type the type of adapter.
> * @return an adapter from the list or null.
> */
> *public static *Adapter getAdapter(List<Adapter> adapters, Object type)
> {
> *for *(*int *i = 0, size = adapters.size(); i < size; ++i)
> {
> Adapter adapter = adapters.get(i);
> *if *(adapter.isAdapterForType(type))
> {
> *return *adapter;
> }
> }
> *return null*;
> }|
>
> If you aren't using a factory and aren't looking up your adapter by
> type, it doesn't matter that you always return false.
>> 2.: I think aboutToBeShown is not the best place for registering the
>> listeners, since it is not called again when switching to another node
>> of the same type. Maybe this sould (also) be done in the setInput method?
> I'm not sure where the best hooks are. I imagine you should clean them
> up whenever a new input is set or when the section itself is disposed.
> The basic EMF properties view is always just refreshed whenever a
> command is executed. I.e., there are no fine-grained notifications to
> keep it up to date. Perhaps that approach would be simpler...
>> 3.: Most time it works fine, but occasionally it crashes [3]. This can
>> occur when making a change and changing the selection, when making no
>> changes and changing the text field (I'm using focusListeners), and
>> possible a number of other occasions -- I have not found a pattern
>> yet. But it's always the refresh method being called by notifyChanged
>> which crashes.
> Sounds likely the result of not cleaning up the adapters.
>>
>> So obviously this is not a very clean implementation, so I would
>> appreciate any hints or comments or links to (understandable ^^;)
>> tutorials on this topic, if you know any.
>>
>> Regards,
>> Tobias
>>
>> [1]
>> < http://www.eclipse.org/articles/Article-Tabbed-Properties/ta bbed_properties_view.html>
>>
>>
>>
>> [2] private Adapter myAdapter= new Adapter() {
>> EObject target= null;
>> public Notifier getTarget() {
>> return target;
>> }
>> public boolean isAdapterForType(Object type) {
>> return false;
>> }
>> public void notifyChanged(Notification notification) {
>> refresh();
>> }
>> public void setTarget(Notifier newTarget) {
>> if (newTarget instanceof EObject) {
>> target= (EObject) newTarget;
>> }
>> }
>> };
>>
>> @Override
>> public void aboutToBeShown() {
>> super.aboutToBeShown();
>> myAdapter.setTarget(eObject);
>> eObject.eAdapters().add(myAdapter);
>> }
>>
>> @Override
>> public void aboutToBeHidden() {
>> super.aboutToBeHidden();
>> eObject.eAdapters().remove(myAdapter);
>> }
>>
>>
>> [3] org.eclipse.swt.SWTException: Widget is disposed
>> at org.eclipse.swt.SWT.error(SWT.java:3563)
>> at org.eclipse.swt.SWT.error(SWT.java:3481)
>> at org.eclipse.swt.SWT.error(SWT.java:3452)
>> at org.eclipse.swt.widgets.Widget.error(Widget.java:432)
>> at org.eclipse.swt.widgets.Widget.checkWidget(Widget.java:325)
>> at org.eclipse.swt.widgets.Text.setText(Text.java:1793)
>> at
>> XXX.diagram.properties.sections.IdObjectSection.refresh(IdOb jectSection.java:50)
>>
>> at
>> XXX.diagram.properties.sections.AbstractVsdtPropertySection$ 1.notifyChanged(AbstractVsdtPropertySection.java:117)
>>
>> at
>> org.eclipse.emf.common.notify.impl.BasicNotifierImpl$EAdapte rList.didRemove(BasicNotifierImpl.java:95)
>>
>> at
>> org.eclipse.emf.common.util.BasicEList.didClear(BasicEList.j ava:260)
>> at org.eclipse.emf.common.util.BasicEList.clear(BasicEList.java :1000)
>> at
>> org.eclipse.emf.common.notify.impl.BasicNotifierImpl$EAdapte rList.clear(BasicNotifierImpl.java:171)
>>
>> at
>> org.eclipse.emf.ecore.resource.impl.ResourceImpl.unloaded(Re sourceImpl.java:1420)
>>
>> at
>> org.eclipse.emf.ecore.resource.impl.ResourceImpl.doUnload(Re sourceImpl.java:1479)
>>
>> at
>> org.eclipse.emf.ecore.xmi.impl.XMLResourceImpl.doUnload(XMLR esourceImpl.java:505)
>>
>> at
>> org.eclipse.emf.ecore.resource.impl.ResourceImpl.unload(Reso urceImpl.java:1494)
>>
>> at
>> de.dailab.sercho.vsdt.diagram.part.VsdtDocumentProvider$Reso urceSetInfo.dispose(VsdtDocumentProvider.java:877)
>>
>> at
>> de.dailab.sercho.vsdt.diagram.part.VsdtDocumentProvider.disp oseElementInfo(VsdtDocumentProvider.java:328)
>>
>> at
>> org.eclipse.gmf.runtime.diagram.ui.resources.editor.document .AbstractDocumentProvider.disconnect(AbstractDocumentProvide r.java:425)
>>
>> at
>> org.eclipse.gmf.runtime.diagram.ui.resources.editor.parts.Di agramDocumentEditor.disposeDocumentProvider(DiagramDocumentE ditor.java:481)
>>
>> at
>> org.eclipse.gmf.runtime.diagram.ui.resources.editor.parts.Di agramDocumentEditor.dispose(DiagramDocumentEditor.java:177)
>>
>> at
>> org.eclipse.ui.internal.WorkbenchPartReference.doDisposePart (WorkbenchPartReference.java:720)
>>
>> at
>> org.eclipse.ui.internal.EditorReference.doDisposePart(Editor Reference.java:306)
>>
>> at
>> org.eclipse.ui.internal.WorkbenchPartReference.dispose(Workb enchPartReference.java:671)
>>
>> at
>> org.eclipse.ui.internal.WorkbenchPage.disposePart(WorkbenchP age.java:1604)
>>
>> at
>> org.eclipse.ui.internal.WorkbenchPage.handleDeferredEvents(W orkbenchPage.java:1354)
>>
>> at
>> org.eclipse.ui.internal.WorkbenchPage.deferUpdates(Workbench Page.java:1338)
>>
>> at
>> org.eclipse.ui.internal.WorkbenchPage.closeEditors(Workbench Page.java:1312)
>>
>> at
>> org.eclipse.ui.internal.WorkbenchPage.closeEditor(WorkbenchP age.java:1367)
>>
>> at org.eclipse.ui.internal.EditorPane.doHide(EditorPane.java:61 )
>> at org.eclipse.ui.internal.PartStack.close(PartStack.java:543)
>> at org.eclipse.ui.internal.EditorStack.close(EditorStack.java:2 06)
>> at org.eclipse.ui.internal.PartStack$1.close(PartStack.java:122 )
>> at
>> org.eclipse.ui.internal.presentations.util.TabbedStackPresen tation$1.handleEvent(TabbedStackPresentation..java:81)
>>
>> at
>> org.eclipse.ui.internal.presentations.util.AbstractTabFolder .fireEvent(AbstractTabFolder.java:267)
>>
>> at
>> org.eclipse.ui.internal.presentations.util.AbstractTabFolder .fireEvent(AbstractTabFolder.java:276)
>>
>> at
>> org.eclipse.ui.internal.presentations.defaultpresentation.De faultTabFolder.access$1(DefaultTabFolder.java:1)
>>
>> at
>> org.eclipse.ui.internal.presentations.defaultpresentation.De faultTabFolder$1.closeButtonPressed(DefaultTabFolder.java:67 )
>>
>> at
>> org.eclipse.ui.internal.presentations.PaneFolder.notifyClose Listeners(PaneFolder.java:596)
>>
>> at
>> org.eclipse.ui.internal.presentations.PaneFolder$3.close(Pan eFolder.java:189)
>>
>> at org.eclipse.swt.custom.CTabFolder.onMouse(CTabFolder.java:21 59)
>> at
>> org.eclipse.swt.custom.CTabFolder$1.handleEvent(CTabFolder.j ava:320)
>> at org.eclipse.swt.widgets.EventTable.sendEvent(EventTable.java :66)
>> at org.eclipse.swt.widgets.Widget.sendEvent(Widget.java:938)
>> at
>> org.eclipse.swt.widgets.Display.runDeferredEvents(Display.ja va:3682)
>> at org.eclipse.swt.widgets.Display.readAndDispatch(Display.java :3293)
>> at
>> org.eclipse.ui.internal.Workbench.runEventLoop(Workbench.jav a:2389)
>> at org.eclipse.ui.internal.Workbench.runUI(Workbench.java:2353)
>> at org.eclipse.ui.internal.Workbench.access$4(Workbench.java:22 19)
>> at org.eclipse.ui.internal.Workbench$4.run(Workbench.java:466)
>> at
>> org.eclipse.core.databinding.observable.Realm.runWithDefault (Realm.java:289)
>>
>> at
>> org.eclipse.ui.internal.Workbench.createAndRunWorkbench(Work bench.java:461)
>>
>> at
>> org.eclipse.ui.PlatformUI.createAndRunWorkbench(PlatformUI.j ava:149)
>> at
>> org.eclipse.ui.internal.ide.application.IDEApplication.start (IDEApplication.java:106)
>>
>> at
>> org.eclipse.equinox.internal.app.EclipseAppHandle.run(Eclips eAppHandle.java:169)
>>
>> at
>> org.eclipse.core.runtime.internal.adaptor.EclipseAppLauncher .runApplication(EclipseAppLauncher.java:106)
>>
>> at
>> org.eclipse.core.runtime.internal.adaptor.EclipseAppLauncher .start(EclipseAppLauncher.java:76)
>>
>> at
>> org.eclipse.core.runtime.adaptor.EclipseStarter.run(EclipseS tarter.java:363)
>>
>> at
>> org.eclipse.core.runtime.adaptor.EclipseStarter.run(EclipseS tarter.java:176)
>>
>> at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
>> at sun.reflect.NativeMethodAccessorImpl.invoke(Unknown Source)
>> at sun.reflect.DelegatingMethodAccessorImpl.invoke(Unknown Source)
>> at java.lang.reflect.Method.invoke(Unknown Source)
>> at org.eclipse.equinox.launcher.Main.invokeFramework(Main.java: 508)
>> at org.eclipse.equinox.launcher.Main.basicRun(Main.java:447)
>> at org.eclipse.equinox.launcher.Main.run(Main.java:1173)
>> at org.eclipse.equinox.launcher.Main.main(Main.java:1148)
>
Re: Using Model Listeners / Adapters in AbstractPropertySections [message #417060 is a reply to message #417059] Mon, 25 February 2008 16:39 Go to previous message
Ed Merks is currently offline Ed MerksFriend
Messages: 33113
Registered: July 2009
Senior Member
This is a multi-part message in MIME format.
--------------070008000607030203070207
Content-Type: text/plain; charset=ISO-8859-15; format=flowed
Content-Transfer-Encoding: 7bit

Tobias,

The new version of the EMF books is greatly expanded from the first
edition, with lots of examples, and is available in draft from

http://safari.informit.com/9780321331885

Rich is working on a book as well...


Tobias wrote:
> Thank you Ed, you just saved my day (again). ^^;;
>
> So the problem realy was that - as I assumed - the
> aboutToBeShown/Hidden methods are not enough. Now that I'm updating
> the adapter in setInput (and dispose, just to be sure), too,
> everything seems to work fine. Not one crash so far and no
> mysteriously multiplying adapters. Maybe the article [1] should be
> extended in this direction.
>
> I'll try to look into whether there's a difference in returning true
> or false in the isAdapterForType method in my case.
>
> Concerning the 'big-big-framework'-problem: I think what's making
> parts of EMF/GMF so hard to understand is the high potion of generated
> code you have to hook your stuff into along with the numerous super
> classes doing all kinds fo stuff "behind your back" (which, of course,
> is a good thing, generally spoken). Do you know of any good book on
> this topic? I do not mean a book how to create a EMF-based editor from
> scratch, like the famous 'red book', but more the cook-book type,
> offering solutions for all kinds of problems (possibly even specific
> for GMF).
>
> Tobias
>
>
> Ed Merks schrieb:
>> Tobias,
>>
>> Comments below.
>>
>> Tobias wrote:
>>> Hello,
>>>
>>> I have to admid that I'm still quite inexperienced in the use of the
>>> Adapters-Framework. I know that this is one of the core components
>>> of the EMF framework and that it's of great help, but it's also
>>> quite complicated...
>> Complexity is always a relative thing. New things will always appear
>> to be complex and often more complex than necessary. Once you learn
>> they, they typically appear simple and intuitive...
>>>
>>> However, I have a GMF editor for which I've created a set of
>>> AdvancedPropertySections following the guide at [1]. In section
>>> "Model Listeners" it is written where to register and deregister
>>> Listeners for the model elements. After a quick research on the
>>> Adapters framework I've implemented the methods as shown in [2] in
>>> the parent class of all my PropertySections. This seems to work
>>> quite well, in that I can set a property, hit the undo-Button
>>> (changing the property outside of the view, which was the major
>>> motivation for trying this) and the change is also undone in the
>>> property section.
>>>
>>> 1.: Honestly I have no clue when to return true in the
>>> isAdapterForType-methods, since the type is always the same, namely
>>> my ItemProviderAdapterFactory. However, returning false seems to
>>> have no effect anyway...
>> Some places you'll see it being used are in AdapterFactoryImpl
>>
>> | *public *Adapter adapt(Notifier target, Object type)
>> {
>> *for *(Adapter adapter : target.eAdapters())
>> {
>> *if *(adapter.isAdapterForType(type))
>> {
>> *return *adapter;
>> }
>> }
>> *return *adaptNew(target, type);
>> }|
>>
>> And EcoreUtil:
>>
>> | /**
>> * Returns the adapter of the specified type.
>> * @param adapters list of adapters to search.
>> * @param type the type of adapter.
>> * @return an adapter from the list or null.
>> */
>> *public static *Adapter getAdapter(List<Adapter> adapters,
>> Object type)
>> {
>> *for *(*int *i = 0, size = adapters.size(); i < size; ++i)
>> {
>> Adapter adapter = adapters.get(i);
>> *if *(adapter.isAdapterForType(type))
>> {
>> *return *adapter;
>> }
>> }
>> *return null*;
>> }|
>>
>> If you aren't using a factory and aren't looking up your adapter by
>> type, it doesn't matter that you always return false.
>>> 2.: I think aboutToBeShown is not the best place for registering the
>>> listeners, since it is not called again when switching to another
>>> node of the same type. Maybe this sould (also) be done in the
>>> setInput method?
>> I'm not sure where the best hooks are. I imagine you should clean
>> them up whenever a new input is set or when the section itself is
>> disposed. The basic EMF properties view is always just refreshed
>> whenever a command is executed. I.e., there are no fine-grained
>> notifications to keep it up to date. Perhaps that approach would be
>> simpler...
>>> 3.: Most time it works fine, but occasionally it crashes [3]. This
>>> can occur when making a change and changing the selection, when
>>> making no changes and changing the text field (I'm using
>>> focusListeners), and possible a number of other occasions -- I have
>>> not found a pattern yet. But it's always the refresh method being
>>> called by notifyChanged which crashes.
>> Sounds likely the result of not cleaning up the adapters.
>>>
>>> So obviously this is not a very clean implementation, so I would
>>> appreciate any hints or comments or links to (understandable ^^;)
>>> tutorials on this topic, if you know any.
>>>
>>> Regards,
>>> Tobias
>>>
>>> [1]
>>> < http://www.eclipse.org/articles/Article-Tabbed-Properties/ta bbed_properties_view.html>
>>>
>>>
>>>
>>> [2] private Adapter myAdapter= new Adapter() {
>>> EObject target= null;
>>> public Notifier getTarget() {
>>> return target;
>>> }
>>> public boolean isAdapterForType(Object type) {
>>> return false;
>>> }
>>> public void notifyChanged(Notification notification) {
>>> refresh();
>>> }
>>> public void setTarget(Notifier newTarget) {
>>> if (newTarget instanceof EObject) {
>>> target= (EObject) newTarget;
>>> }
>>> }
>>> };
>>>
>>> @Override
>>> public void aboutToBeShown() {
>>> super.aboutToBeShown();
>>> myAdapter.setTarget(eObject);
>>> eObject.eAdapters().add(myAdapter);
>>> }
>>>
>>> @Override
>>> public void aboutToBeHidden() {
>>> super.aboutToBeHidden();
>>> eObject.eAdapters().remove(myAdapter);
>>> }
>>>
>>>
>>> [3] org.eclipse.swt.SWTException: Widget is disposed
>>> at org.eclipse.swt.SWT.error(SWT.java:3563)
>>> at org.eclipse.swt.SWT.error(SWT.java:3481)
>>> at org.eclipse.swt.SWT.error(SWT.java:3452)
>>> at org.eclipse.swt.widgets.Widget.error(Widget.java:432)
>>> at org.eclipse.swt.widgets.Widget.checkWidget(Widget.java:325)
>>> at org.eclipse.swt.widgets.Text.setText(Text.java:1793)
>>> at
>>> XXX.diagram.properties.sections.IdObjectSection.refresh(IdOb jectSection.java:50)
>>>
>>> at
>>> XXX.diagram.properties.sections.AbstractVsdtPropertySection$ 1.notifyChanged(AbstractVsdtPropertySection.java:117)
>>>
>>> at
>>> org.eclipse.emf.common.notify.impl.BasicNotifierImpl$EAdapte rList.didRemove(BasicNotifierImpl.java:95)
>>>
>>> at
>>> org.eclipse.emf.common.util.BasicEList.didClear(BasicEList.j ava:260)
>>> at
>>> org.eclipse.emf.common.util.BasicEList.clear(BasicEList.java :1000)
>>> at
>>> org.eclipse.emf.common.notify.impl.BasicNotifierImpl$EAdapte rList.clear(BasicNotifierImpl.java:171)
>>>
>>> at
>>> org.eclipse.emf.ecore.resource.impl.ResourceImpl.unloaded(Re sourceImpl.java:1420)
>>>
>>> at
>>> org.eclipse.emf.ecore.resource.impl.ResourceImpl.doUnload(Re sourceImpl.java:1479)
>>>
>>> at
>>> org.eclipse.emf.ecore.xmi.impl.XMLResourceImpl.doUnload(XMLR esourceImpl.java:505)
>>>
>>> at
>>> org.eclipse.emf.ecore.resource.impl.ResourceImpl.unload(Reso urceImpl.java:1494)
>>>
>>> at
>>> de.dailab.sercho.vsdt.diagram.part.VsdtDocumentProvider$Reso urceSetInfo.dispose(VsdtDocumentProvider.java:877)
>>>
>>> at
>>> de.dailab.sercho.vsdt.diagram.part.VsdtDocumentProvider.disp oseElementInfo(VsdtDocumentProvider.java:328)
>>>
>>> at
>>> org.eclipse.gmf.runtime.diagram.ui.resources.editor.document .AbstractDocumentProvider.disconnect(AbstractDocumentProvide r.java:425)
>>>
>>> at
>>> org.eclipse.gmf.runtime.diagram.ui.resources.editor.parts.Di agramDocumentEditor.disposeDocumentProvider(DiagramDocumentE ditor.java:481)
>>>
>>> at
>>> org.eclipse.gmf.runtime.diagram.ui.resources.editor.parts.Di agramDocumentEditor.dispose(DiagramDocumentEditor.java:177)
>>>
>>> at
>>> org.eclipse.ui.internal.WorkbenchPartReference.doDisposePart (WorkbenchPartReference.java:720)
>>>
>>> at
>>> org.eclipse.ui.internal.EditorReference.doDisposePart(Editor Reference.java:306)
>>>
>>> at
>>> org.eclipse.ui.internal.WorkbenchPartReference.dispose(Workb enchPartReference.java:671)
>>>
>>> at
>>> org.eclipse.ui.internal.WorkbenchPage.disposePart(WorkbenchP age.java:1604)
>>>
>>> at
>>> org.eclipse.ui.internal.WorkbenchPage.handleDeferredEvents(W orkbenchPage.java:1354)
>>>
>>> at
>>> org.eclipse.ui.internal.WorkbenchPage.deferUpdates(Workbench Page.java:1338)
>>>
>>> at
>>> org.eclipse.ui.internal.WorkbenchPage.closeEditors(Workbench Page.java:1312)
>>>
>>> at
>>> org.eclipse.ui.internal.WorkbenchPage.closeEditor(WorkbenchP age.java:1367)
>>>
>>> at org.eclipse.ui.internal.EditorPane.doHide(EditorPane.java:61 )
>>> at org.eclipse.ui.internal.PartStack.close(PartStack.java:543)
>>> at org.eclipse.ui.internal.EditorStack.close(EditorStack.java:2 06)
>>> at org.eclipse.ui.internal.PartStack$1.close(PartStack.java:122 )
>>> at
>>> org.eclipse.ui.internal.presentations.util.TabbedStackPresen tation$1.handleEvent(TabbedStackPresentation..java:81)
>>>
>>> at
>>> org.eclipse.ui.internal.presentations.util.AbstractTabFolder .fireEvent(AbstractTabFolder.java:267)
>>>
>>> at
>>> org.eclipse.ui.internal.presentations.util.AbstractTabFolder .fireEvent(AbstractTabFolder.java:276)
>>>
>>> at
>>> org.eclipse.ui.internal.presentations.defaultpresentation.De faultTabFolder.access$1(DefaultTabFolder.java:1)
>>>
>>> at
>>> org.eclipse.ui.internal.presentations.defaultpresentation.De faultTabFolder$1.closeButtonPressed(DefaultTabFolder.java:67 )
>>>
>>> at
>>> org.eclipse.ui.internal.presentations.PaneFolder.notifyClose Listeners(PaneFolder.java:596)
>>>
>>> at
>>> org.eclipse.ui.internal.presentations.PaneFolder$3.close(Pan eFolder.java:189)
>>>
>>> at org.eclipse.swt.custom.CTabFolder.onMouse(CTabFolder.java:21 59)
>>> at
>>> org.eclipse.swt.custom.CTabFolder$1.handleEvent(CTabFolder.j ava:320)
>>> at org.eclipse.swt.widgets.EventTable.sendEvent(EventTable.java :66)
>>> at org.eclipse.swt.widgets.Widget.sendEvent(Widget.java:938)
>>> at
>>> org.eclipse.swt.widgets.Display.runDeferredEvents(Display.ja va:3682)
>>> at
>>> org.eclipse.swt.widgets.Display.readAndDispatch(Display.java :3293)
>>> at
>>> org.eclipse.ui.internal.Workbench.runEventLoop(Workbench.jav a:2389)
>>> at org.eclipse.ui.internal.Workbench.runUI(Workbench.java:2353)
>>> at org.eclipse.ui.internal.Workbench.access$4(Workbench.java:22 19)
>>> at org.eclipse.ui.internal.Workbench$4.run(Workbench.java:466)
>>> at
>>> org.eclipse.core.databinding.observable.Realm.runWithDefault (Realm.java:289)
>>>
>>> at
>>> org.eclipse.ui.internal.Workbench.createAndRunWorkbench(Work bench.java:461)
>>>
>>> at
>>> org.eclipse.ui.PlatformUI.createAndRunWorkbench(PlatformUI.j ava:149)
>>> at
>>> org.eclipse.ui.internal.ide.application.IDEApplication.start (IDEApplication.java:106)
>>>
>>> at
>>> org.eclipse.equinox.internal.app.EclipseAppHandle.run(Eclips eAppHandle.java:169)
>>>
>>> at
>>> org.eclipse.core.runtime.internal.adaptor.EclipseAppLauncher .runApplication(EclipseAppLauncher.java:106)
>>>
>>> at
>>> org.eclipse.core.runtime.internal.adaptor.EclipseAppLauncher .start(EclipseAppLauncher.java:76)
>>>
>>> at
>>> org.eclipse.core.runtime.adaptor.EclipseStarter.run(EclipseS tarter.java:363)
>>>
>>> at
>>> org.eclipse.core.runtime.adaptor.EclipseStarter.run(EclipseS tarter.java:176)
>>>
>>> at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
>>> at sun.reflect.NativeMethodAccessorImpl.invoke(Unknown Source)
>>> at sun.reflect.DelegatingMethodAccessorImpl.invoke(Unknown Source)
>>> at java.lang.reflect.Method.invoke(Unknown Source)
>>> at org.eclipse.equinox.launcher.Main.invokeFramework(Main.java: 508)
>>> at org.eclipse.equinox.launcher.Main.basicRun(Main.java:447)
>>> at org.eclipse.equinox.launcher.Main.run(Main.java:1173)
>>> at org.eclipse.equinox.launcher.Main.main(Main.java:1148)
>>


--------------070008000607030203070207
Content-Type: text/html; charset=ISO-8859-15
Content-Transfer-Encoding: 8bit

<!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN">
<html>
<head>
<meta content="text/html;charset=ISO-8859-15"
http-equiv="Content-Type">
</head>
<body bgcolor="#ffffff" text="#000000">
Tobias,<br>
<br>
The new version of the EMF books is greatly expanded from the first
edition, with lots of examples, and is available in draft from<br>
<blockquote><a href="http://safari.informit.com/9780321331885">http://safari.informit.com/9780321331885</a><br>
</blockquote>
Rich is working on a book as well...<br>
<br>
<br>
Tobias wrote:
<blockquote cite="mid:fpuq15$mmq$1@build.eclipse.org" type="cite">Thank
you Ed, you just saved my day (again). ^^;;
<br>
<br>
So the problem realy was that - as I assumed - the
aboutToBeShown/Hidden methods are not enough. Now that I'm updating the
adapter in setInput (and dispose, just to be sure), too, everything
seems to work fine. Not one crash so far and no mysteriously
multiplying adapters. Maybe the article [1] should be extended in this
direction.
<br>
<br>
I'll try to look into whether there's a difference in returning true or
false in the isAdapterForType method in my case.
<br>
<br>
Concerning the 'big-big-framework'-problem: I think what's making parts
of EMF/GMF so hard to understand is the high potion of generated code
you have to hook your stuff into along with the numerous super classes
doing all kinds fo stuff "behind your back" (which, of course, is a
good thing, generally spoken). Do you know of any good book on this
topic? I do not mean a book how to create a EMF-based editor from
scratch, like the famous 'red book', but more the cook-book type,
offering solutions for all kinds of problems (possibly even specific
for GMF).
<br>
<br>
Tobias
<br>
<br>
<br>
Ed Merks schrieb:
<br>
<blockquote type="cite">


Ed Merks
Professional Support: https://www.macromodeling.com/
Previous Topic:How to listen to EMF clipboard?
Next Topic:How to access EList template type at runtime
Goto Forum:
  


Current Time: Fri Mar 29 09:57:35 GMT 2024

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

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

Back to the top