Home » Modeling » GMF (Graphical Modeling Framework) » how to display referenced feature in label
how to display referenced feature in label [message #128237] |
Tue, 22 May 2007 11:25  |
Eclipse User |
|
|
|
Hello
I'm having problems using the new MessageFormatParser.
I want to display two features in a label. Those two features are not
direct features of the labeled node, instead the node element has 2
references. I want to display one feature of each element behind these
references, and display them together, separated by some token. So the
label would show a left-hand-side variable and a right-hand-side formula
of an assignment, all 3 modeled as separate elements).
How can I resolve the reference in code and get the feature of the
resolved element?
I tried the following:
EAttribute varName = ThetamlPackage.eINSTANCE.getVariable_Name();
EAttribute valueFormulaValue =
ThetamlPackage.eINSTANCE.getValueFormula_Value();
EAttribute[] features = new EAttribute[] { varName, valueFormulaValue };
MessageFormatParser parser = new MessageFormatParser(features);
parser.setViewPattern("{0} = {1}");
parser.setEditPattern("{0} = {1}");
But at runtime I get a NullPointerException in
AbstractParser#getValue(EObject element, EAttribute feature)
because the first line fails:
Object value = element.eGet(feature);
I also studied the EcoreParserProvider from the ECore Modeller to see
how the experts do it, but there only direct features are used.
Any hints on how to do this?
I need to somehow resolve the reference but I don't know how...
Thanks for any comment
Norbert Schöpke
|
|
| |
Re: how to display referenced feature in label [message #128587 is a reply to message #128490] |
Wed, 23 May 2007 07:56   |
Eclipse User |
|
|
|
Dmitry Stadnik wrote:
> This functionality is not supported yet; first we should figure out how to:
> 1. Specify path to element that has respective attributes from the
> current element; in other words which references to follow.
> 2. What to do if some elements are missing / reference multiplicity is
> more then one and possibly other conditions.
>
> At this moment my advice is to write your own parser based on
> MessageFormatParser.
>
Thanks, good to know.
Now I can at least display my labels. I plugged in a custom parser provider and handle the edit part with my own parser
which extends MessageFormatParser and overwrites the getValue() method.
I specify the features I want by accessing them using ...Package.eInstance.getFeature() and do a switch in the
getValue() method. As I know the element and the feature, I just cast the element and resolve the reference needed to
get this feature.
@Override
protected Object getValue(EObject element, EAttribute feature) {
Object value;
if (element instanceof Assignment) {
Assignment a = (Assignment) element;
if (ThetamlPackage.eINSTANCE.getVariable_Name().equals(feature) ) {
LHSValue lhs = a.getLhs();
value = lhs == null ? "" : lhs.getVariable().getName();
} else if (ThetamlPackage.eINSTANCE.getValueFormula_Value().equals(fea ture)) {
ValueFormula valueFormula = (ValueFormula) a.getFormula();
value = valueFormula == null ? "" : valueFormula.getValue();
} else {
// TODO: implement for other formula types
value = null;
}
} else {
value = element.eGet(feature);
}
//Object value = element.eGet(feature);
Class iClass = feature.getEAttributeType().getInstanceClass();
if (String.class.equals(iClass)) {
if (value == null) {
value = ""; //$NON-NLS-1$
}
}
return value;
}
However I think this way "smells". It's nowhere near as generic as I would want to solve this and I have problems when I
want to parse and write back the new values.
Of multiple paths and reference multiplicity I don't even dream atm because I have enough nightmares already ;)
> Norbert Schöpke wrote:
>> Hello
>>
>> I'm having problems using the new MessageFormatParser.
>> I want to display two features in a label. Those two features are not
>> direct features of the labeled node, instead the node element has 2
>> references. I want to display one feature of each element behind these
>> references, and display them together, separated by some token. So the
>> label would show a left-hand-side variable and a right-hand-side formula
>> of an assignment, all 3 modeled as separate elements).
>>
>> How can I resolve the reference in code and get the feature of the
>> resolved element?
>>
>> I tried the following:
>>
>> EAttribute varName = ThetamlPackage.eINSTANCE.getVariable_Name();
>> EAttribute valueFormulaValue =
>> ThetamlPackage.eINSTANCE.getValueFormula_Value();
>> EAttribute[] features = new EAttribute[] { varName, valueFormulaValue };
>> MessageFormatParser parser = new MessageFormatParser(features);
>> parser.setViewPattern("{0} = {1}");
>> parser.setEditPattern("{0} = {1}");
>>
>> But at runtime I get a NullPointerException in
>> AbstractParser#getValue(EObject element, EAttribute feature)
>> because the first line fails:
>> Object value = element.eGet(feature);
>>
>>
>> I also studied the EcoreParserProvider from the ECore Modeller to see
>> how the experts do it, but there only direct features are used.
>>
>> Any hints on how to do this?
>> I need to somehow resolve the reference but I don't know how...
>>
>> Thanks for any comment
>> Norbert Schöpke
|
|
|
Re: how to display referenced feature in label [message #133070 is a reply to message #128490] |
Wed, 06 June 2007 08:43   |
Eclipse User |
|
|
|
I solved the display problem by writing my own parser extending MessageFormatParser.
Instead of resolving any references I use a custom made formatter class that just returns the string to display.
protected Object getValue(EObject element, EAttribute feature) {
Object value;
if (element instanceof Formula) {
Formula f = (Formula) element;
value = FormulaFormatter.format(f);
if (value == null) {
value = ""; //$NON-NLS-1$
}
return value;
}
}
This works fine. However, parsing in new values (set using direct editing feature) poses a lot of problems.
The AbstractParser class can only handle EAttribute type features, which in my humble opinion is to harsh a constraint.
Iirc this restriction was introduced in one of the last milestone releases. Why?
In my model I have elements called "operators" which may contain references to formulas. The above code correctly
displays these formulas if I open an existing model that has some of these operators.
However, creating new formulas is impossible in a straightforward manner.
What I have is a string and code to parse that string back into a formula (similar to what happens inside the
MessageFormatParser.getParseCommand() method).
Upon entering the string GMF calls my custom parser in the context of the new element (some kind of formula impl).
But now I can't just call AbstractParser.getParseCommand() because
a) it opens the CompositeTransactionalCommand on the formula element, but I want to modify its container and just set
the parsed formula
b) if extending AbstractParser / MessageFormatParser, I _HAVE_ to specify EAttributes (in the AbstractParser constructor
for instance). But I don't want that, because all I have is my formula, which is an EStructuralFeature.
I already tried to override large portions of AbstractParser / MessageFormatParser, namely the getParseCommand method
and wrote a replacement for the getModificationCommand (which also only works with EAttribute), but to no avail.
Is there something I'm missing / totally doing wrong here? It seems to complicated to achieve a simple feature modification.
Any help appreciated...
Norbert Schöpke
|
|
|
Re: how to display referenced feature in label [message #133118 is a reply to message #133070] |
Wed, 06 June 2007 08:43   |
Eclipse User |
|
|
|
Originally posted by: 5d5.mail.ru
When you construct label text you use values of attributes in the end,
so you should specify them in AbstractParser.
There is a request https://bugs.eclipse.org/bugs/show_bug.cgi?id=138179
to use attributes of referenced elements but:
1. You will use attribute values in the end
2. It's planned for GMF 2.1, sorry
I could refactor MessageFormatParser so there will be some
getDomainElement() method that will 'shift context' of attributes. I
mean that this will be a single point that you will override to travel
from the current domain element to another referenced element that
contains the attributes.
Norbert Schöpke wrote:
> I solved the display problem by writing my own parser extending MessageFormatParser.
> Instead of resolving any references I use a custom made formatter class that just returns the string to display.
>
> protected Object getValue(EObject element, EAttribute feature) {
> Object value;
> if (element instanceof Formula) {
> Formula f = (Formula) element;
> value = FormulaFormatter.format(f);
>
> if (value == null) {
> value = ""; //$NON-NLS-1$
> }
> return value;
> }
> }
>
>
> This works fine. However, parsing in new values (set using direct editing feature) poses a lot of problems.
> The AbstractParser class can only handle EAttribute type features, which in my humble opinion is to harsh a constraint.
> Iirc this restriction was introduced in one of the last milestone releases. Why?
>
> In my model I have elements called "operators" which may contain references to formulas. The above code correctly
> displays these formulas if I open an existing model that has some of these operators.
> However, creating new formulas is impossible in a straightforward manner.
> What I have is a string and code to parse that string back into a formula (similar to what happens inside the
> MessageFormatParser.getParseCommand() method).
> Upon entering the string GMF calls my custom parser in the context of the new element (some kind of formula impl).
> But now I can't just call AbstractParser.getParseCommand() because
> a) it opens the CompositeTransactionalCommand on the formula element, but I want to modify its container and just set
> the parsed formula
> b) if extending AbstractParser / MessageFormatParser, I _HAVE_ to specify EAttributes (in the AbstractParser constructor
> for instance). But I don't want that, because all I have is my formula, which is an EStructuralFeature.
>
> I already tried to override large portions of AbstractParser / MessageFormatParser, namely the getParseCommand method
> and wrote a replacement for the getModificationCommand (which also only works with EAttribute), but to no avail.
>
> Is there something I'm missing / totally doing wrong here? It seems to complicated to achieve a simple feature modification.
>
> Any help appreciated...
> Norbert Schöpke
|
|
| | | | |
Re: how to display referenced feature in label [message #135454 is a reply to message #133070] |
Wed, 13 June 2007 05:21   |
Eclipse User |
|
|
|
Originally posted by: jan.herriger.gmx.de
I am using volatile attributes in my ecore models. This way, empty
getters/setters are generated. Now, you can fill these methods with
code, that forwards method calls to corresponding getters/setters of the
referenced eObjects.
So, diagram code doesn't have to care about what to display. The model
code does.
Norbert Schöpke schrieb:
> I solved the display problem by writing my own parser extending MessageFormatParser.
> Instead of resolving any references I use a custom made formatter class that just returns the string to display.
>
> protected Object getValue(EObject element, EAttribute feature) {
> Object value;
> if (element instanceof Formula) {
> Formula f = (Formula) element;
> value = FormulaFormatter.format(f);
>
> if (value == null) {
> value = ""; //$NON-NLS-1$
> }
> return value;
> }
> }
>
>
> This works fine. However, parsing in new values (set using direct editing feature) poses a lot of problems.
> The AbstractParser class can only handle EAttribute type features, which in my humble opinion is to harsh a constraint.
> Iirc this restriction was introduced in one of the last milestone releases. Why?
>
> In my model I have elements called "operators" which may contain references to formulas. The above code correctly
> displays these formulas if I open an existing model that has some of these operators.
> However, creating new formulas is impossible in a straightforward manner.
> What I have is a string and code to parse that string back into a formula (similar to what happens inside the
> MessageFormatParser.getParseCommand() method).
> Upon entering the string GMF calls my custom parser in the context of the new element (some kind of formula impl).
> But now I can't just call AbstractParser.getParseCommand() because
> a) it opens the CompositeTransactionalCommand on the formula element, but I want to modify its container and just set
> the parsed formula
> b) if extending AbstractParser / MessageFormatParser, I _HAVE_ to specify EAttributes (in the AbstractParser constructor
> for instance). But I don't want that, because all I have is my formula, which is an EStructuralFeature.
>
> I already tried to override large portions of AbstractParser / MessageFormatParser, namely the getParseCommand method
> and wrote a replacement for the getModificationCommand (which also only works with EAttribute), but to no avail.
>
> Is there something I'm missing / totally doing wrong here? It seems to complicated to achieve a simple feature modification.
>
> Any help appreciated...
> Norbert Schöpke
|
|
|
Re: how to display referenced feature in label [message #135481 is a reply to message #135454] |
Wed, 13 June 2007 05:49  |
Eclipse User |
|
|
|
Originally posted by: 5d5.mail.ru
Good solution; thanks for sharing!
Jan Herriger wrote:
> I am using volatile attributes in my ecore models. This way, empty
> getters/setters are generated. Now, you can fill these methods with
> code, that forwards method calls to corresponding getters/setters of the
> referenced eObjects.
>
> So, diagram code doesn't have to care about what to display. The model
> code does.
>
> Norbert Schöpke schrieb:
>> I solved the display problem by writing my own parser extending
>> MessageFormatParser.
>> Instead of resolving any references I use a custom made formatter
>> class that just returns the string to display.
>>
>> protected Object getValue(EObject element, EAttribute feature) {
>> Object value;
>> if (element instanceof Formula) {
>> Formula f = (Formula) element;
>> value = FormulaFormatter.format(f);
>>
>> if (value == null) {
>> value = ""; //$NON-NLS-1$
>> }
>> return value;
>> }
>> }
>>
>>
>> This works fine. However, parsing in new values (set using direct
>> editing feature) poses a lot of problems.
>> The AbstractParser class can only handle EAttribute type features,
>> which in my humble opinion is to harsh a constraint.
>> Iirc this restriction was introduced in one of the last milestone
>> releases. Why?
>>
>> In my model I have elements called "operators" which may contain
>> references to formulas. The above code correctly
>> displays these formulas if I open an existing model that has some of
>> these operators.
>> However, creating new formulas is impossible in a straightforward manner.
>> What I have is a string and code to parse that string back into a
>> formula (similar to what happens inside the
>> MessageFormatParser.getParseCommand() method).
>> Upon entering the string GMF calls my custom parser in the context of
>> the new element (some kind of formula impl).
>> But now I can't just call AbstractParser.getParseCommand() because
>> a) it opens the CompositeTransactionalCommand on the formula element,
>> but I want to modify its container and just set
>> the parsed formula
>> b) if extending AbstractParser / MessageFormatParser, I _HAVE_ to
>> specify EAttributes (in the AbstractParser constructor
>> for instance). But I don't want that, because all I have is my
>> formula, which is an EStructuralFeature.
>>
>> I already tried to override large portions of AbstractParser /
>> MessageFormatParser, namely the getParseCommand method
>> and wrote a replacement for the getModificationCommand (which also
>> only works with EAttribute), but to no avail.
>>
>> Is there something I'm missing / totally doing wrong here? It seems to
>> complicated to achieve a simple feature modification.
>>
>> Any help appreciated...
>> Norbert Schöpke
|
|
|
Goto Forum:
Current Time: Fri May 23 13:35:24 EDT 2025
Powered by FUDForum. Page generated in 0.05742 seconds
|