Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Replace mounted with rendered lifecycle method #1072

Merged
merged 2 commits into from Apr 25, 2020
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Jump to
Jump to file
Failed to load files.
Diff view
Diff view
9 changes: 5 additions & 4 deletions examples/node_refs/src/lib.rs
Expand Up @@ -28,11 +28,12 @@ impl Component for Model {
}
}

fn mounted(&mut self) -> ShouldRender {
if let Some(input) = self.refs[self.focus_index].cast::<InputElement>() {
input.focus().unwrap();
fn rendered(&mut self, first_render: bool) {
if first_render {
if let Some(input) = self.refs[self.focus_index].cast::<InputElement>() {
input.focus().unwrap();
}
}
false
}

fn update(&mut self, msg: Self::Message) -> ShouldRender {
Expand Down
27 changes: 12 additions & 15 deletions examples/webgl/src/lib.rs
@@ -1,10 +1,9 @@
use wasm_bindgen::JsCast;
use web_sys::HtmlCanvasElement;
use web_sys::WebGlRenderingContext as GL;
use yew::services::{RenderService, Task};
use yew::{html, Component, ComponentLink, Html, NodeRef, ShouldRender};

use wasm_bindgen::JsCast;

pub struct Model {
canvas: Option<HtmlCanvasElement>,
gl: Option<GL>,
Expand All @@ -31,8 +30,8 @@ impl Component for Model {
}
}

fn mounted(&mut self) -> ShouldRender {
// Once mounted, store references for the canvas and GL context. These can be used for
fn rendered(&mut self, first_render: bool) {
// Once rendered, store references for the canvas and GL context. These can be used for
// resizing the rendering area when the window or canvas element are resized, as well as
// for making GL calls.

Expand All @@ -52,18 +51,16 @@ impl Component for Model {
// done here, such as enabling or disabling depth testing, depth functions, face
// culling etc.

// The callback to request animation frame is passed a time value which can be used for
// rendering motion independent of the framerate which may vary.
let render_frame = self.link.callback(Msg::Render);
let handle = RenderService::new().request_animation_frame(render_frame);
if first_render {
// The callback to request animation frame is passed a time value which can be used for
// rendering motion independent of the framerate which may vary.
let render_frame = self.link.callback(Msg::Render);
let handle = RenderService::new().request_animation_frame(render_frame);

// A reference to the handle must be stored, otherwise it is dropped and the render won't
// occur.
self.render_loop = Some(Box::new(handle));

// Since WebGL is rendered to the canvas "separate" from the DOM, there is no need to
// render the DOM element(s) again.
false
// A reference to the handle must be stored, otherwise it is dropped and the render won't
// occur.
self.render_loop = Some(Box::new(handle));
}
}

fn update(&mut self, msg: Self::Message) -> ShouldRender {
Expand Down
17 changes: 12 additions & 5 deletions yew-functional/tests/lib.rs
Expand Up @@ -181,9 +181,16 @@ fn use_effect_destroys_on_component_drop() {
type TProps = DestroyCalledProps;

fn run(props: &Self::TProps) -> Html {
let (should_rerender, set_rerender) = use_state(|| true);
if *should_rerender {
set_rerender(false);
let (show, set_show) = use_state(|| true);
use_effect_with_deps(
move |_| {
set_show(false);
|| {}
},
(),
);

if *show {
return html! {
<UseEffectComponent destroy_called=props.destroy_called.clone() />
};
Expand All @@ -196,11 +203,11 @@ fn use_effect_destroys_on_component_drop() {
}
let app: App<UseEffectWrapperComponent> = yew::App::new();
let destroy_counter = Rc::new(std::cell::RefCell::new(0));
let destroy_country_c = destroy_counter.clone();
let destroy_counter_c = destroy_counter.clone();
app.mount_with_props(
yew::utils::document().get_element_by_id("output").unwrap(),
DestroyCalledProps {
destroy_called: Rc::new(move || *destroy_country_c.borrow_mut().deref_mut() += 1),
destroy_called: Rc::new(move || *destroy_counter_c.borrow_mut().deref_mut() += 1),
},
);
assert_eq!(1, *destroy_counter.borrow().deref());
Expand Down
11 changes: 7 additions & 4 deletions yew-router/examples/guide/src/guide.rs
Expand Up @@ -34,18 +34,21 @@ impl Component for Guide {
}
}

fn mounted(&mut self) -> ShouldRender {
fn rendered(&mut self, _first_render: bool) {
self.router_agent.send(GetCurrentRoute);
false
}

fn update(&mut self, msg: Self::Message) -> bool {
match msg {
Msg::UpdateRoute(route) => {
self.route = Some(route);
let new_route = Some(route);
if self.route != new_route {
self.route = new_route;
return true;
}
}
}
true
false
}

fn change(&mut self, _: Self::Properties) -> bool {
Expand Down
4 changes: 0 additions & 4 deletions yew-router/examples/guide/src/markdown_window.rs
Expand Up @@ -41,10 +41,6 @@ impl Component for MarkdownWindow {
}
}

fn mounted(&mut self) -> ShouldRender {
false
}

fn update(&mut self, msg: Self::Message) -> bool {
match msg {
Msg::MarkdownArrived(md) => {
Expand Down
3 changes: 1 addition & 2 deletions yew-router/src/router.rs
Expand Up @@ -185,9 +185,8 @@ where
}
}

fn mounted(&mut self) -> ShouldRender {
fn rendered(&mut self, _first_render: bool) {
self.router_agent.send(RouteRequest::GetCurrentRoute);
false
}

fn update(&mut self, msg: Self::Message) -> ShouldRender {
Expand Down
9 changes: 5 additions & 4 deletions yew-stdweb/examples/node_refs/src/lib.rs
Expand Up @@ -29,11 +29,12 @@ impl Component for Model {
}
}

fn mounted(&mut self) -> ShouldRender {
if let Some(input) = self.refs[self.focus_index].cast::<InputElement>() {
input.focus();
fn rendered(&mut self, first_render: bool) {
if first_render {
if let Some(input) = self.refs[self.focus_index].cast::<InputElement>() {
input.focus();
}
}
false
}

fn update(&mut self, msg: Self::Message) -> ShouldRender {
Expand Down
24 changes: 11 additions & 13 deletions yew-stdweb/examples/webgl/src/lib.rs
Expand Up @@ -33,8 +33,8 @@ impl Component for Model {
}
}

fn mounted(&mut self) -> ShouldRender {
// Once mounted, store references for the canvas and GL context. These can be used for
fn rendered(&mut self, first_render: bool) {
// Once rendered, store references for the canvas and GL context. These can be used for
// resizing the rendering area when the window or canvas element are resized, as well as
// for making GL calls.
let c: CanvasElement = self.node_ref.cast().unwrap();
Expand All @@ -47,18 +47,16 @@ impl Component for Model {
// done here, such as enabling or disabling depth testing, depth functions, face
// culling etc.

// The callback to request animation frame is passed a time value which can be used for
// rendering motion independent of the framerate which may vary.
let render_frame = self.link.callback(Msg::Render);
let handle = RenderService::new().request_animation_frame(render_frame);

// A reference to the handle must be stored, otherwise it is dropped and the render won't
// occur.
self.render_loop = Some(Box::new(handle));
if first_render {
// The callback to request animation frame is passed a time value which can be used for
// rendering motion independent of the framerate which may vary.
let render_frame = self.link.callback(Msg::Render);
let handle = RenderService::new().request_animation_frame(render_frame);

// Since WebGL is rendered to the canvas "separate" from the DOM, there is no need to
// render the DOM element(s) again.
false
// A reference to the handle must be stored, otherwise it is dropped and the render won't
// occur.
self.render_loop = Some(Box::new(handle));
}
}

fn update(&mut self, msg: Self::Message) -> ShouldRender {
Expand Down
27 changes: 14 additions & 13 deletions yew/src/html/mod.rs
Expand Up @@ -67,14 +67,9 @@ pub trait Component: Sized + 'static {
/// Components are created with their properties as well as a `ComponentLink` which
/// can be used to send messages and create callbacks for triggering updates.
fn create(props: Self::Properties, link: ComponentLink<Self>) -> Self;
/// Called after the component has been attached to the VDOM and it is safe to receive messages
/// from agents but before the browser updates the screen. If true is returned, the view will
/// be re-rendered and the user will not see the initial render.
fn mounted(&mut self) -> ShouldRender {
false
}
/// Called everytime when a messages of `Msg` type received. It also takes a
/// reference to a context.

/// Components handle messages in their `update` method and commonly use this method
/// to update their state and (optionally) re-render themselves.
fn update(&mut self, msg: Self::Message) -> ShouldRender;

/// When the parent of a Component is re-rendered, it will either be re-created or
Expand Down Expand Up @@ -107,7 +102,12 @@ pub trait Component: Sized + 'static {
/// `html!` procedural macro. The full guide to using the macro can be found in [Yew's
/// documentation](https://yew.rs/docs/concepts/html).
fn view(&self) -> Html;
/// Called for finalization on the final point of the component's lifetime.

/// The `rendered` method is called after each time a Component is rendered but
/// before the browser updates the page.
fn rendered(&mut self, _first_render: bool) {}

/// The `destroy` method is called right before a Component is unmounted.
fn destroy(&mut self) {} // TODO(#941): Replace with `Drop`
}

Expand Down Expand Up @@ -359,11 +359,12 @@ where
/// }
/// }
///
/// fn mounted(&mut self) -> ShouldRender {
/// if let Some(input) = self.node_ref.cast::<InputElement>() {
/// input.focus();
/// fn rendered(&mut self, first_render: bool) {
/// if first_render {
/// if let Some(input) = self.node_ref.cast::<InputElement>() {
/// input.focus();
/// }
/// }
/// false
/// }
///
/// fn change(&mut self, _: Self::Properties) -> ShouldRender {
Expand Down