From 16b7370d8cac304eb2af800b9c6a584784a0c600 Mon Sep 17 00:00:00 2001 From: Adam <2363879+adamdotdevin@users.noreply.github.com> Date: Thu, 11 Dec 2025 13:02:57 -0600 Subject: wip(desktop): progress --- packages/ui/src/components/dialog.css | 11 +++ packages/ui/src/components/icon.tsx | 2 + packages/ui/src/components/input.css | 99 --------------------- packages/ui/src/components/input.tsx | 75 ---------------- packages/ui/src/components/list.css | 3 + packages/ui/src/components/select-dialog.tsx | 4 +- packages/ui/src/components/text-field.css | 125 +++++++++++++++++++++++++++ packages/ui/src/components/text-field.tsx | 103 ++++++++++++++++++++++ packages/ui/src/styles/index.css | 2 +- 9 files changed, 247 insertions(+), 177 deletions(-) delete mode 100644 packages/ui/src/components/input.css delete mode 100644 packages/ui/src/components/input.tsx create mode 100644 packages/ui/src/components/text-field.css create mode 100644 packages/ui/src/components/text-field.tsx (limited to 'packages/ui') diff --git a/packages/ui/src/components/dialog.css b/packages/ui/src/components/dialog.css index 1c7cd4f41..979906e26 100644 --- a/packages/ui/src/components/dialog.css +++ b/packages/ui/src/components/dialog.css @@ -88,8 +88,19 @@ flex-direction: column; flex: 1; overflow-y: auto; + + &:focus-visible { + outline: none; + } + } + &:focus-visible { + outline: none; } } + + &:focus-visible { + outline: none; + } } } diff --git a/packages/ui/src/components/icon.tsx b/packages/ui/src/components/icon.tsx index 56cef2d8c..ce4bf7556 100644 --- a/packages/ui/src/components/icon.tsx +++ b/packages/ui/src/components/icon.tsx @@ -47,6 +47,8 @@ const icons = { "layout-bottom-full": ``, "dot-grid": ``, "circle-check": ``, + copy: ``, + check: ``, } export interface IconProps extends ComponentProps<"svg"> { diff --git a/packages/ui/src/components/input.css b/packages/ui/src/components/input.css deleted file mode 100644 index 276e8069b..000000000 --- a/packages/ui/src/components/input.css +++ /dev/null @@ -1,99 +0,0 @@ -[data-component="input"] { - width: 100%; - - [data-slot="input-input"] { - width: 100%; - color: var(--text-strong); - - /* text-14-regular */ - font-family: var(--font-family-sans); - font-size: 14px; - font-style: normal; - font-weight: var(--font-weight-regular); - line-height: var(--line-height-large); /* 142.857% */ - letter-spacing: var(--letter-spacing-normal); - - &:focus { - outline: none; - } - - &::placeholder { - color: var(--text-weak); - } - } - - &[data-variant="normal"] { - display: flex; - flex-direction: column; - align-items: flex-start; - gap: 8px; - - [data-slot="input-label"] { - color: var(--text-weak); - - /* text-12-medium */ - font-family: var(--font-family-sans); - font-size: var(--font-size-small); - font-style: normal; - font-weight: var(--font-weight-medium); - line-height: 18px; /* 150% */ - letter-spacing: var(--letter-spacing-normal); - } - - [data-slot="input-input"] { - color: var(--text-strong); - - display: flex; - height: 32px; - padding: 2px 12px; - align-items: center; - gap: 8px; - align-self: stretch; - - border-radius: var(--radius-md); - border: 1px solid var(--border-weak-base); - background: var(--input-base); - - /* text-14-regular */ - font-family: var(--font-family-sans); - font-size: 14px; - font-style: normal; - font-weight: var(--font-weight-regular); - line-height: var(--line-height-large); /* 142.857% */ - letter-spacing: var(--letter-spacing-normal); - - &:focus { - outline: none; - - /* border/shadow-xs/select */ - box-shadow: - 0 0 0 3px var(--border-weak-selected), - 0 0 0 1px var(--border-selected), - 0 1px 2px -1px rgba(19, 16, 16, 0.25), - 0 1px 2px 0 rgba(19, 16, 16, 0.08), - 0 1px 3px 0 rgba(19, 16, 16, 0.12); - } - - &[data-invalid] { - background: var(--surface-critical-weak); - border: 1px solid var(--border-critical-selected); - } - - &::placeholder { - color: var(--text-weak); - } - } - - [data-slot="input-error"] { - color: var(--text-on-critical-base); - - /* text-12-medium */ - font-family: var(--font-family-sans); - font-size: var(--font-size-small); - font-style: normal; - font-weight: var(--font-weight-medium); - line-height: 18px; /* 150% */ - letter-spacing: var(--letter-spacing-normal); - } - } -} diff --git a/packages/ui/src/components/input.tsx b/packages/ui/src/components/input.tsx deleted file mode 100644 index 8e2a115c6..000000000 --- a/packages/ui/src/components/input.tsx +++ /dev/null @@ -1,75 +0,0 @@ -import { TextField as Kobalte } from "@kobalte/core/text-field" -import { Show, splitProps } from "solid-js" -import type { ComponentProps } from "solid-js" - -export interface InputProps - extends ComponentProps, - Partial< - Pick< - ComponentProps, - | "name" - | "defaultValue" - | "value" - | "onChange" - | "onKeyDown" - | "validationState" - | "required" - | "disabled" - | "readOnly" - > - > { - label?: string - hideLabel?: boolean - hidden?: boolean - description?: string - error?: string - variant?: "normal" | "ghost" -} - -export function Input(props: InputProps) { - const [local, others] = splitProps(props, [ - "name", - "defaultValue", - "value", - "onChange", - "onKeyDown", - "validationState", - "required", - "disabled", - "readOnly", - "class", - "label", - "hidden", - "hideLabel", - "description", - "error", - "variant", - ]) - return ( - - - - {local.label} - - - - - {local.description} - - {local.error} - - ) -} diff --git a/packages/ui/src/components/list.css b/packages/ui/src/components/list.css index 783b0ef4a..132824164 100644 --- a/packages/ui/src/components/list.css +++ b/packages/ui/src/components/list.css @@ -105,6 +105,9 @@ &:active { background: var(--surface-raised-base-active); } + &:focus-visible { + outline: none; + } } } } diff --git a/packages/ui/src/components/select-dialog.tsx b/packages/ui/src/components/select-dialog.tsx index efa6c405b..06953168c 100644 --- a/packages/ui/src/components/select-dialog.tsx +++ b/packages/ui/src/components/select-dialog.tsx @@ -3,7 +3,7 @@ import { Dialog, DialogProps } from "./dialog" import { Icon } from "./icon" import { IconButton } from "./icon-button" import { List, ListRef, ListProps } from "./list" -import { Input } from "./input" +import { TextField } from "./text-field" interface SelectDialogProps extends Omit, "filter">, @@ -55,7 +55,7 @@ export function SelectDialog(props: SelectDialogProps) {
- , + Partial< + Pick< + ComponentProps, + | "name" + | "defaultValue" + | "value" + | "onChange" + | "onKeyDown" + | "validationState" + | "required" + | "disabled" + | "readOnly" + > + > { + label?: string + hideLabel?: boolean + description?: string + error?: string + variant?: "normal" | "ghost" + copyable?: boolean +} + +export function TextField(props: TextFieldProps) { + const [local, others] = splitProps(props, [ + "name", + "defaultValue", + "value", + "onChange", + "onKeyDown", + "validationState", + "required", + "disabled", + "readOnly", + "class", + "label", + "hideLabel", + "description", + "error", + "variant", + "copyable", + ]) + const [copied, setCopied] = createSignal(false) + + async function handleCopy() { + const value = local.value ?? local.defaultValue ?? "" + await navigator.clipboard.writeText(value) + setCopied(true) + setTimeout(() => setCopied(false), 2000) + } + + return ( + + + + {local.label} + + +
+ + + + + + +
+ + {local.description} + + {local.error} +
+ ) +} + +/** @deprecated Use TextField instead */ +export const Input = TextField +/** @deprecated Use TextFieldProps instead */ +export type InputProps = TextFieldProps diff --git a/packages/ui/src/styles/index.css b/packages/ui/src/styles/index.css index 918ba9e44..d60082d93 100644 --- a/packages/ui/src/styles/index.css +++ b/packages/ui/src/styles/index.css @@ -21,7 +21,7 @@ @import "../components/provider-icon.css" layer(components); @import "../components/icon.css" layer(components); @import "../components/icon-button.css" layer(components); -@import "../components/input.css" layer(components); +@import "../components/text-field.css" layer(components); @import "../components/list.css" layer(components); @import "../components/logo.css" layer(components); @import "../components/markdown.css" layer(components); -- cgit v1.2.3