| [news.eclipse.tools.emf] Re: ChangeRecorder issue ? |
Ed,
Answers below.
Ed Merks wrote:
Stephane,
Comments below.
Stephane wrote:As opposed to those non-wierd problems. :-PHi,
I'm using the ChangeRecorder API and I have got a weird problem.Hmm. Is it an unsettable multi-valued containment? Do you need that?
I monitor an EMF object "Canvas" that has a containment reference named "figures" of type Figure .
Let's imagine, one instance of this "Canvas" named canvas1 has 2 objects contained in the "figures" feature.
a) I start a change recorder for canvas1. b) I unset the "figures" containment feature. c) I end the change recorder and get the change description.
Result : no change happens for canvas1 : ChangeDescription#getObjectChanges(), ChangeDescription#getObjectsToAttach or ChangeDescription#getObjectsToDetach are empty collections !! Weird isn'it ?
When ending the change recorder, the BasicChangeRecorder#eliminateEmptyChanges() is called.It doesn't sound good. I would expect the unset to fire a REMOVE_MANY and for this code in the ChangeRecorder to kick in to record the old value of the list.
I debug the code, and the featureChange is retrieved according the unset on the "figures" feature. Nevertheless, It compares the value registered into the featureChange with the current value of the related feature on canvas1. Both lists are empty ones and hence equals, the featureChange is removed... What's a pitty !!
Is it a bug or normal behavior ? How can i figure out that issue ?
case Notification.REMOVE_MANY:
{
if (change == null && changes != null)
{
@SuppressWarnings("unchecked") List<Object> removedValues = (List<Object>)notification.getOldValue();
List<Object> oldValue = new BasicEList<Object>((Collection<?>)eObject.eGet(feature));
int[] positions = (int[])notification.getNewValue();
if (positions == null)
{
oldValue.addAll(removedValues);
}
else
{
for (int i = 0; i < positions.length; ++i)
{
oldValue.add(positions[i], removedValues.get(i));
}
}
change = createFeatureChange(eObject, feature, oldValue, notification.wasSet());
((InternalEList<FeatureChange>)changes).addUnique(change);
}
break;
}
Does a clear cause the same problems as an unset? Does the unset case kick in?
case Notification.UNSET:
{
if (change == null && changes != null)
{
if (feature.isMany())
{
List<Object> oldValue = new
BasicEList<Object>((Collection<?>)eObject.eGet(feature));
int index = notification.getPosition();
if (index != Notification.NO_INDEX)
{
oldValue.set(index, notification.getOldValue());
}
change = createFeatureChange(eObject, feature, oldValue,
notification.wasSet());
}
else
{
Object oldValue = notification.getOldValue();
change = createFeatureChange(eObject, feature, oldValue,
notification.wasSet());
}
((InternalEList<FeatureChange>)changes).addUnique(change);
}
if (containment != null)
{
Object newValue = notification.getNewValue();
if (newValue != null && newValue != Boolean.TRUE &&
newValue != Boolean.FALSE)
{
addAdapter((Notifier)newValue);
}
}
break;
}
Stephane.