[Insight-developers] Command / Observer / Event
Miller, James V (Research)
millerjv@crd.ge.com
Thu, 2 May 2002 08:58:23 -0400
I agree with Lydia. I think an Observer should be able
to modify the object it is observing. I have used StartEvents
as a mechanism for something external to the pipeline to
set ivars on an ProcessObject. For instance, I can use
the StartEvent as a mechanism to tie a parameter (say a float)
calculated by one process object to a Set method on another
process object.
For instance, one filter may calculate a mean and variance
over an image. These are floats or doubles. Since we have
yet to wrap simple types as pipelinable data objects, I use
the StartEvent of a filter to go query the mean and variance
calculated by a filter before it in the pipeline. This way,
I know every time my second filter executes it has the most
recent values of the mean and variance from the filter before it.
There also shouldn't be a problem with an observer calling
an Update(). The pipeline keeps track of whether it is currently
updating and should exit out of a second Update().
Luis, have you verified that your example is indeed a problem?
> Filter says to command: I'm going to start
> Command says to filter: Start.
> Filter says to command: I'm going to start
> Command says to filter: Start.
> Filter says to command: I'm going to start...
>
I also don't think we should limit the observers to
"small tasks that update a GUI". They should be a general
mechansism that allows ITK to be interfaced to other systems.
-----Original Message-----
From: Lydia Ng [mailto:lng@insightful.com]
Sent: Wednesday, May 01, 2002 7:18 PM
To: Luis Ibanez; Insight Developers
Subject: RE: [Insight-developers] Command / Observer / Event
> Observers should not be able to modify the
> observed Object..... because that will
> trigger a ModifiedEvent while we are still
> in the middle of processing the list of
> events on this object.
>
Why not?
I currently have two applications (one inside the toolkit
and one outside) that rely on this functionality.
[1] I have an observer that externally monitors the progress of
some algorithm. If it satisfies some requirement, the
the observer tells the subject to stop via some
m_Subject->Stop() routine.
For example, a GUI updates some display
and when the user is satified they can hit some button
and that will trigger the algorithm to stop nicely.
[2] For the multi-resolution, I think I was Stephen who
suggested it would be nice to have the ability to swap
registration components around, change parameters etc
at the beginning of each resolution level.
This is what I have implemented.
This is the mechanism which I use to alter parameters
at each resolution level.
I think one definitely have to have a mechanism for the
GUI to talk back and control the filter. So that one
can respond to cancel, change in parameters etc
I have used observers in this way because that is what I thought
they were for. I liked this way of handling the GUI-filter
communication because there is good decoupling so I can
fairly easier tied filter to different GUIs.
Please don't take this away dear const meister!
- Lydia
> -----Original Message-----
> From: Luis Ibanez [mailto:luis.ibanez@kitware.com]
> Sent: Wednesday, May 01, 2002 3:32 PM
> To: Insight Developers
> Subject: [Insight-developers] Command / Observer / Event
>
>
>
> Hi,
>
> This is a proposal for a change in the
> current structure of the Command/Events
> management in ITK.
>
> ------
>
> The current implementation of the Observer
> Pattern in ITK is represented in the figure
> below.(Fig.1) The itk::Command classes play
> the role of Observers while the itk::Object
> play the role of Subjects.
>
> Subjects send messages to observers by
> invoking Events.
>
> +----------+ Event +----------+
> | Subject |----------->| Observer |
> +----------+ +----------+
>
> (Figure 1.)
>
> This was initially introduced as hook where
> GUI interaction could be connected. The events
> allowed to update the GUI as changes in the
> pipeline occur.
>
> Every itk::Object has a list of
> pairs : <Event, Observer *>
>
> These pairs are created in the itk::Object
> by the method
>
> AddObserver(Event, Command *)
>
>
> When the Subject (any itk::Object) is running
> it may decide to send messages in order to
> inform others about their internal state.
> When the Subject invoke an event, it goes
> through its list of pairs and for every
> event that matches the type of the invoked
> event, it will call the associated observer
> Execute() method.
>
> +-----------------------+
> | Subject = itk::Object |
> +-----------------------+
> |
> |----< ModifiedEvent, Observer_1 >
> |
> |----< ModifiedEvent, Observer_2 >
> |
> |----< DeleteEvent , Observer_3 >
> |
> |----< StartEvent , Observer_4 >
> |
> |----< EndEvent, Observer_5 >
> |
>
> (Figure 2)
>
> This mechanisms allows to interconect the
> system yet allowing decoupling since Subject
> don't need to know about observers. The mechanism
> of Events is relatively independent of the
> control of the pipeline. They are only related
> by the fact that some standard Pipeline methods
> InvokeEvents as part of they action.
>
> As in the management of Event in GUI's,
> the spirit of the ITK Event is that they
> are just carring information out of the
> pipeline. They are not intended to control
> de pipeline itself.
>
> Because of the linear execution of the
> events in the list. It is not desirable
> that the Execute() method of an Observer
> could trigger the Invokation of other
> Events. The execute method should be
> as rapid and passive from the point of
> view of the Pipeling. For example, we
> should not call and Update() from the
> Execute method of a Command.
>
> Imaging for example:
>
> Filter1->AddObserver( StartEvent, Command )
>
> if the execute method of the command,
> can end up calling directly or indirectly
> the Update() method of Filter1, it will
> enter in an infinite loop with the following
> dialog:
>
> Filter says to command: I'm going to start
> Command says to filter: Start.
> Filter says to command: I'm going to start
> Command says to filter: Start.
> Filter says to command: I'm going to start...
>
> So,...
>
> The proposed change in the current mechanism
> is intended to make sure that Observers can
> only be passive elements on the pipeline.
> A first step on this direction is of course:
>
> Const-correctness !
>
> Observers should not be able to modify the
> observed Object..... because that will
> trigger a ModifiedEvent while we are still
> in the middle of processing the list of
> events on this object.
>
> A more direct way of enforcing pasivness on
> the Observers is not even pass to them the
> pointer to the Subject, only the type of
> event. In that way the command will just
> blindly execute an action on its side.
> In this options, particular commands that
> actually have to query the state of the
> observed object will have to be created
> as a specialized type of observer and will
> probably keep a internal Constsmart pointer
> to the observed object (the Subject).
>
>
> Observers that observe multiple object will
> not be selective. The will react in the
> same way to the received Event no matter
> who send it. If multiple behaviors are
> required, multiple observers should be
> created.
>
>
> Observers are mostly used in examples
> an in some tests that monitor the progress
> of filter execution.
>
> Does anybody see potential conflicts
> with doing these changes ?
>
>
>
>
> Luis
>
>
>
> _______________________________________________
> Insight-developers mailing list
> Insight-developers@public.kitware.com
> http://public.kitware.com/mailman/listinfo/insight-developers
>
>
_______________________________________________
Insight-developers mailing list
Insight-developers@public.kitware.com
http://public.kitware.com/mailman/listinfo/insight-developers