Skip to content

Commit 4c77a87

Browse files
authored
Improve <Show> reference (#1163)
1 parent 9a11242 commit 4c77a87

File tree

1 file changed

+72
-31
lines changed

1 file changed

+72
-31
lines changed

src/routes/reference/components/show.mdx

Lines changed: 72 additions & 31 deletions
Original file line numberDiff line numberDiff line change
@@ -3,48 +3,89 @@ title: <Show>
33
order: 5
44
---
55

6-
The `Show` control flow is used to conditionally render part of the view: it renders children when `when` is truthy, a fallback otherwise. It is similar to the ternary operator `(when ? children : fallback)` but is ideal for templating JSX.
7-
8-
```ts
9-
import { Show } from "solid-js"
10-
import type { JSX } from "solid-js"
11-
12-
function Show<T>(props: {
13-
when: T | undefined | null | false
14-
keyed?: boolean
15-
fallback?: JSX.Element
16-
children: JSX.Element | ((item: T | Accessor<T>) => JSX.Element)
17-
}): () => JSX.Element
18-
```
19-
20-
Here's an example of using the `Show` control flow:
6+
The `<Show>` component is used for conditionally rendering UI elements.
7+
It takes a `when` prop that defines the condition for rendering.
8+
When the `when` prop is truthy, the children of the `<Show>` component are displayed.
9+
Additionally, an optional `fallback` prop can be provided to specify an element that is shown when the condition is falsy.
2110

2211
```tsx
23-
<Show when={state.count > 0} fallback={<div>Loading...</div>}>
24-
<div>My Content</div>
25-
</Show>
12+
import { createSignal, Show } from "solid-js";
13+
14+
function Example() {
15+
const [value, setValue] = createSignal(true);
16+
return (
17+
<div>
18+
<button onClick={() => setValue((prev) => !prev)}>Toggle Show</button>
19+
<Show when={value()} fallback={<div>Fallback Element</div>}>
20+
<div>Child Element</div>
21+
</Show>
22+
</div>
23+
);
24+
}
2625
```
2726

28-
`Show` can also be used as a way of keying blocks to a specific data model. For example the function is re-executed whenever the user model is replaced.
27+
## Keyed rendering
28+
29+
When the `keyed` prop is set to `true`, the children of the `<Show>` component are re-rendered every time the `when` prop changes.
30+
It's important to note that in this case, even if the reference of the `when` prop changes, the children will still re-render.
2931

3032
```tsx
31-
<Show when={state.user} fallback={<div>Loading...</div>} keyed>
32-
{(user) => <div>{user.firstName}</div>}
33-
</Show>
33+
import { createSignal, Show } from "solid-js";
34+
35+
function KeyedExample() {
36+
const [user, setUser] = createSignal({ name: "John Wick" });
37+
38+
function update() {
39+
// This operation changes the reference of the user object.
40+
setUser({ ...user() });
41+
}
42+
43+
return (
44+
<div>
45+
<button onClick={update}>Update</button>
46+
<Show when={user()} keyed>
47+
<p>Name: {user().name}</p>
48+
{/* Updates shown with each click */}
49+
<p>Last updated: {Date.now()}</p>
50+
</Show>
51+
</div>
52+
);
53+
}
3454
```
3555

36-
If the `keyed` property is not used, the argument of the child function will be an accessor containing the item.
56+
## Render function
57+
58+
The `<Show>` component can also accept a render function as its child.
59+
In this case, the first argument of the render function is an _accessor_ to the `when` prop.
60+
However, when the `keyed` prop is set to `true`, the argument is the `when` prop itself instead of an accessor.
61+
62+
The render function is treated like a separate component.
63+
A key point to understand is that the render function is wrapped in [`untrack`](/reference/reactive-utilities/untrack).
64+
As a result, any changes to signals accessed directly within the render function will not trigger updates.
65+
66+
For example, in the following code, clicking the increment button does not update the count value displayed on the screen because the `count` signal is not tracked.
3767

3868
```tsx
39-
<Show when={state.user} fallback={<div>Loading...</div>}>
40-
{(user) => <div>{user().firstName}</div>}
41-
</Show>
69+
import { createSignal, Show } from "solid-js";
70+
71+
function RenderFunctionExample() {
72+
const [count, setCount] = createSignal(0);
73+
return (
74+
<div>
75+
<button onClick={() => setCount((c) => c + 1)}>Increment</button>
76+
{/* This does not update because the count signal is not being tracked. */}
77+
<Show when={count()}>{(c) => count()}</Show>
78+
{/* This will update because the outer JSX element creates a tracking scope. */}
79+
<Show when={count()}>{(c) => <>{count()}</>}</Show>
80+
</div>
81+
);
82+
}
4283
```
4384

4485
## Props
4586

46-
| Name | Type | Description |
47-
| :--------- | :-------------------------------- | :-------------------------------------------- |
48-
| `when` | `T \| undefined \| null \| false` | The value to test for truthiness |
49-
| `keyed` | `boolean` | Whether to key the block to the value of when |
50-
| `fallback` | `JSX.Element` | The fallback to render when the `when` is falsy |
87+
| Name | Type | Description |
88+
| :--------- | :-------------------------------- | :---------------------------------------------------- |
89+
| `when` | `T \| undefined \| null \| false` | The condition value. |
90+
| `keyed` | `boolean` | Whether to key the block to the value of when. |
91+
| `fallback` | `JSX.Element` | The fallback to render when the `when` prop is falsy. |

0 commit comments

Comments
 (0)