Properties
プロパティは、子コンポーネントと親コンポーネントが互いに通信できるようにします。
各コンポーネントには、親から渡されるものを記述する関連付けられたプロパティタイプがあります。
理論的には、これは Properties
trait を実装する任意のタイプにすることができますが、実際には
各フィールドがプロパティを表す構造体以外にする理由はありません。
マクロの継承
Properties
を自分で実装しようとせず、代わりに#[derive(Properties)]
を使ってください。
Properties
を継承した型はPartialEq
も実装していなければいけません。
フィールド属性
デフォルトでは、Properties
を導出する構造体内のフィールドは必須です。
以下の属性を使うと、props に初期値を与えることができ、他の値に設定されない限りこの値が使用されます。
Attributes aren't visible in Rustdoc generated documentation. The doc strings of your properties should mention whether a prop is optional and if it has a special default value.
#[prop_or_default]
Initialize the prop value with the default value of the field's type using the Default
trait.
#[prop_or(value)]
Use value
to initialize the prop value. value
can be any expression that returns the field's type.
For example, to default a boolean prop to true
, use the attribute #[prop_or(true)]
.
#[prop_or_else(function)]
Call function
to initialize the prop value. function
should have the signature FnMut() -> T
where T
is the field type.
PartialEq
もし可能なら props で PartialEq
を継承するのが良いかもしれません。
PartialEq
を使うことで、不必要な再レンダリングを避けることができます
(これについては、最適化とベストプラクティスのセクションで説明しています)。
プロパティを使用する際のメモリと速度のオーバーヘッド
Component::view
ではコンポーネントの状態への参照を取り、それを使って Html
を作成します。
しかし、プロパティは自身の値です。
つまり、それらを作成して子コンポーネントに渡すためには、view
関数で提供される参照を所有する必要があるのです。
これは所有する値を取得するためにコンポーネントに渡される参照を暗黙のうちにクローンすることで行われます。
Make use of AttrValue
which is our custom type for attribute values instead of defining them as String or another similar type.
Example
use yew::Properties;
/// Importing the AttrValue from virtual_dom
use yew::virtual_dom::AttrValue;
#[derive(Clone, PartialEq)]
pub enum LinkColor {
Blue,
Red,
Green,
Black,
Purple,
}
fn create_default_link_color() -> LinkColor {
LinkColor::Blue
}
#[derive(Properties, PartialEq)]
pub struct LinkProps {
/// The link must have a target.
href: AttrValue,
/// Also notice that we are using AttrValue instead of String
text: AttrValue,
/// Color of the link. Defaults to `Blue`.
#[prop_or_else(create_default_link_color)]
color: LinkColor,
/// The view function will not specify a size if this is None.
#[prop_or_default]
size: Option<u32>,
/// When the view function does not specify active, it defaults to true.
#[prop_or(true)]
active: bool,
}
Props macro
The yew::props!
macro allows you to build properties the same way the html!
macro does it.
The macro uses the same syntax as a struct expression except that you cannot use attributes or a base expression (Foo { ..base }
).
The type path can either point to the props directly (path::to::Props
) or the associated properties of a component (MyComp::Properties
).
use yew::{props, Properties, virtual_dom::AttrValue};
#[derive(Clone, PartialEq)]
pub enum LinkColor {
Blue,
Red,
Green,
Black,
Purple,
}
fn create_default_link_color() -> LinkColor {
LinkColor::Blue
}
#[derive(Properties, PartialEq)]
pub struct LinkProps {
/// The link must have a target.
href: AttrValue,
/// Also notice that we're using AttrValue instead of String
text: AttrValue,
/// Color of the link. Defaults to `Blue`.
#[prop_or_else(create_default_link_color)]
color: LinkColor,
/// The view function will not specify a size if this is None.
#[prop_or_default]
size: Option<u32>,
/// When the view function doesn't specify active, it defaults to true.
#[prop_or(true)]
active: bool,
}
impl LinkProps {
/// Notice that this function receives href and text as String
/// We can use `AttrValue::from` to convert it to a `AttrValue`
pub fn new_link_with_size(href: String, text: String, size: u32) -> Self {
props! {LinkProps {
href: AttrValue::from(href),
text: AttrValue::from(text),
size,
}}
}
}