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