1import { interactive, toggleable } from "../element"
2import {
3 TextProperties,
4 background,
5 foreground,
6 text,
7} from "../style_tree/components"
8import { useTheme, Theme } from "../theme"
9import { Margin } from "./icon_button"
10
11interface TextButtonOptions {
12 layer?: Theme["lowest"] | Theme["middle"] | Theme["highest"]
13 color?: keyof Theme["lowest"]
14 margin?: Partial<Margin>
15 text_properties?: TextProperties
16}
17
18type ToggleableTextButtonOptions = TextButtonOptions & {
19 active_color?: keyof Theme["lowest"]
20}
21
22export function text_button({
23 color,
24 layer,
25 margin,
26 text_properties,
27}: TextButtonOptions) {
28 const theme = useTheme()
29 if (!color) color = "base"
30
31 const text_options: TextProperties = {
32 size: "xs",
33 weight: "normal",
34 ...text_properties,
35 }
36
37 const m = {
38 top: margin?.top ?? 0,
39 bottom: margin?.bottom ?? 0,
40 left: margin?.left ?? 0,
41 right: margin?.right ?? 0,
42 }
43
44 return interactive({
45 base: {
46 corner_radius: 6,
47 padding: {
48 top: 1,
49 bottom: 1,
50 left: 6,
51 right: 6,
52 },
53 margin: m,
54 button_height: 22,
55 ...text(layer ?? theme.lowest, "sans", color, text_options),
56 },
57 state: {
58 default: {
59 background: background(layer ?? theme.lowest, color),
60 color: foreground(layer ?? theme.lowest, color),
61 },
62 hovered: {
63 background: background(layer ?? theme.lowest, color, "hovered"),
64 color: foreground(layer ?? theme.lowest, color, "hovered"),
65 },
66 clicked: {
67 background: background(layer ?? theme.lowest, color, "pressed"),
68 color: foreground(layer ?? theme.lowest, color, "pressed"),
69 },
70 },
71 })
72}
73
74export function toggleable_text_button(
75 theme: Theme,
76 { color, active_color, margin }: ToggleableTextButtonOptions
77) {
78 if (!color) color = "base"
79
80 return toggleable({
81 state: {
82 inactive: text_button({ color, margin }),
83 active: text_button({
84 color: active_color ? active_color : color,
85 margin,
86 layer: theme.middle,
87 }),
88 },
89 })
90}