Skip to content

Commit f4b1769

Browse files
committed
docs: explain a workaround for if with typed children
1 parent 1d88934 commit f4b1769

File tree

1 file changed

+94
-0
lines changed

1 file changed

+94
-0
lines changed

website/docs/concepts/html/conditional-rendering.mdx

Lines changed: 94 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -71,3 +71,97 @@ html! {
7171

7272
</TabItem>
7373
</Tabs>
74+
75+
## Using typed children
76+
77+
Assuming you have a component which uses `ChildrenRenderer<T>` or `ChildrenWithProps<T>`, it is currently not possible
78+
to use the `if` syntax. However, as it is possible to use an `Iterator<T>` and `Option<T>` implements the iterator trait
79+
in Rust, this can be transformed into using `for` instead.
80+
81+
Assuming you have the following component structure, `Parent` only accepting children of the type `Child`:
82+
83+
```rust
84+
use yew::prelude::*;
85+
86+
#[function_component(Child)]
87+
fn child() -> Html {
88+
html! {}
89+
}
90+
91+
#[derive(PartialEq, Properties)]
92+
struct ParentProperties {
93+
pub children: ChildrenRenderer<Child>,
94+
}
95+
96+
#[function_component(Parent)]
97+
fn parent() -> Html {
98+
html! {}
99+
}
100+
```
101+
102+
Then it is possible to compose the children using `for`, translating the `bool` condition into an `Option` using
103+
`Option::then`:
104+
105+
<Tabs>
106+
<TabItem value="typed-children-valid" label="Using for">
107+
108+
```rust
109+
110+
use yew::prelude::*;
111+
112+
// component definition
113+
114+
#[function_component(Child)]
115+
fn child() -> Html { html! {} }
116+
117+
#[derive(PartialEq, Properties)]
118+
struct ParentProperties {
119+
pub children: ChildrenRenderer<Child>,
120+
}
121+
122+
#[function_component(Parent)]
123+
fn parent() -> Html { html! {} }
124+
125+
// Making use of the `for` construct
126+
127+
#[function_component(Example)]
128+
fn example() -> Html {
129+
let condition = true; // or false
130+
131+
html! {
132+
<Parent>
133+
<Child /> // first child
134+
<Child /> // second child
135+
{ for condition.then(|| html_nested!(
136+
<Child /> // optional third child
137+
)) }
138+
</Parent>
139+
}
140+
}
141+
```
142+
143+
</TabItem>
144+
145+
<TabItem value="typed-children-invalid" label="Invalid">
146+
147+
What does not work is to use the `if` keyword directly, as it turns the component into an untyped children, which
148+
cannot be assigned to the typed children types.
149+
150+
```rust, compile_fail
151+
use yew::prelude::*;
152+
153+
let condition = true; // or false
154+
155+
html! {
156+
<Parent>
157+
<Child />
158+
<Child />
159+
if condition {
160+
<Child /> // optional third child
161+
}
162+
</Parent>
163+
}
164+
```
165+
166+
</TabItem>
167+
</Tabs>

0 commit comments

Comments
 (0)