[prev in list] [next in list] [prev in thread] [next in thread]
List: kfm-devel
Subject: Re: [PATCH] tracking form value changes in onclick-handlers
From: Tobias Anton <TA () ESC-Electronics ! de>
Date: 2004-07-13 19:10:31
Message-ID: 200407132110.31587.TA () ESC-Electronics ! de
[Download RAW message or body]
On Dienstag, 13. Juli 2004 02:06, bj@altern.org wrote:
> On Monday 12 July 2004 19.52, Tobias Anton wrote:
> > I'm planning to commit a patch like this one, and then I'd like to change
> > the default event handlers of activatable elements (links, form controls
> > and labels) to react on DOMACTIVATE_EVENT instead of CLICK_EVENT, or
> > event worse, MOUSEUP_EVENTS.
> >
> > Is there anything basically wrong or can I try this approach?
>
> Many webmail have a checkbox with something like this:
>
> <form>
> <input type="checkbox" onclick="anotherform.checked=this.checked">1<br>
> <input id="anotherform" type="checkbox"
> onclick="anotherform.checked=this.checked">2
> </form>
>
> Clicking on the checkbox 1 should always set the second checkbox to the
> same value. If you process the javascript events first, the this.checked
> will return a wrong value...
>
> I don't think your patch adresses this issue.
I just made a few other tests with IE. The bottom line is:
When a click event is to be processed, the following steps happen internally:
1. the old value of the form is backed up.
2. the value is changed
3. the onclick-javascript code is called
4. if the script returns false, the old value is restored.
And:
onclick-javascript is executed after both mouse clicks and pressing space.
This behaviour is resembled by this new patch (attached).
Comments and ideas welcome.
Cheers
-- Tobias
["temp.diff" (text/x-diff)]
? temp
? testregression
Index: html/html_formimpl.cpp
===================================================================
RCS file: /home/kde/kdelibs/khtml/html/html_formimpl.cpp,v
retrieving revision 1.375
diff -u -3 -p -r1.375 html_formimpl.cpp
--- html/html_formimpl.cpp 12 Jul 2004 22:39:44 -0000 1.375
+++ html/html_formimpl.cpp 13 Jul 2004 20:09:27 -0000
@@ -850,58 +850,48 @@ void HTMLGenericFormElementImpl::default
}
}
- if (evt->target()==this && !m_disabled)
+ if (!m_disabled)
{
- // Report focus in/out changes to the browser extension (editable widgets \
only)
- KHTMLView *view = getDocument()->view();
- if (view && evt->id() == EventImpl::DOMFOCUSIN_EVENT && isEditable() && \
m_render && m_render->isWidget()) {
- KHTMLPartBrowserExtension *ext = static_cast<KHTMLPartBrowserExtension \
*>(view->part()->browserExtension());
- QWidget *widget = static_cast<RenderWidget*>(m_render)->widget();
- if (ext)
- ext->editableWidgetFocused(widget);
- }
- if (evt->id()==EventImpl::MOUSEDOWN_EVENT || \
evt->id()==EventImpl::KEYDOWN_EVENT)
- {
- setActive();
- }
- else if (evt->id() == EventImpl::MOUSEUP_EVENT || \
evt->id()==EventImpl::KEYUP_EVENT)
- {
- if (m_active)
- {
- setActive(false);
- setFocus();
- }
- else {
- setActive(false);
- }
- }
-
- if (evt->id() == EventImpl::KHTML_KEYPRESS_EVENT) {
- TextEventImpl * k = static_cast<TextEventImpl *>(evt);
- int key = k->qKeyEvent ? k->qKeyEvent->key() : 0;
- if (m_render && (key == Qt::Key_Tab || key == Qt::Key_BackTab)) {
- QWidget *widget = static_cast<RenderWidget*>(m_render)->widget();
- if (widget)
- static_cast<FocusHandleWidget *>(widget)
- ->focusNextPrev(key == Qt::Key_Tab);
- }
- }
-
-
- if (view && evt->id() == EventImpl::DOMFOCUSOUT_EVENT && isEditable() && m_render \
&& m_render->isWidget()) {
- KHTMLPartBrowserExtension *ext = static_cast<KHTMLPartBrowserExtension \
*>(view->part()->browserExtension());
- QWidget *widget = static_cast<RenderWidget*>(m_render)->widget();
- if (ext)
- ext->editableWidgetBlurred(widget);
+ if (evt->target()==this)
+ {
+ // Report focus in/out changes to the browser extension (editable widgets only)
+ KHTMLView *view = getDocument()->view();
+ if (view && evt->id() == EventImpl::DOMFOCUSIN_EVENT && isEditable() && m_render \
&& m_render->isWidget()) { + KHTMLPartBrowserExtension *ext = \
static_cast<KHTMLPartBrowserExtension *>(view->part()->browserExtension()); \
+ QWidget *widget = static_cast<RenderWidget*>(m_render)->widget(); + if (ext)
+ ext->editableWidgetFocused(widget);
+ }
+ if (evt->id() == EventImpl::KHTML_KEYPRESS_EVENT) {
+ TextEventImpl * k = static_cast<TextEventImpl *>(evt);
+ int key = k->qKeyEvent ? k->qKeyEvent->key() : 0;
+ if (m_render && (key == Qt::Key_Tab || key == Qt::Key_BackTab)) {
+ QWidget *widget = static_cast<RenderWidget*>(m_render)->widget();
+ if (widget)
+ static_cast<FocusHandleWidget *>(widget)
+ ->focusNextPrev(key == Qt::Key_Tab);
+ }
+ }
+
+ if (view && evt->id() == EventImpl::DOMFOCUSOUT_EVENT && isEditable() && m_render \
&& m_render->isWidget()) { + KHTMLPartBrowserExtension *ext = \
static_cast<KHTMLPartBrowserExtension *>(view->part()->browserExtension()); \
+ QWidget *widget = static_cast<RenderWidget*>(m_render)->widget(); + if (ext)
+ ext->editableWidgetBlurred(widget);
+
+ // ### Don't count popup as a valid reason for losing the focus (example: \
opening the options of a select + // combobox shouldn't emit onblur)
+ }
- // ### Don't count popup as a valid reason for losing the focus (example: \
opening the options of a select
- // combobox shouldn't emit onblur)
- }
+ if (evt->isMouseEvent() && renderer())
+ evt->setDefaultHandled();
+ }
+
+ // don't call the base class if the form control is disabled!
+ // HTMLElementImpl doesn't know about the inactive state
+ // and will set this element focused.
+ HTMLElementImpl::defaultEventHandler(evt);
}
- if (evt->target() == this && evt->isMouseEvent() && renderer())
- evt->setDefaultHandled();
-
- HTMLElementImpl::defaultEventHandler(evt);
}
bool HTMLGenericFormElementImpl::isEditable()
@@ -959,16 +949,8 @@ void HTMLButtonElementImpl::parseAttribu
void HTMLButtonElementImpl::defaultEventHandler(EventImpl *evt)
{
- if (m_type != BUTTON && !m_disabled) {
- bool act = (evt->id() == EventImpl::DOMACTIVATE_EVENT);
- if (!act && evt->id()==EventImpl::KEYUP_EVENT) {
- QKeyEvent *ke = static_cast<TextEventImpl *>(evt)->qKeyEvent;
- if (ke && active() && (ke->key() == Qt::Key_Return || ke->key() == \
Qt::Key_Enter || ke->key() == Qt::Key_Space))
- act = true;
- }
- if (act)
- activate();
- }
+ if (evt->target() == this && m_type != BUTTON && !m_disabled && evt->id() == \
EventImpl::DOMACTIVATE_EVENT) + activate();
HTMLGenericFormElementImpl::defaultEventHandler(evt);
}
@@ -1476,58 +1458,56 @@ void HTMLInputElementImpl::focus()
getDocument()->setFocusNode(this);
}
+void HTMLInputElementImpl::handleLocalEvents(EventImpl *evt, bool useCapture)
+{
+ if (!useCapture && evt->id()==EventImpl::KHTML_ECMA_CLICK_EVENT && (m_type == \
CHECKBOX || m_type == RADIO)) + {
+ kdDebug ( 6000 ) << "ecma click on " << (m_type == CHECKBOX?"checkbox":"radio") << \
endl; + bool oldvalue = checked();
+ setChecked(m_type==RADIO?true:!oldvalue);
+ HTMLGenericFormElementImpl::handleLocalEvents(evt, useCapture);
+ if (evt->defaultPrevented())
+ setChecked(oldvalue);
+ }
+ else HTMLGenericFormElementImpl::handleLocalEvents(evt, useCapture);
+}
+
void HTMLInputElementImpl::defaultEventHandler(EventImpl *evt)
{
if ( !m_disabled )
{
-
- if (evt->isMouseEvent()) {
- MouseEventImpl *me = static_cast<MouseEventImpl*>(evt);
- if ((m_type == RADIO || m_type == CHECKBOX)
- && me->id() == EventImpl::MOUSEUP_EVENT && me->detail() > 0) {
- // click will follow
- setChecked(m_type == RADIO ? true : !checked());
- }
- if (evt->id() == EventImpl::CLICK_EVENT && m_type == IMAGE && m_render) \
{
- // record the mouse position for when we get the DOMActivate event
- int offsetX, offsetY;
- m_render->absolutePosition(offsetX,offsetY);
- xPos = me->clientX()-offsetX;
- yPos = me->clientY()-offsetY;
- }
- }
-
- if (m_type == RADIO || m_type == CHECKBOX || m_type == SUBMIT || m_type == \
RESET || m_type == BUTTON ) {
- bool check = false;
- if (active() && ( evt->id() == EventImpl::KEYUP_EVENT ||
- evt->id() == EventImpl::KHTML_KEYPRESS_EVENT ) ) {
- TextEventImpl *te = static_cast<TextEventImpl *>(evt);
- if (te->keyVal() == ' ')
- check = true;
- }
- if (check) {
- if (evt->id() == EventImpl::KEYUP_EVENT)
- click();
- // Tell the parent that we handle this key (keyup and keydown), even though \
only keyup activates (#70478)
- evt->setDefaultHandled();
- }
- }
-
-
- // DOMActivate events cause the input to be "activated" - in the case of \
image and submit inputs, this means
- // actually submitting the form. For reset inputs, the form is reset. These \
events are sent when the user clicks
- // on the element, or presses enter while it is the active element. \
Javascript code wishing to activate the element
- // must dispatch a DOMActivate event - a click event will not do the job.
- if (m_type == IMAGE || m_type == SUBMIT || m_type == RESET) {
- bool act = (evt->id() == EventImpl::DOMACTIVATE_EVENT);
- if (!act && evt->id() == EventImpl::KEYUP_EVENT) {
- QKeyEvent *ke = static_cast<TextEventImpl *>(evt)->qKeyEvent;
- if (ke && active() && (ke->key() == Qt::Key_Return || ke->key() == Qt::Key_Enter \
|| ke->key() == Qt::Key_Space))
- act = true;
- }
- if (act)
- activate();
- }
+ switch ( evt->id() )
+ {
+ case EventImpl::KEYUP_EVENT:
+ case EventImpl::KHTML_KEYPRESS_EVENT:
+ if ( static_cast<TextEventImpl *>(evt)->keyVal() == ' ' && active() && (m_type == \
RADIO || + m_type == CHECKBOX ||
+ m_type == SUBMIT ||
+ m_type == RESET ||
+ m_type == BUTTON ) )
+ evt->setDefaultHandled();
+
+ break;
+ case EventImpl::DOMACTIVATE_EVENT:
+ if (m_type == BUTTON || m_type == IMAGE || m_type == SUBMIT || m_type == RESET)
+ {
+ DOMActivateEventImpl *ae = static_cast<DOMActivateEventImpl*>(evt);
+ if (ae->parent() && ae->parent()->id()==EventImpl::CLICK_EVENT && m_type == \
IMAGE && m_render) + {
+ MouseEventImpl *me = static_cast<MouseEventImpl*>(ae->parent());
+ // record the mouse position for when we get the DOMActivate event
+ int offsetX, offsetY;
+ m_render->absolutePosition(offsetX,offsetY);
+ xPos = me->clientX()-offsetX;
+ yPos = me->clientY()-offsetY;
+ }
+ activate();
+ evt->setDefaultHandled();
+ }
+ break;
+ default:
+ break;
+ };
}
HTMLGenericFormElementImpl::defaultEventHandler(evt);
}
@@ -1601,26 +1581,25 @@ return newNode;
void HTMLLabelElementImpl::defaultEventHandler(EventImpl *evt)
{
if ( !m_disabled ) {
- bool act = false;
- if ( evt->id() == EventImpl::CLICK_EVENT ) {
- act = true;
- }
- else if ( evt->id() == EventImpl::KEYUP_EVENT ||
- evt->id() == EventImpl::KHTML_KEYPRESS_EVENT ) {
- QKeyEvent *ke = static_cast<TextEventImpl *>(evt)->qKeyEvent;
- if (ke && active() && (ke->key() == Qt::Key_Return || ke->key() == \
Qt::Key_Enter || ke->key() == Qt::Key_Space))
- act = true;
- }
+ if (evt->id()==EventImpl::DOMACTIVATE_EVENT) {
- if (act) {
- NodeImpl *formNode=getFormElement();
- if (formNode) {
- getDocument()->setFocusNode(formNode);
- if (formNode->id()==ID_INPUT)
- static_cast<DOM::HTMLInputElementImpl*>(formNode)->click();
- }
- evt->setDefaultHandled();
- }
+ NodeImpl *formNode=getFormElement();
+
+ if (formNode) {
+ Node guard(formNode);
+ getDocument()->setFocusNode(formNode);
+ if (formNode->isSelectable())
+ {
+ kdDebug ( 6000 ) << " activating label's target\n";
+ int exceptioncode = 0;
+ DOMActivateEventImpl *ae = new \
DOMActivateEventImpl(getDocument()->defaultView(), 1, static_cast<UIEventImpl \
*>(evt)); + ae->ref();
+ formNode->dispatchEvent(ae,exceptioncode,true);
+ ae->deref();
+ }
+ }
+ evt->setDefaultHandled();
+ }
}
HTMLGenericFormElementImpl::defaultEventHandler(evt);
}
Index: html/html_formimpl.h
===================================================================
RCS file: /home/kde/kdelibs/khtml/html/html_formimpl.h,v
retrieving revision 1.154
diff -u -3 -p -r1.154 html_formimpl.h
--- html/html_formimpl.h 12 Jul 2004 19:57:03 -0000 1.154
+++ html/html_formimpl.h 13 Jul 2004 20:09:27 -0000
@@ -273,6 +273,7 @@ public:
void select();
void click();
+ void activate();
virtual void parseAttribute(AttributeImpl *attr);
@@ -286,11 +287,11 @@ public:
int clickX() const { return xPos; }
int clickY() const { return yPos; }
+ virtual void handleLocalEvents(EventImpl *, bool);
virtual void defaultEventHandler(EventImpl *evt);
virtual bool isEditable();
DOMString altText() const;
- void activate();
protected:
Index: html/html_inlineimpl.cpp
===================================================================
RCS file: /home/kde/kdelibs/khtml/html/html_inlineimpl.cpp,v
retrieving revision 1.134
diff -u -3 -p -r1.134 html_inlineimpl.cpp
--- html/html_inlineimpl.cpp 18 Mar 2004 13:41:37 -0000 1.134
+++ html/html_inlineimpl.cpp 13 Jul 2004 20:09:27 -0000
@@ -51,43 +51,21 @@ NodeImpl::Id HTMLAnchorElementImpl::id()
void HTMLAnchorElementImpl::defaultEventHandler(EventImpl *evt)
{
- bool keydown = evt->id() == EventImpl::KEYDOWN_EVENT;
+ if (evt->id()==EventImpl::DOMACTIVATE_EVENT)
+ {
+ DOMActivateEventImpl *ae = static_cast<DOMActivateEventImpl*>(evt);
- // React on clicks and on keypresses.
- // Don't make this KEYUP_EVENT again, it makes khtml follow links
- // it shouldn't, when pressing Enter in the combo.
- if ( ( (evt->id() == EventImpl::CLICK_EVENT && \
!static_cast<MouseEventImpl*>(evt)->isDoubleClick()) ||
- ( keydown && m_focused)) && m_hasAnchor) {
-
- MouseEventImpl *e = 0;
- if ( evt->id() == EventImpl::CLICK_EVENT )
- e = static_cast<MouseEventImpl*>( evt );
-
- TextEventImpl *k = 0;
- if (keydown)
- k = static_cast<TextEventImpl *>( evt );
+ MouseEventImpl *e = NULL;
+ if (ae->parent() && ae->parent()->id() == EventImpl::CLICK_EVENT)
+ e = static_cast <MouseEventImpl *>(ae->parent());
- QString utarget;
- QString url;
if ( e && e->button() == 2 ) {
HTMLElementImpl::defaultEventHandler(evt);
return;
}
- if ( k ) {
- if (k->virtKeyVal() != TextEventImpl::DOM_VK_ENTER) {
- if (k->qKeyEvent)
- k->qKeyEvent->ignore();
- HTMLElementImpl::defaultEventHandler(evt);
- return;
- }
- if (k->qKeyEvent) k->qKeyEvent->accept();
- }
-
- url = khtml::parseURL(getAttribute(ATTR_HREF)).string();
-
- utarget = getAttribute(ATTR_TARGET).string();
-
+ QString utarget = getAttribute(ATTR_TARGET).string();
+ QString url = khtml::parseURL(getAttribute(ATTR_HREF)).string();
if ( e && e->button() == 1 )
utarget = "_blank";
@@ -117,45 +95,61 @@ void HTMLAnchorElementImpl::defaultEvent
}
}
}
- if ( !evt->defaultPrevented() ) {
- int state = 0;
- int button = 0;
-
- if ( e ) {
- if ( e->ctrlKey() )
- state |= Qt::ControlButton;
- if ( e->shiftKey() )
- state |= Qt::ShiftButton;
- if ( e->altKey() )
- state |= Qt::AltButton;
- if ( e->metaKey() )
- state |= Qt::MetaButton;
-
- if ( e->button() == 0 )
- button = Qt::LeftButton;
- else if ( e->button() == 1 )
- button = Qt::MidButton;
- else if ( e->button() == 2 )
- button = Qt::RightButton;
- }
- else if ( k )
- {
- if ( k->checkModifier(Qt::ShiftButton) )
+
+ TextEventImpl *k = NULL;
+ if (ae->parent() && (ae->parent()->id() == EventImpl::KEYUP_EVENT || \
ae->parent()->id() == EventImpl::KHTML_KEYPRESS_EVENT)) + k = static_cast \
<TextEventImpl *>(ae->parent()); +
+ int state = 0;
+ int button = 0;
+ if ( e ) {
+ if ( e->ctrlKey() )
+ state |= Qt::ControlButton;
+ if ( e->shiftKey() )
+ state |= Qt::ShiftButton;
+ if ( e->altKey() )
+ state |= Qt::AltButton;
+ if ( e->metaKey() )
+ state |= Qt::MetaButton;
+
+ if ( e->button() == 0 )
+ button = Qt::LeftButton;
+ else if ( e->button() == 1 )
+ button = Qt::MidButton;
+ else if ( e->button() == 2 )
+ button = Qt::RightButton;
+ }
+ else if ( k )
+ {
+ if ( k->checkModifier(Qt::ShiftButton) )
state |= Qt::ShiftButton;
- if ( k->checkModifier(Qt::AltButton) )
+ if ( k->checkModifier(Qt::AltButton) )
state |= Qt::AltButton;
- if ( k->checkModifier(Qt::ControlButton) )
+ if ( k->checkModifier(Qt::ControlButton) )
state |= Qt::ControlButton;
- }
+ }
- // ### also check if focused node is editable if not in designmode,
- // and prevent link loading then (LS)
- if (getDocument()->view() && !getDocument()->designMode())
- getDocument()->view()->part()->
- urlSelected( url, button, state, utarget );
- }
- evt->setDefaultHandled();
+ // ### also check if focused node is editable if not in designmode,
+ // and prevent link loading then (LS)
+ if (getDocument()->view() && !getDocument()->designMode())
+ getDocument()->view()->part()->
+ urlSelected( url, button, state, utarget );
+
+ evt->setDefaultHandled();
}
+ else if (evt->id()==EventImpl::KEYUP_EVENT || \
evt->id()==EventImpl::KHTML_KEYPRESS_EVENT) + {
+ TextEventImpl * k = static_cast<TextEventImpl*>(evt);
+
+ if (k->virtKeyVal() != TextEventImpl::DOM_VK_ENTER) {
+ if (k->qKeyEvent)
+ k->qKeyEvent->ignore();
+ HTMLElementImpl::defaultEventHandler(evt);
+ return;
+ }
+ if (k->qKeyEvent) k->qKeyEvent->accept();
+ }
+
HTMLElementImpl::defaultEventHandler(evt);
}
Index: xml/dom2_eventsimpl.cpp
===================================================================
RCS file: /home/kde/kdelibs/khtml/xml/dom2_eventsimpl.cpp,v
retrieving revision 1.46
diff -u -3 -p -r1.46 dom2_eventsimpl.cpp
--- xml/dom2_eventsimpl.cpp 24 Feb 2004 16:11:56 -0000 1.46
+++ xml/dom2_eventsimpl.cpp 13 Jul 2004 20:09:27 -0000
@@ -731,6 +731,24 @@ bool TextEventImpl::isTextEvent() const
return true;
}
+
+// -----------------------------------------------------------------------------
+
+DOMActivateEventImpl::DOMActivateEventImpl(AbstractViewImpl *viewArg,
+ long detailArg, UIEventImpl *_parent)
+ : UIEventImpl(DOMACTIVATE_EVENT, true, true, viewArg, detailArg)
+{
+ if (_parent)
+ _parent->ref();
+ m_parent = _parent;
+}
+
+DOMActivateEventImpl::~DOMActivateEventImpl()
+{
+ if (m_parent)
+ m_parent->deref();
+}
+
// -----------------------------------------------------------------------------
MutationEventImpl::MutationEventImpl()
Index: xml/dom2_eventsimpl.h
===================================================================
RCS file: /home/kde/kdelibs/khtml/xml/dom2_eventsimpl.h,v
retrieving revision 1.41
diff -u -3 -p -r1.41 dom2_eventsimpl.h
--- xml/dom2_eventsimpl.h 24 Feb 2004 16:11:56 -0000 1.41
+++ xml/dom2_eventsimpl.h 13 Jul 2004 20:09:27 -0000
@@ -360,6 +360,25 @@ private:
unsigned long m_modifier;
};
+
+// the domactivate event acts like a normal UIEvent,
+// but carries the ui event that caused it in the
+// property "getParent()".
+// parent() can be 0 for activate events generated
+// by javascript code.
+
+class DOMActivateEventImpl : public UIEventImpl
+{
+public:
+ DOMActivateEventImpl(AbstractViewImpl *viewArg,
+ long detailArg, UIEventImpl *_parent);
+ virtual ~DOMActivateEventImpl();
+ UIEventImpl *parent() const { return m_parent; }
+ private:
+ DOMActivateEventImpl() : UIEventImpl() {}
+ UIEventImpl * m_parent;
+};
+
class MutationEventImpl : public EventImpl {
// ### fire these during parsing (if necessary)
public:
Index: xml/dom_nodeimpl.cpp
===================================================================
RCS file: /home/kde/kdelibs/khtml/xml/dom_nodeimpl.cpp,v
retrieving revision 1.236
diff -u -3 -p -r1.236 dom_nodeimpl.cpp
--- xml/dom_nodeimpl.cpp 12 Jun 2004 15:05:03 -0000 1.236
+++ xml/dom_nodeimpl.cpp 13 Jul 2004 20:09:27 -0000
@@ -414,12 +414,13 @@ void NodeImpl::dispatchGenericEvent( Eve
nodeChain.prepend(n);
}
+ QPtrListIterator<NodeImpl> it(nodeChain);
+
// trigger any capturing event handlers on our way down
evt->setEventPhase(Event::CAPTURING_PHASE);
- QPtrListIterator<NodeImpl> it(nodeChain);
for (; it.current() && it.current() != this && !evt->propagationStopped(); ++it) \
{
- evt->setCurrentTarget(it.current());
- it.current()->handleLocalEvents(evt,true);
+ evt->setCurrentTarget(it.current());
+ it.current()->handleLocalEvents(evt,true);
}
// dispatch to the actual target node
@@ -427,6 +428,9 @@ void NodeImpl::dispatchGenericEvent( Eve
if (!evt->propagationStopped()) {
evt->setEventPhase(Event::AT_TARGET);
evt->setCurrentTarget(it.current());
+#ifdef EVENTS_DEBUG
+ kdDebug(6000) << "handling event at "<<it.current()->nodeName().string()<<endl;
+#endif
it.current()->handleLocalEvents(evt, true);
if (!evt->propagationStopped())
it.current()->handleLocalEvents(evt,false);
@@ -449,11 +453,53 @@ void NodeImpl::dispatchGenericEvent( Eve
evt->setEventPhase(0); // I guess this is correct, the spec does not seem to \
say
for (it.toLast(); it.current() && it.current() != propagationSentinel &&
!evt->defaultPrevented() && !evt->defaultHandled(); --it)
+ {
+#ifdef EVENTS_DEBUG
+ kdDebug(6000) << "default event handler of \
"<<it.current()->nodeName().string()<<endl; +#endif
it.current()->defaultEventHandler(evt);
+ }
- if (evt->id() == EventImpl::CLICK_EVENT && !evt->defaultPrevented() &&
- static_cast<MouseEventImpl*>( evt )->button() == 0) // LMB click
- dispatchUIEvent(EventImpl::DOMACTIVATE_EVENT, \
static_cast<UIEventImpl*>(evt)->detail()); + if (!evt->defaultPrevented()) {
+ if (evt->id() == EventImpl::CLICK_EVENT && static_cast<MouseEventImpl*>( evt \
)->isDoubleClick() && static_cast<MouseEventImpl*>( evt )->button()==0) + {
+ // hyper activation event resulting from e.g. double click
+
+ DOMActivateEventImpl *ae = new DOMActivateEventImpl(getDocument()->defaultView(), \
2, static_cast<UIEventImpl*>(evt)); + int exceptioncode = 0;
+ ae->ref();
+ dispatchEvent(ae,exceptioncode,true);
+ ae->deref();
+ }
+ else if ((evt->id() == EventImpl::CLICK_EVENT && static_cast<MouseEventImpl*>( \
evt )->button() == 0) || + (evt->id() == EventImpl::KEYUP_EVENT && \
static_cast<TextEventImpl*>( evt )->keyVal() == ' ')) + {
+ // simple activation event
+
+#ifdef EVENTS_DEBUG
+ kdDebug(6000) << "generating activate event on " << nodeName().string() << endl;
+#endif
+ DOMActivateEventImpl *ae = new DOMActivateEventImpl(getDocument()->defaultView(), \
1, static_cast<UIEventImpl*>(evt)); +
+ int exceptioncode = 0;
+ ae->ref();
+ dispatchEvent(ae,exceptioncode,true);
+ ae->deref();
+ }
+ else if (evt->id() == EventImpl::DOMACTIVATE_EVENT)
+ {
+ // trigger legacy onclick & ondblclick handlers after a successful activate event
+
+#ifdef EVENTS_DEBUG
+ kdDebug(6000) << "generating CLICK event on " << nodeName().string() << endl;
+#endif
+ DOMActivateEventImpl *ae = static_cast<DOMActivateEventImpl*> ( evt );
+ if (ae->detail() == 1)
+ dispatchHTMLEvent(EventImpl::KHTML_ECMA_CLICK_EVENT, false, true);
+ else if (ae->detail() == 2)
+ dispatchHTMLEvent(EventImpl::KHTML_ECMA_DBLCLICK_EVENT, false, true);
+ }
+ }
}
// copy this over into a local variable, as the following deref() calls might \
cause this to be deleted. @@ -620,23 +666,30 @@ void \
NodeImpl::handleLocalEvents(EventIm
if (current->id == evt->id() && current->useCapture == useCapture)
current->listener->handleEvent(ev);
- // ECMA legacy hack
- if (current->useCapture == useCapture && evt->id() == \
EventImpl::CLICK_EVENT) {
- MouseEventImpl* me = static_cast<MouseEventImpl*>(evt);
- // To find whether to call onclick or ondblclick, we can't
- // * use me->detail(), it's 2 when clicking twice w/o moving, even very \
slowly
- // * use me->qEvent(), it's not available when using \
initMouseEvent/dispatchEvent
- // So we currently store a bool in MouseEventImpl. If anyone needs to \
trigger
- // dblclicks from the DOM API, we'll need a timer here (well in the \
doc).
- if ( ( !me->isDoubleClick() && current->id == \
EventImpl::KHTML_ECMA_CLICK_EVENT) ||
- ( me->isDoubleClick() && current->id == \
EventImpl::KHTML_ECMA_DBLCLICK_EVENT) )
- current->listener->handleEvent(ev);
- }
}
}
-void NodeImpl::defaultEventHandler(EventImpl *)
+void NodeImpl::defaultEventHandler(EventImpl *evt)
{
+ if (isSelectable() && evt->target() == this)
+ {
+ if (evt->id()==EventImpl::MOUSEDOWN_EVENT || \
evt->id()==EventImpl::KEYDOWN_EVENT) + {
+ setActive();
+ }
+ else if (evt->id() == EventImpl::MOUSEUP_EVENT || \
evt->id()==EventImpl::KEYUP_EVENT) + {
+ if (m_active)
+ {
+ setActive(false);
+ setFocus();
+ }
+ else {
+ setActive(false);
+ }
+ }
+ evt->setDefaultHandled();
+ }
}
unsigned long NodeImpl::childNodeCount()
Index: xml/dom_nodeimpl.h
===================================================================
RCS file: /home/kde/kdelibs/khtml/xml/dom_nodeimpl.h,v
retrieving revision 1.159
diff -u -3 -p -r1.159 dom_nodeimpl.h
--- xml/dom_nodeimpl.h 12 Jun 2004 15:05:03 -0000 1.159
+++ xml/dom_nodeimpl.h 13 Jul 2004 20:09:27 -0000
@@ -238,7 +238,7 @@ public:
// this matches the logic in KHTMLView.
bool dispatchKeyEvent(QKeyEvent *key, bool keypress);
- void handleLocalEvents(EventImpl *evt, bool useCapture);
+ virtual void handleLocalEvents(EventImpl *evt, bool useCapture);
/**
* Perform the default action for an event e.g. submitting a form
[prev in list] [next in list] [prev in thread] [next in thread]
Configure |
About |
News |
Add a list |
Sponsored by KoreLogic