diff --git a/packages/yew/src/virtual_dom/listeners.rs b/packages/yew/src/virtual_dom/listeners.rs index 5b3099e9fb2..0b4e0859012 100644 --- a/packages/yew/src/virtual_dom/listeners.rs +++ b/packages/yew/src/virtual_dom/listeners.rs @@ -502,7 +502,7 @@ impl Registry { run_handler(&target); - if unsafe { BUBBLE_EVENTS } { + if unsafe { BUBBLE_EVENTS } && !event.cancel_bubble() { let mut el = target; loop { el = match el.parent_element() { @@ -523,7 +523,7 @@ mod tests { use std::marker::PhantomData; use wasm_bindgen_test::{wasm_bindgen_test as test, wasm_bindgen_test_configure}; - use web_sys::{Event, EventInit}; + use web_sys::{Event, EventInit, MouseEvent}; wasm_bindgen_test_configure!(run_in_browser); use crate::{html, html::TargetCast, AppHandle, Component, Context, Html}; @@ -794,6 +794,40 @@ mod tests { assert_count(&el, 4); } + #[test] + fn cancel_bubbling() { + struct CancelBubbling; + + impl Mixin for CancelBubbling { + fn view(ctx: &Context, state: &State) -> Html + where + C: Component, + { + html! { +
+ + {state.action} + +
+ } + } + } + + let (_, el) = init::("a"); + + assert_count(&el, 0); + + el.click(); + assert_count(&el, 1); + + el.click(); + assert_count(&el, 2); + } + fn test_input_listener(make_event: impl Fn() -> E) where E: JsCast + std::fmt::Debug, @@ -858,7 +892,7 @@ mod tests { test_input_listener(|| { web_sys::InputEvent::new_with_event_init_dict( "input", - &web_sys::InputEventInit::new().bubbles(true), + web_sys::InputEventInit::new().bubbles(true), ) .unwrap() }) @@ -869,7 +903,7 @@ mod tests { test_input_listener(|| { web_sys::Event::new_with_event_init_dict( "change", - &web_sys::EventInit::new().bubbles(true), + web_sys::EventInit::new().bubbles(true), ) .unwrap() }) diff --git a/packages/yew/src/virtual_dom/mod.rs b/packages/yew/src/virtual_dom/mod.rs index d763f68af59..e9b0e1b5493 100644 --- a/packages/yew/src/virtual_dom/mod.rs +++ b/packages/yew/src/virtual_dom/mod.rs @@ -721,7 +721,7 @@ mod benchmarks { let static_ = Attributes::Static(&[]); let dynamic = Attributes::Dynamic { keys: &[], - values: vec![], + values: Box::new([]), }; let map = Attributes::IndexMap(Default::default()); @@ -776,7 +776,7 @@ mod benchmarks { fn make_dynamic(values: Vec) -> Attributes { Attributes::Dynamic { keys: sample_keys(), - values: values.into_iter().map(|v| Some(v)).collect(), + values: values.into_iter().map(Some).collect(), } }