-
-
Notifications
You must be signed in to change notification settings - Fork 22
Expand file tree
/
Copy pathmain.ts
More file actions
98 lines (83 loc) · 2.44 KB
/
Copy pathmain.ts
File metadata and controls
98 lines (83 loc) · 2.44 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
import { Match as M, Schema as S } from 'effect'
import { Command, Runtime } from 'foldkit'
import { Document, html } from 'foldkit/html'
import { m } from 'foldkit/message'
import { Button } from '@foldkit/ui'
// MODEL
export const Model = S.Struct({ count: S.Number })
export type Model = typeof Model.Type
// MESSAGE
export const ClickedDecrement = m('ClickedDecrement')
export const ClickedIncrement = m('ClickedIncrement')
export const ClickedReset = m('ClickedReset')
export const Message = S.Union([
ClickedDecrement,
ClickedIncrement,
ClickedReset,
])
export type Message = typeof Message.Type
// UPDATE
export const update = (
model: Model,
message: Message,
): readonly [Model, ReadonlyArray<Command.Command<Message>>] =>
M.value(message).pipe(
M.withReturnType<
readonly [Model, ReadonlyArray<Command.Command<Message>>]
>(),
M.tagsExhaustive({
ClickedDecrement: () => [{ count: model.count - 1 }, []],
ClickedIncrement: () => [{ count: model.count + 1 }, []],
ClickedReset: () => [{ count: 0 }, []],
}),
)
// INIT
export const init: Runtime.ApplicationInit<Model, Message> = () => [
{ count: 0 },
[],
]
// VIEW
export const view = (model: Model): Document => {
const h = html<Message>()
return {
title: `Counter: ${model.count}`,
body: h.div(
[
h.Class(
'min-h-screen bg-white flex flex-col items-center justify-center gap-6 p-6',
),
],
[
h.p(
[h.Class('text-6xl font-bold text-gray-800')],
[model.count.toString()],
),
h.div(
[h.Class('flex flex-wrap justify-center gap-4')],
[
Button.view<Message>({
onClick: ClickedDecrement(),
toView: attributes =>
h.button([...attributes.button, h.Class(buttonStyle)], ['-']),
}),
Button.view<Message>({
onClick: ClickedReset(),
toView: attributes =>
h.button(
[...attributes.button, h.Class(buttonStyle)],
['Reset'],
),
}),
Button.view<Message>({
onClick: ClickedIncrement(),
toView: attributes =>
h.button([...attributes.button, h.Class(buttonStyle)], ['+']),
}),
],
),
],
),
}
}
// STYLE
const buttonStyle = 'bg-black text-white hover:bg-gray-700 px-4 py-2 transition'