Skip to main content


Eclipse Community Forums
Forum Search:

Search      Help    Register    Login    Home
Home » Modeling » EMF » synchronize form editor with emf editing domain
synchronize form editor with emf editing domain [message #413672] Tue, 09 October 2007 12:54 Go to next message
Norbert  Schöpke is currently offline Norbert SchöpkeFriend
Messages: 63
Registered: July 2009
Member
Hello EMF folks

I'm currently developing a form editor for my ECore model. I studied the source of the EMF-generated editor, but it only
contains editors/viewers using the ContentProvider approach. What I need however, is a handle to the model to traverse
it and build form sections with text fields for each property I want the user to edit (the structure of the model should
not be editable, only the attribute values).
How can I do this and still be able to leverage the editing domain for saving and resource change management? Do I need
to crawl through the PDE editor sources or is there some easier way?

Thx for any advice

Norbert Schöpke
Re: synchronize form editor with emf editing domain [message #413673 is a reply to message #413672] Tue, 09 October 2007 13:16 Go to previous messageGo to next message
Eric Rizzo is currently offline Eric RizzoFriend
Messages: 3070
Registered: July 2009
Senior Member
Norbert Schöpke wrote:
> Hello EMF folks
>
> I'm currently developing a form editor for my ECore model. I studied
> the source of the EMF-generated editor, but it only contains
> editors/viewers using the ContentProvider approach. What I need
> however, is a handle to the model to traverse it and build form
> sections with text fields for each property I want the user to edit
> (the structure of the model should not be editable, only the
> attribute values). How can I do this and still be able to leverage
> the editing domain for saving and resource change management? Do I
> need to crawl through the PDE editor sources or is there some easier
> way?

I've worked on two projects that implemented Forms-based editors for EMF
models. What I did was create an abstract subclass of FormEditor and in
its init() method deserilialize the model object from the IEditorInput.
To create an EditingDomain, I first get the AdapterFactoryEditingDomain
from the generated editor class; I really only want the AdapterFactory
from it, because the EditingDomain itself has stuff that is specific to
the generated editor. So I create a new AdapterFactoryEditingDomain with
the AdapterFactory that I got from the generated editor EditingDomain
(that's a mouthful, isn't it:-) and a BasicCommandStack that I create
myself. I wish there was a better way to get an instance of a valid
EditingDomain, so maybe one of the EMF developers can chime in here...

You can attach a CommandStackListener to call editorDirtyStateChanged()
if all model modifications will go through EMF commands, thus getting
editor dirty state management without having to rely on the ManagedForm
mechanism. (don't forget to notify the CommandStack when doSave() is
called).

Hope this helps,
Eric
Re: synchronize form editor with emf editing domain [message #413675 is a reply to message #413673] Tue, 09 October 2007 13:32 Go to previous messageGo to next message
Norbert  Schöpke is currently offline Norbert SchöpkeFriend
Messages: 63
Registered: July 2009
Member
Wow, many thx for the reply!
I'll try to get on with this, although on first read I only understood half of it...
Anyway now I know it can be done, so I'm feeling a lot better!
thx
Norbert
Re: synchronize form editor with emf editing domain [message #413688 is a reply to message #413673] Tue, 09 October 2007 17:22 Go to previous messageGo to next message
Steve Blass is currently offline Steve BlassFriend
Messages: 276
Registered: July 2009
Senior Member
Another approach is to place form pages directly into ViewerPanes in the
generated editor so that all the generated edit/editor tooling is
available to the forms. Doing that a few times led to creation of a
plug-in defining an extension point for form page tabs, a form page tab
interface and a small patch for Editor.javajet so that EMF will generate
editors that can pick up form pages to include as editor tabs through
this extension point at run time. I need to verify permission to share
the basic implementation before I post code.

-
Steve


Eric Rizzo wrote:
> Norbert Schöpke wrote:
>> Hello EMF folks
>>
>> I'm currently developing a form editor for my ECore model. I studied
>> the source of the EMF-generated editor, but it only contains
>> editors/viewers using the ContentProvider approach. What I need
>> however, is a handle to the model to traverse it and build form
>> sections with text fields for each property I want the user to edit
>> (the structure of the model should not be editable, only the
>> attribute values). How can I do this and still be able to leverage
>> the editing domain for saving and resource change management? Do I
>> need to crawl through the PDE editor sources or is there some easier
>> way?
>
> I've worked on two projects that implemented Forms-based editors for EMF
> models. What I did was create an abstract subclass of FormEditor and in
> its init() method deserilialize the model object from the IEditorInput.
> To create an EditingDomain, I first get the AdapterFactoryEditingDomain
> from the generated editor class; I really only want the AdapterFactory
> from it, because the EditingDomain itself has stuff that is specific to
> the generated editor. So I create a new AdapterFactoryEditingDomain with
> the AdapterFactory that I got from the generated editor EditingDomain
> (that's a mouthful, isn't it:-) and a BasicCommandStack that I create
> myself. I wish there was a better way to get an instance of a valid
> EditingDomain, so maybe one of the EMF developers can chime in here...
>
> You can attach a CommandStackListener to call editorDirtyStateChanged()
> if all model modifications will go through EMF commands, thus getting
> editor dirty state management without having to rely on the ManagedForm
> mechanism. (don't forget to notify the CommandStack when doSave() is
> called).
>
> Hope this helps,
> Eric
Re: synchronize form editor with emf editing domain [message #413707 is a reply to message #413688] Wed, 10 October 2007 08:24 Go to previous messageGo to next message
Norbert  Schöpke is currently offline Norbert SchöpkeFriend
Messages: 63
Registered: July 2009
Member
sounds cool to me...please let me know if it's possible.
Are there instructions on how to patch EMF? Because i never patched anything Eclipse at all...

thx anyway
Norbert
Re: synchronize form editor with emf editing domain [message #413732 is a reply to message #413707] Wed, 10 October 2007 20:34 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.
--------------070808000200080602020307
Content-Type: text/plain; charset=ISO-8859-1; format=flowed
Content-Transfer-Encoding: 8bit

Norbert,

Here's a project file set for the projects I extract from CVS which
shows where to get the projects; it includes way more than you'll need,
but if you use it (File->Import...->Team->Team Project File Set) to get
the codegen.ecore plugin, you'll be able to apply (popup on any project
Team->Apply patch) patches.


Norbert Sch


Ed Merks
Professional Support: https://www.macromodeling.com/
Re: synchronize form editor with emf editing domain [message #413878 is a reply to message #413672] Wed, 17 October 2007 12:06 Go to previous messageGo to next message
Norbert  Schöpke is currently offline Norbert SchöpkeFriend
Messages: 63
Registered: July 2009
Member
Thanks again for the help.
I managed to get my form working with the editing domain (will post my solution in a separate reply).
However, I do have problems with updating the form upon resource changes.
I have my resource change listener running and it kicks in correctly when it should, only I can't get my form to display
the updated GUI ( the form itself may change, not only the values). I tried to call the dispose() method followed by
createPartControl(this.getPartControl().getParent());

But it just keeps displaying the outdated GUI. I checked if the editing domains resource really contains the new data,
and it does. How can I just replace my form-page contents from scratch?

thx
Norbert

btw. if this question is too off-topic, I'd like to know where i can ask eclispe forms specific questions
Re: synchronize form editor with emf editing domain [message #413879 is a reply to message #413878] Wed, 17 October 2007 12:09 Go to previous messageGo to next message
Ed Merks is currently offline Ed MerksFriend
Messages: 33113
Registered: July 2009
Senior Member
Norbert,

I really don't know anything about forms. Likely Steve will know. If
not, I think the best place to ask would be the platform newsgroup.
news://news.eclipse.org/eclipse.platform


Norbert Schöpke wrote:
> Thanks again for the help.
> I managed to get my form working with the editing domain (will post my solution in a separate reply).
> However, I do have problems with updating the form upon resource changes.
> I have my resource change listener running and it kicks in correctly when it should, only I can't get my form to display
> the updated GUI ( the form itself may change, not only the values). I tried to call the dispose() method followed by
> createPartControl(this.getPartControl().getParent());
>
> But it just keeps displaying the outdated GUI. I checked if the editing domains resource really contains the new data,
> and it does. How can I just replace my form-page contents from scratch?
>
> thx
> Norbert
>
> btw. if this question is too off-topic, I'd like to know where i can ask eclispe forms specific questions
>


Ed Merks
Professional Support: https://www.macromodeling.com/
Re: synchronize form editor with emf editing domain (solution) [message #413880 is a reply to message #413672] Wed, 17 October 2007 13:16 Go to previous messageGo to next message
Norbert  Schöpke is currently offline Norbert SchöpkeFriend
Messages: 63
Registered: July 2009
Member
Ok, here's what I did to create my Eclipse form from my .ecore model.

First of all, I studied the EMF-generated editor for my domain model and re-used all of the resource-management
boilerplate code like saving, handling resource changes and so on. I left out the SelectionProvider stuff since I didn't
need it (having no property sheet and no outline view).
I merged this code with the SimpleFormEditor from the Forms Article (found at
http://www.eclipse.org/articles/Article-Forms/article.html).

Now the real work starts: Form what I understand, one needs the following things to get this working:
ComposedAdapterFactory : this adapts all the ItemProvider stuff from the EMF-generated .edit plugin to suit your needs
AdapterFactoryEditingDomain : this is the read/write interface to your model's resource, it needs the adapter factory
and a command stack
AdapterFactoryItemDelegator : delegates from a model element (item) to the respective item provider from the .edit plugin
AdapterFactoryLabelProvider : gets text for your model elements by asking the item provider
BasicCommandStack : well...a basic command stack with some undo/redo support

Most important is the setup of these components. I put it in a method "initializeEditingDomain" which I call in the form
editor's constructor:

protected void initializeEditingDomain() {
// Create an adapter factory that yields item providers.
// For this to work this plugin needs the dependency on the
// EMF edit plugin generated from the ThetaML .ecore and .genmodel
adapterFactory = new ComposedAdapterFactory(
ComposedAdapterFactory.Descriptor.Registry.INSTANCE);

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

// command stack that will notify this editor as commands are executed
BasicCommandStack commandStack = new BasicCommandStack();

// Add a listener to set the editor dirty of commands have been executed
commandStack.addCommandStackListener(new CommandStackListener() {
public void commandStackChanged(final EventObject event) {
getContainer().getDisplay().asyncExec(new Runnable() {
public void run() {
editorDirtyStateChanged();
}
});
}
});

// Create the editing domain with our adapterFactory and command stack.
//
editingDomain = new AdapterFactoryEditingDomain(adapterFactory,
commandStack, new HashMap<Resource, Boolean>());

// These provide access to the model items, their property source and label
itemDelegator = new AdapterFactoryItemDelegator(adapterFactory);
labelProvider = new AdapterFactoryLabelProvider(adapterFactory);
}


Next you have to create your model. You have to do this by loading it's resource into the editing domain.
I call the respective code in the "init" method, which gets called shortly after the constructor.
Here I also add in the part listener and resource change listener.

public void init(IEditorSite site, IEditorInput editorInput)
throws PartInitException {
super.init(site, editorInput);
setPartName(editorInput.getName());
site.getPage().addPartListener(partListener);
createModel();
// TODO
ResourcesPlugin.getWorkspace().addResourceChangeListener(res ourceChangeListener,
IResourceChangeEvent.POST_CHANGE);
}


private void createModel() {

URI resourceURI = EditUIUtil.getURI(getEditorInput());
Resource resource = null;
try {
// Load the resource through the editing domain.
resource = editingDomain.getResourceSet().getResource(resourceURI,
true);
} catch (Exception e) {
resource = editingDomain.getResourceSet().getResource(resourceURI,
false);
}

if (resource != null) {
this.thetaml = (ThetaML) resource.getContents().get(0);
}
}

"ThetaML" is just the root of my .ecore model. Now I can use it in the pages to be added to construct widgets for any of
it's properties.


Now, of course, each form will look different, so I'll just sketch out what one has to do the build a widget for an
element in the model.

If you have the element instance (of the element class in the EMF-generated model code), you can instruct the
above-mentioned ItemDelegator to fetch so-called "property descriptors" for this element. Just iterate over this list
and for every IItemPropertyDescriptor "descriptor" you get, you call

EObject feature = (EObject) descriptor.getFeature(your_element_instance);

Now you may introspect this thingie and decide what widget you want to create for it.
The actual value you get by calling

Object value = ((EObject) editor.getItemDelegator().getEditableValue(your_element_inst ance)).eGet(your_feature_instance)

In most cases it will be a String value, so you may just create a text field for it.

Text text = toolkit.createText(client, valueString, SWT.SINGLE);

To update your model when user modifies the value in the GUI, you have to handle this

if (value instanceof String) {
text.addModifyListener(new ModifyListener() {
public void modifyText(ModifyEvent event) {
for (IItemPropertyDescriptor descriptor2 : variablePropertyDescriptors) {
if (descriptor2.getId(formula).equals(descriptor.getId(formula) )) {
String newValueText = ((Text) event.widget).getText();
descriptor2.setPropertyValue(your_element_instance, newValueText);
}
}
}
});
}


(Note: the descriptor used here - our loop variable - needs to be final)

The line where setPropertyValue is called is the important one - here the magic happens. This call is delegated to the
ItemProvider for the element you used and a SetCommand is created, added to the command stack we setup for our editing
domain, and executed. All editor state management like mark dirty, save, undo/redo is handled for you by EMF.

So thats basically it. Your mileage may vary.
Norbert

Note to the dev's: I had to debug into how the EMF-generated editor and the simpleFormEditor works for several hours to
grasp this and I'm still not sure if there is a better, "canonical" way to do this. The classes and interfaces I visited
on the way were hard to understand for the average eclipse monkey (which I still consider myself to be ;)).
The generated editor is a nice starting point but more useful would be a couple of classes which consitute the basis on
which to build an editor (not necessarily a tree editor). What I mean is I want simple and well-documented functionalty
to establish an editing domain for my model (maybe this could be done with an extension point?) and get/set values for
the elements of my domain.
Re: synchronize form editor with emf editing domain (solution) [message #413883 is a reply to message #413880] Wed, 17 October 2007 13:31 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.
--------------000706010100090603030402
Content-Type: text/plain; charset=ISO-8859-1; format=flowed
Content-Transfer-Encoding: 8bit

Norbert,

Thanks. This is very helpful! Perhaps you'd like to put it into the
wiki as a recipe.

http://wiki.eclipse.org/EMF/Recipes

The core development team currently doesn't even have spare cycles to do
development work (they're busy working on an appendix for the second
edition of the EMF book to cover the things added for EMF 2.3) so we
don't have time for other helpful things either. What would be really
cool is if other folks will do like you've done and simply document
their experiences and insights in the wiki. Then the next guy will have
a better starting point, and can improve on it. And ultimately the
development team will understand where the biggest gaps are and what
people are doing with the frameworks so we can create useful utilities
to make these things easier and help flesh out the documentation.
Thanks so much for contributing back!


Norbert Sch


Ed Merks
Professional Support: https://www.macromodeling.com/
Re: synchronize form editor with emf editing domain (solution) [message #413887 is a reply to message #413883] Wed, 17 October 2007 16:50 Go to previous messageGo to next message
Norbert  Schöpke is currently offline Norbert SchöpkeFriend
Messages: 63
Registered: July 2009
Member
ok, done
If I got something wrong, maybe you could post me a hint or just correct it
Re: synchronize form editor with emf editing domain (solution) [message #413889 is a reply to message #413887] Wed, 17 October 2007 17:02 Go to previous messageGo to next message
Ed Merks is currently offline Ed MerksFriend
Messages: 33113
Registered: July 2009
Senior Member
Norbert,

Awesome! I made a few minor typographical fixes; it looks great.

Norbert Schöpke wrote:
> ok, done
> If I got something wrong, maybe you could post me a hint or just correct it
>


Ed Merks
Professional Support: https://www.macromodeling.com/
Re: synchronize form editor with emf editing domain [message #413890 is a reply to message #413879] Wed, 17 October 2007 17:21 Go to previous messageGo to next message
Steve Blass is currently offline Steve BlassFriend
Messages: 276
Registered: July 2009
Senior Member
I'm not 100% sure how to cleanly add/change/delete the actual widgets on
the form on the fly but there were a couple of planet eclipse posts in
the last week or so about disposing/hiding widgets in SWT layouts that
might help. I think you would need to basically rebuild the form. The
code for the details part of the MasterDetailsBlock might be a guide but
even there the details pages are only each created once.

-
Steve


Ed Merks wrote:
> Norbert,
>
> I really don't know anything about forms. Likely Steve will know. If
> not, I think the best place to ask would be the platform newsgroup.
> news://news.eclipse.org/eclipse.platform
>
>
> Norbert Schöpke wrote:
>> Thanks again for the help.
>> I managed to get my form working with the editing domain (will post my
>> solution in a separate reply).
>> However, I do have problems with updating the form upon resource changes.
>> I have my resource change listener running and it kicks in correctly
>> when it should, only I can't get my form to display
>> the updated GUI ( the form itself may change, not only the values). I
>> tried to call the dispose() method followed by
>> createPartControl(this.getPartControl().getParent());
>>
>> But it just keeps displaying the outdated GUI. I checked if the
>> editing domains resource really contains the new data,
>> and it does. How can I just replace my form-page contents from scratch?
>>
>> thx
>> Norbert
>>
>> btw. if this question is too off-topic, I'd like to know where i can
>> ask eclispe forms specific questions
>>
Re: synchronize form editor with emf editing domain (solution) [message #413891 is a reply to message #413880] Wed, 17 October 2007 17:24 Go to previous messageGo to next message
Steve Blass is currently offline Steve BlassFriend
Messages: 276
Registered: July 2009
Senior Member
> addModifyListener(

I've run into notification cascades with ModifyListeners attached to
text widgets in forms because it updates on every character you type.
Switching to FocusListeners and updating the value when the widget loses
focus stopped some of that for me.
-
Steve


Norbert Schöpke wrote:
> Ok, here's what I did to create my Eclipse form from my .ecore model.
>
> First of all, I studied the EMF-generated editor for my domain model and re-used all of the resource-management
> boilerplate code like saving, handling resource changes and so on. I left out the SelectionProvider stuff since I didn't
> need it (having no property sheet and no outline view).
> I merged this code with the SimpleFormEditor from the Forms Article (found at
> http://www.eclipse.org/articles/Article-Forms/article.html).
>
> Now the real work starts: Form what I understand, one needs the following things to get this working:
> ComposedAdapterFactory : this adapts all the ItemProvider stuff from the EMF-generated .edit plugin to suit your needs
> AdapterFactoryEditingDomain : this is the read/write interface to your model's resource, it needs the adapter factory
> and a command stack
> AdapterFactoryItemDelegator : delegates from a model element (item) to the respective item provider from the .edit plugin
> AdapterFactoryLabelProvider : gets text for your model elements by asking the item provider
> BasicCommandStack : well...a basic command stack with some undo/redo support
>
> Most important is the setup of these components. I put it in a method "initializeEditingDomain" which I call in the form
> editor's constructor:
>
> protected void initializeEditingDomain() {
> // Create an adapter factory that yields item providers.
> // For this to work this plugin needs the dependency on the
> // EMF edit plugin generated from the ThetaML .ecore and .genmodel
> adapterFactory = new ComposedAdapterFactory(
> ComposedAdapterFactory.Descriptor.Registry.INSTANCE);
>
> adapterFactory
> .addAdapterFactory(new ResourceItemProviderAdapterFactory());
> adapterFactory
> .addAdapterFactory(new ThetamlItemProviderAdapterFactory());
> adapterFactory
> .addAdapterFactory(new ReflectiveItemProviderAdapterFactory());
>
> // command stack that will notify this editor as commands are executed
> BasicCommandStack commandStack = new BasicCommandStack();
>
> // Add a listener to set the editor dirty of commands have been executed
> commandStack.addCommandStackListener(new CommandStackListener() {
> public void commandStackChanged(final EventObject event) {
> getContainer().getDisplay().asyncExec(new Runnable() {
> public void run() {
> editorDirtyStateChanged();
> }
> });
> }
> });
>
> // Create the editing domain with our adapterFactory and command stack.
> //
> editingDomain = new AdapterFactoryEditingDomain(adapterFactory,
> commandStack, new HashMap<Resource, Boolean>());
>
> // These provide access to the model items, their property source and label
> itemDelegator = new AdapterFactoryItemDelegator(adapterFactory);
> labelProvider = new AdapterFactoryLabelProvider(adapterFactory);
> }
>
>
> Next you have to create your model. You have to do this by loading it's resource into the editing domain.
> I call the respective code in the "init" method, which gets called shortly after the constructor.
> Here I also add in the part listener and resource change listener.
>
> public void init(IEditorSite site, IEditorInput editorInput)
> throws PartInitException {
> super.init(site, editorInput);
> setPartName(editorInput.getName());
> site.getPage().addPartListener(partListener);
> createModel();
> // TODO
> ResourcesPlugin.getWorkspace().addResourceChangeListener(res ourceChangeListener,
> IResourceChangeEvent.POST_CHANGE);
> }
>
>
> private void createModel() {
>
> URI resourceURI = EditUIUtil.getURI(getEditorInput());
> Resource resource = null;
> try {
> // Load the resource through the editing domain.
> resource = editingDomain.getResourceSet().getResource(resourceURI,
> true);
> } catch (Exception e) {
> resource = editingDomain.getResourceSet().getResource(resourceURI,
> false);
> }
>
> if (resource != null) {
> this.thetaml = (ThetaML) resource.getContents().get(0);
> }
> }
>
> "ThetaML" is just the root of my .ecore model. Now I can use it in the pages to be added to construct widgets for any of
> it's properties.
>
>
> Now, of course, each form will look different, so I'll just sketch out what one has to do the build a widget for an
> element in the model.
>
> If you have the element instance (of the element class in the EMF-generated model code), you can instruct the
> above-mentioned ItemDelegator to fetch so-called "property descriptors" for this element. Just iterate over this list
> and for every IItemPropertyDescriptor "descriptor" you get, you call
>
> EObject feature = (EObject) descriptor.getFeature(your_element_instance);
>
> Now you may introspect this thingie and decide what widget you want to create for it.
> The actual value you get by calling
>
> Object value = ((EObject) editor.getItemDelegator().getEditableValue(your_element_inst ance)).eGet(your_feature_instance)
>
> In most cases it will be a String value, so you may just create a text field for it.
>
> Text text = toolkit.createText(client, valueString, SWT.SINGLE);
>
> To update your model when user modifies the value in the GUI, you have to handle this
>
> if (value instanceof String) {
> text.addModifyListener(new ModifyListener() {
> public void modifyText(ModifyEvent event) {
> for (IItemPropertyDescriptor descriptor2 : variablePropertyDescriptors) {
> if (descriptor2.getId(formula).equals(descriptor.getId(formula) )) {
> String newValueText = ((Text) event.widget).getText();
> descriptor2.setPropertyValue(your_element_instance, newValueText);
> }
> }
> }
> });
> }
>
>
> (Note: the descriptor used here - our loop variable - needs to be final)
>
> The line where setPropertyValue is called is the important one - here the magic happens. This call is delegated to the
> ItemProvider for the element you used and a SetCommand is created, added to the command stack we setup for our editing
> domain, and executed. All editor state management like mark dirty, save, undo/redo is handled for you by EMF.
>
> So thats basically it. Your mileage may vary.
> Norbert
>
> Note to the dev's: I had to debug into how the EMF-generated editor and the simpleFormEditor works for several hours to
> grasp this and I'm still not sure if there is a better, "canonical" way to do this. The classes and interfaces I visited
> on the way were hard to understand for the average eclipse monkey (which I still consider myself to be ;)).
> The generated editor is a nice starting point but more useful would be a couple of classes which consitute the basis on
> which to build an editor (not necessarily a tree editor). What I mean is I want simple and well-documented functionalty
> to establish an editing domain for my model (maybe this could be done with an extension point?) and get/set values for
> the elements of my domain.
Re: synchronize form editor with emf editing domain (solution) [message #413896 is a reply to message #413891] Wed, 17 October 2007 18:30 Go to previous messageGo to next message
Eric Rizzo is currently offline Eric RizzoFriend
Messages: 3070
Registered: July 2009
Senior Member
Steve Blass wrote:
> > addModifyListener(
>
> I've run into notification cascades with ModifyListeners attached to
> text widgets in forms because it updates on every character you type.
> Switching to FocusListeners and updating the value when the widget loses
> focus stopped some of that for me.

+1 on that advice. I'm on my second EMF + JFace Forms project, and both
times the initial thought was to update the model (via Commands) on
every Text keystroke, but when it was discussed in depth and the number
of Commands generated is taken into consideration, both projects decided
to go the "on-focus-lost" route instead.
It is a little bit of a strange experience for new users, I'll admit;
some people seem to want to see the editor marked dirty as soon as they
type something. I've thought briefly about marking the editor dirty
without actually issuing a Command to modify the model, but not enough
to have a solution. Any ideas?

Eric
Re: synchronize form editor with emf editing domain (solution) [message #413905 is a reply to message #413896] Thu, 18 October 2007 03:10 Go to previous messageGo to next message
Steve Blass is currently offline Steve BlassFriend
Messages: 276
Registered: July 2009
Senior Member
Eric Rizzo wrote:
> some people seem to want to see the editor marked dirty as soon as
they type something. I've thought briefly about marking the editor dirty
without actually issuing a Command to modify the model, but not enough
to have a solution. Any ideas?

The standard properties view doesn't mark the editor dirty until you
leave the first cell editor where you change a value. And the Part
doesn't change until the model is changed. But if you have the
EditorPart in hand, firePropertyChange(IEditorPart.PROP_DIRTY); should
take care of placing the asterisk.

-
Steve
Re: synchronize form editor with emf editing domain (solution) [message #413907 is a reply to message #413905] Thu, 18 October 2007 04:35 Go to previous messageGo to next message
Miles Parker is currently offline Miles ParkerFriend
Messages: 1341
Registered: July 2009
Senior Member
That actually makes sense to me...going all the way back to character
based db input and wearing my user hat I wouldn't expect a change to be
'real' until I moved outside of a given field. Think also of editing a
file under word completion or a combobox.

On 2007-10-17 20:10:03 -0700, Steve Blass <sblass@acm.org> said:
> The standard properties view doesn't mark the editor dirty until you
> leave the first cell editor where you change a value.
Re: synchronize form editor with emf editing domain (solution) [message #413909 is a reply to message #413907] Thu, 18 October 2007 08:31 Go to previous messageGo to next message
Norbert  Schöpke is currently offline Norbert SchöpkeFriend
Messages: 63
Registered: July 2009
Member
The problem I see with that approach is: what to do if the user only wants to change one value?
He has to click into some other field just to be able to save, which seems a little bit awkward to me.
I recently read about how the RAP project solved a related problem by introducing a delay between character input and
actual event sent to the server. Maybe something along these lines is possible in this case too?

Beside that: thx for the FocusListener advice, I'll give it a try in any case
Norbert
Re: synchronize form editor with emf editing domain (solution) [message #413911 is a reply to message #413909] Thu, 18 October 2007 11:13 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.
--------------090401040705050100060407
Content-Type: text/plain; charset=ISO-8859-1; format=flowed
Content-Transfer-Encoding: 8bit

Norbert,

Here's an example of that in the XSDEditor

document.addDocumentListener
(new IDocumentListener()
{
protected Timer timer = new Timer();
protected TimerTask timerTask;

public void documentAboutToBeChanged(DocumentEvent
documentEvent)
{
// Ingore
}

public void documentChanged(final DocumentEvent
documentEvent)
{
try
{
// This is need for the Properties view.
//
// setSelection(StructuredSelection.EMPTY);

if (timerTask != null)
{
timerTask.cancel();
}

if (handledStructuredModelChange)
{
handledStructuredModelChange = false;
handleDocumentChange();
}
else
{
timerTask =
new TimerTask()
{
@Override
public void run()
{
getSite().getShell().getDisplay().asyncExec
(new Runnable()
{
public void run()
{
handleDocumentChange();
}
});
}
};

timer.schedule(timerTask, 1000);
}
}
catch (Exception exception)
{
XSDEditorPlugin.INSTANCE.log(exception);
}
}
});

Given that this is such a standard and common problem, I'm a bit
surprised that there isn't some simple framework support for it. I
suppose with a field, one might want to be fancy and some how modify the
already executed command to include additional changes as long as the
field remains in focus. A brute force way to do that might be to undo
the top command and execute a new one so that the undo stack doesn't
fill up if you type slowly; again, you'd only do that while the field
keeps focus. But then you'd have the issue of a notification wanting to
change the field back to the original value. Clearly it's nasty to for
each client to have to think about all this type of complex logic...


Norbert Sch


Ed Merks
Professional Support: https://www.macromodeling.com/
Re: synchronize form editor with emf editing domain (solution) [message #413957 is a reply to message #413896] Thu, 18 October 2007 12:09 Go to previous messageGo to next message
Norbert  Schöpke is currently offline Norbert SchöpkeFriend
Messages: 63
Registered: July 2009
Member
ok, I just tried this:
add a modifyListener to the text control. In the modifyText method you just set the editor dirty and immediately remove
the listener, so it's only called once. The FocusListener does the work of updating the model.

But, as strange as it may seem, the editor only gets dirty if I set a breakpoint to look if the listener is activated.
If I remove the breakpoint, the debugger doesn't jump in, but there appears no asterisk indicating the editor got marked
dirty.
Any idea what might cause this strange behaviour?
I'm attaching the code I just described for reference:
thx
Norbert


ModifyListener dirtyNotifyer = new ModifyListener() {
public void modifyText(ModifyEvent event) {
editor.editorDirtyStateChanged();
// remove listener immediately after first modification event
((Text) event.widget).removeModifyListener(this);
}
};
FocusListener fl = new FocusAdapter() {
public void focusLost(FocusEvent event) {
for (IItemPropertyDescriptor pd2 : variablePropertyDescriptors) {
if (pd2.getId(formula).equals(pd.getId(formula))) {
String newValueText = ((Text) event.widget).getText();
String origValueText = (String) ((EObject) editor.getItemDelegator()
.getEditableValue(formula)).eGet(attribute);
if (!origValueText.equals(newValueText)) {
pd2.setPropertyValue(formula, newValueText);
}
}
}
}
};
text.addFocusListener(fl);
text.addModifyListener(dirtyNotifyer);
Re: synchronize form editor with emf editing domain (solution) [message #413959 is a reply to message #413957] Thu, 18 October 2007 15:04 Go to previous messageGo to next message
Eric Rizzo is currently offline Eric RizzoFriend
Messages: 3070
Registered: July 2009
Senior Member
Norbert Schöpke wrote:
> ok, I just tried this:
> add a modifyListener to the text control. In the modifyText method you just set the editor dirty and immediately remove
> the listener, so it's only called once. The FocusListener does the work of updating the model.
>
> But, as strange as it may seem, the editor only gets dirty if I set a breakpoint to look if the listener is activated.
> If I remove the breakpoint, the debugger doesn't jump in, but there appears no asterisk indicating the editor got marked
> dirty.
> Any idea what might cause this strange behaviour?
> I'm attaching the code I just described for reference:
> thx
> Norbert
>
>
> ModifyListener dirtyNotifyer = new ModifyListener() {
> public void modifyText(ModifyEvent event) {
> editor.editorDirtyStateChanged();
> // remove listener immediately after first modification event
> ((Text) event.widget).removeModifyListener(this);
> }
> };
> FocusListener fl = new FocusAdapter() {
> public void focusLost(FocusEvent event) {
> for (IItemPropertyDescriptor pd2 : variablePropertyDescriptors) {
> if (pd2.getId(formula).equals(pd.getId(formula))) {
> String newValueText = ((Text) event.widget).getText();
> String origValueText = (String) ((EObject) editor.getItemDelegator()
> .getEditableValue(formula)).eGet(attribute);
> if (!origValueText.equals(newValueText)) {
> pd2.setPropertyValue(formula, newValueText);
> }
> }
> }
> }
> };
> text.addFocusListener(fl);
> text.addModifyListener(dirtyNotifyer);


Wouldn't you have to re-add the dirtyNotifier on every focusGained
event? Otherwise it would be removed upon first modify event and never
re-added. In fact, it seems best to always add dirtyListener in
focusGained and remove it in focusLost, right?
Another thing: how does all of this affect undo/redo, which when using
CommandStack to track dirty state handles everything gracefully. I'd be
surprised if this does no interfere somehow.

Eric
Re: synchronize form editor with emf editing domain (solution) [message #413960 is a reply to message #413909] Thu, 18 October 2007 15:08 Go to previous messageGo to next message
Eric Rizzo is currently offline Eric RizzoFriend
Messages: 3070
Registered: July 2009
Senior Member
Norbert Schöpke wrote:
> The problem I see with that approach is: what to do if the user only
> wants to change one value? He has to click into some other field just
> to be able to save, which seems a little bit awkward to me. I
> recently read about how the RAP project solved a related problem by
> introducing a delay between character input and actual event sent to
> the server. Maybe something along these lines is possible in this
> case too?

I've taken a brief look at this bug and patch for Data binding:
https://bugs.eclipse.org/bugs/show_bug.cgi?id=180746

It takes the built-in delay approach. I agree with Ed, however, that
this is something that should be built in to Text as an option. I'm
going to enter a feature request.

Eric
Re: synchronize form editor with emf editing domain (solution) [message #413962 is a reply to message #413911] Thu, 18 October 2007 15:32 Go to previous messageGo to next message
Eric Rizzo is currently offline Eric RizzoFriend
Messages: 3070
Registered: July 2009
Senior Member
Ed Merks wrote:
> Given that this is such a standard and common problem, I'm a bit
> surprised that there isn't some simple framework support for it. I
> suppose with a field, one might want to be fancy and some how modify
> the already executed command to include additional changes as long as
> the field remains in focus. A brute force way to do that might be to
> undo the top command and execute a new one so that the undo stack
> doesn't fill up if you type slowly; again, you'd only do that while
> the field keeps focus. But then you'd have the issue of a
> notification wanting to change the field back to the original value.
> Clearly it's nasty to for each client to have to think about all this
> type of complex logic...

I just entered a feature request about it:
https://bugs.eclipse.org/bugs/show_bug.cgi?id=206773

Eric

> Norbert Schöpke wrote:
>> The problem I see with that approach is: what to do if the user
>> only wants to change one value? He has to click into some other
>> field just to be able to save, which seems a little bit awkward to
>> me. I recently read about how the RAP project solved a related
>> problem by introducing a delay between character input and actual
>> event sent to the server. Maybe something along these lines is
>> possible in this case too?
>>
>> Beside that: thx for the FocusListener advice, I'll give it a try
>> in any case Norbert
>>
>
Re: synchronize form editor with emf editing domain (solution) [message #413963 is a reply to message #413909] Thu, 18 October 2007 16:11 Go to previous messageGo to next message
Miles Parker is currently offline Miles ParkerFriend
Messages: 1341
Registered: July 2009
Senior Member
On 2007-10-18 01:31:17 -0700, Norbert Schöpke <norbert.schoepke@web.de> said:

> The problem I see with that approach is: what to do if the user only
> wants to change one value?
> He has to click into some other field just to be able to save, which
> seems a little bit awkward to me.

Ah.. I was eliding issue of markers with that of dialog buttons. (I am
assumng that on a form dismissal or environment exit that there is
first a lost focus or similar event that is used to trigger save
option.) Perhaps this is why traditional Mac interface simply provides
a "Done" button for any modify dialogs regardless of dirty state. :)
Re: synchronize form editor with emf editing domain (solution) [message #1782140 is a reply to message #413963] Mon, 19 February 2018 11:53 Go to previous message
Gaurav Tripathi is currently offline Gaurav TripathiFriend
Messages: 43
Registered: September 2015
Member
Hi Nobert,

How your this problem got resolved. Can you share some input as I am facing the same issue:

Quote:
I have my resource change listener running and it kicks in correctly when it should, only I can't get my form to display
the updated GUI ( the form itself may change, not only the values). I tried to call the dispose() method followed by
createPartControl(this.getPartControl().getParent());

But it just keeps displaying the outdated GUI. I checked if the editing domains resource really contains the new data,
and it does. How can I just replace my form-page contents from scratch?

Previous Topic:Refresh widget contents in Form Page when resource is changed
Next Topic:Register EPackage in Xcore programatically in Standalone
Goto Forum:
  


Current Time: Thu Mar 28 15:00:05 GMT 2024

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

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

Back to the top