Igor, the way i've handled the "mouse hit" issue, is by asking the parent shape (morph) to take care of a mouse hit, and let him handle or forward the hit.
The topmost shape are sent the mouseDown: aLocalPoint, then each shape can choose to react, if its a composite shape or by a specific behavior. The topmost shape is always "a scene shape", which knows the bounds in global coordinates, then internally it applies local transforms to eventually get to the inner shape which was hit. The separation between scene shapes and shapes, allows this mechanism, similar to the one you propose, to cache the global state. I prefer this approach, instead of the "framework" level as you propose, because is more of a top-down collaboration, always dealing with local coordinates. It greatly simplifies the UI framework, avoiding the messy "god classes" and complex methods you mentioned and many more in Morphic. Fernando On Sun, Sep 2, 2012 at 10:12 AM, Stéphane Ducasse <[email protected]> wrote: > Yes we should really refactor this hierarchy. > We should finish first the event model cleaning at VM/Image border then we > work on this one. > > On Aug 31, 2012, at 9:21 PM, Igor Stasenko wrote: > >> and to give an idea, how current Morphic doing that, a starting point is >> MorphicEventDispatcher >> >> personally, i find this code too complex to understand, given heavy >> use of case statements and branches. >> >> But i figured out, that this method: >> >> >> dispatchEvent: anEvent with: aMorph >> "Dispatch the given event for a morph that has chosen the receiver to >> dispatch its events. The method implements a shortcut for repeated >> dispatches of events using the same dispatcher." >> anEvent type == lastType ifTrue:[^self perform: lastDispatch with: >> anEvent with: aMorph]. >> "Otherwise classify" >> lastType := anEvent type. >> anEvent isMouse ifTrue:[ >> anEvent isMouseDown ifTrue:[ >> lastDispatch := #dispatchMouseDown:with:. >> ^self dispatchMouseDown: anEvent with: aMorph]]. >> anEvent type == #dropEvent ifTrue:[ >> lastDispatch := #dispatchDropEvent:with:. >> ^self dispatchDropEvent: anEvent with: aMorph]. >> anEvent isWindowEvent ifTrue:[ >> lastDispatch := #dispatchWindowEvent:with:. >> ^self dispatchWindowEvent: anEvent with: aMorph]. >> lastDispatch := #dispatchDefault:with:. >> ^self dispatchDefault: anEvent with: aMorph >> >> --- >> >> actually can be replaced by one-liner: >> >> dispatchEvent: anEvent with: aMorph >> morph := aMorph. >> ^ anEvent sentTo: self >> >> .. yeah.. my favorite thing: double-dispatch. >> >> -- >> Best regards, >> Igor Stasenko. >> > >
