From: Gabriel Ivăncescu gabrielopcode@gmail.com
Signed-off-by: Gabriel Ivăncescu gabrielopcode@gmail.com --- dlls/mshtml/htmlevent.c | 16 +++++++++--- dlls/mshtml/tests/events.js | 49 ++++++++++++++++++++++++++++++++++--- 2 files changed, 57 insertions(+), 8 deletions(-)
diff --git a/dlls/mshtml/htmlevent.c b/dlls/mshtml/htmlevent.c index 68f20607c7b..a8cff87c8a2 100644 --- a/dlls/mshtml/htmlevent.c +++ b/dlls/mshtml/htmlevent.c @@ -2041,15 +2041,23 @@ static HRESULT WINAPI DOMEvent_get_isTrusted(IDOMEvent *iface, VARIANT_BOOL *p) static HRESULT WINAPI DOMEvent_put_cancelBubble(IDOMEvent *iface, VARIANT_BOOL v) { DOMEvent *This = impl_from_IDOMEvent(iface); - FIXME("(%p)->(%x)\n", This, v); - return E_NOTIMPL; + + TRACE("(%p)->(%x)\n", This, v); + + if(This->phase < 2) + return S_OK; + + return DOMEvent_stopPropagation(&This->IDOMEvent_iface); }
static HRESULT WINAPI DOMEvent_get_cancelBubble(IDOMEvent *iface, VARIANT_BOOL *p) { DOMEvent *This = impl_from_IDOMEvent(iface); - FIXME("(%p)->(%p)\n", This, p); - return E_NOTIMPL; + + TRACE("(%p)->(%p)\n", This, p); + + *p = variant_bool(This->stop_propagation); + return S_OK; }
static HRESULT WINAPI DOMEvent_get_srcElement(IDOMEvent *iface, IHTMLElement **p) diff --git a/dlls/mshtml/tests/events.js b/dlls/mshtml/tests/events.js index 9282d48bacc..a9d0fad3f9d 100644 --- a/dlls/mshtml/tests/events.js +++ b/dlls/mshtml/tests/events.js @@ -255,14 +255,34 @@ sync_test("stop_propagation", function() {
function stop_propagation(e) { calls += "stop,"; + ok(e.cancelBubble === (e.cancelBubble_winetest ? true : false), "cancelBubble before stopPropagation = " + e.cancelBubble); e.stopPropagation(); + e.cancelBubble_winetest = true; + ok(e.cancelBubble === true, "cancelBubble after stopPropagation = " + e.cancelBubble); ok(e.bubbles === true, "bubbles = " + e.bubbles); ok(e.defaultPrevented === false, "defaultPrevented = " + e.defaultPrevented); }
function stop_immediate_propagation(e) { calls += "immediateStop,"; + ok(e.cancelBubble === (e.cancelBubble_winetest ? true : false), "cancelBubble before stopImmediatePropagation = " + e.cancelBubble); e.stopImmediatePropagation(); + e.cancelBubble_winetest = true; + ok(e.cancelBubble === true, "cancelBubble after stopImmediatePropagation = " + e.cancelBubble); + ok(e.bubbles === true, "bubbles = " + e.bubbles); + ok(e.cancelable === true, "cancelable = " + e.cancelable); + ok(e.defaultPrevented === false, "defaultPrevented = " + e.defaultPrevented); + } + + function cancel_bubble(e) { + calls += "cancelBubble,"; + ok(e.cancelBubble === (e.cancelBubble_winetest ? true : false), "cancelBubble before setting cancelBubble = " + e.cancelBubble); + e.cancelBubble = true; + if(e.eventPhase === 1) + ok(e.cancelBubble === (e.cancelBubble_winetest ? true : false), "cancelBubble after setting cancelBubble during capture phase = " + e.cancelBubble); + else + ok(e.cancelBubble === true, "cancelBubble after setting cancelBubble during bubble phase = " + e.cancelBubble); + e.cancelBubble_winetest = e.cancelBubble; ok(e.bubbles === true, "bubbles = " + e.bubbles); ok(e.cancelable === true, "cancelable = " + e.cancelable); ok(e.defaultPrevented === false, "defaultPrevented = " + e.defaultPrevented); @@ -270,16 +290,20 @@ sync_test("stop_propagation", function() {
div1.addEventListener("click", stop_immediate_propagation, true); div1.addEventListener("click", stop_propagation, true); + div1.addEventListener("click", cancel_bubble, true); div1.addEventListener("click", record_call("div1.click(capture)"), true);
div2.addEventListener("click", stop_immediate_propagation, true); + div2.addEventListener("click", cancel_bubble, true); div2.addEventListener("click", stop_propagation, true); div2.addEventListener("click", record_call("div2.click(capture)"), true);
+ div1.addEventListener("click", cancel_bubble, false); div1.addEventListener("click", stop_propagation, false); div1.addEventListener("click", record_call("div1.click(bubble)"), false);
div2.addEventListener("click", stop_propagation, false); + div2.addEventListener("click", cancel_bubble, false); div2.addEventListener("click", record_call("div2.click(bubble)"), false);
calls = ""; @@ -289,29 +313,46 @@ sync_test("stop_propagation", function() { div1.removeEventListener("click", stop_immediate_propagation, true); calls = ""; div2.click(); - ok(calls === "stop,div1.click(capture),", "calls = " + calls); + ok(calls === "stop,cancelBubble,div1.click(capture),", "calls = " + calls);
div1.removeEventListener("click", stop_propagation, true); calls = ""; div2.click(); + ok(calls === "cancelBubble,div1.click(capture),immediateStop,", "calls = " + calls); + + div1.removeEventListener("click", cancel_bubble, true); + calls = ""; + div2.click(); ok(calls === "div1.click(capture),immediateStop,", "calls = " + calls);
div2.removeEventListener("click", stop_immediate_propagation, true); calls = ""; div2.click(); - ok(calls === "div1.click(capture),stop,div2.click(capture),stop,div2.click(bubble),", + ok(calls === "div1.click(capture),cancelBubble,stop,div2.click(capture),stop,cancelBubble,div2.click(bubble),", + "calls = " + calls); + + div2.removeEventListener("click", cancel_bubble, true); + calls = ""; + div2.click(); + ok(calls === "div1.click(capture),stop,div2.click(capture),stop,cancelBubble,div2.click(bubble),", "calls = " + calls);
div2.removeEventListener("click", stop_propagation, true); calls = ""; div2.click(); - ok(calls === "div1.click(capture),div2.click(capture),stop,div2.click(bubble),", + ok(calls === "div1.click(capture),div2.click(capture),stop,cancelBubble,div2.click(bubble),", "calls = " + calls);
div2.removeEventListener("click", stop_propagation, false); calls = ""; div2.click(); - ok(calls === "div1.click(capture),div2.click(capture),div2.click(bubble),stop,div1.click(bubble),", + ok(calls === "div1.click(capture),div2.click(capture),cancelBubble,div2.click(bubble),", + "calls = " + calls); + + div2.removeEventListener("click", cancel_bubble, false); + calls = ""; + div2.click(); + ok(calls === "div1.click(capture),div2.click(capture),div2.click(bubble),cancelBubble,stop,div1.click(bubble),", "calls = " + calls); });