January 31, 2003

Event System Madness

I really need to get out of events and fix my other topembed+ bugs, but things keep pulling me back.

Some perfect ass is creating a new nsIDOMEvent, or retargeting the old one, with the target as the textnode, after all that hard work I did targeting the event at the element's parent. This is why bug 103055 has regressed even though it shouldn't have. This leads to some of the points I want to make in this bug, specifically the way we store our target.

Our event system needs fixing, and HandleDOMEvent in particular (the lynchpin of the event system) needs some serious lovin'. Several bugs have been filed on that. Here are some specific things I think we need to do:

  1. Store the event target in the nsDOMEvent when you create it. Currently when you ask for the target, nsDOMEvent::GetTarget asks the ESM for the current target. It isn't stored when it's created. Worse, the range asks the ESM for the current target frame all the time--doesn't even cache it. We must be breaking here. The next item is related to this.
  2. Make HandleDOMEvent just take an nsIDOMEvent*. We probably originally tried to avoid creating nsIDOMEvent*'s in order to keep heap allocations from happening, but since we actually have an arena for that now, that point is moot. Doing this would make the previous point easier to implement.
  3. Move the retargeting stuff out of nsGenericElement::HandleDOMEvent into a separate function that it calls. It's ugly as sin and distracts from the real purpose of the function, which is to handle the DOM event.
  4. Factor event flow out of elements. Default handling (like anchors or buttons handling clicks) is currently done by overriding nsGenericElement::HandleDOMEvent and doing your dirty deed there, calling the parent HandleDOMEvent before you do so. We should move it into a HandleDefault() method or maybe even a separate actual listener (HandleEvent()) that is called in its own event pass. (You could make this a special event group that is always called so you avoid the overhead of all those listeners, if we determine that the number of listeners would justify that.) Otherwise an element is responsible not just for handling clicks but also dispatching them. And who wants to be responsible for that? (Certainly not me.) This is a huge blocker for any kind of clean event groups. It also would make it easier to handle fixing the flow of default handlers to go the right direction, which is currently impossible.
  5. Stop targeting events at frames. This actually sounds harder than anything else here, and is not something I've been personally bitten by, but it sure sounds like a good idea :) Perhaps we could keep targeting events at frames, but do it through a listener so that the event system is not directly burdened with it and the frames receive the events in their proper time.
  6. Remove nsIPresContext* from HandleDOMEvent parameters. We need to accept the fact the we cannot, and will never, handle events on any presentation other than the primary presentation. Just grab that presentation from the doc / window and you are good to go. bz brought this one up.
Posted by jkeiser at January 31, 2003 6:58 PM