@denarolabs/email-template 1.0.5 → 1.0.6

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (52) hide show
  1. package/dist/index.d.ts +425 -8
  2. package/dist/index.js +9841 -7
  3. package/package.json +16 -23
  4. package/dist/components/ai-email-editor/AIEmailEditor.d.ts +0 -3
  5. package/dist/components/ai-email-editor/AIEmailEditor.js +0 -207
  6. package/dist/components/ai-email-editor/chat-message.d.ts +0 -36
  7. package/dist/components/ai-email-editor/chat-message.js +0 -49
  8. package/dist/components/ai-email-editor/images.d.ts +0 -2
  9. package/dist/components/ai-email-editor/images.js +0 -14
  10. package/dist/components/ai-email-editor/model-picker.d.ts +0 -7
  11. package/dist/components/ai-email-editor/model-picker.js +0 -9
  12. package/dist/components/ai-email-editor/preview.d.ts +0 -35
  13. package/dist/components/ai-email-editor/preview.js +0 -728
  14. package/dist/components/ai-email-editor/send-test-email-modal.d.ts +0 -13
  15. package/dist/components/ai-email-editor/send-test-email-modal.js +0 -70
  16. package/dist/components/ai-email-editor/stream.d.ts +0 -20
  17. package/dist/components/ai-email-editor/stream.js +0 -57
  18. package/dist/components/ai-email-editor/use-ai-email-editor.d.ts +0 -117
  19. package/dist/components/ai-email-editor/use-ai-email-editor.js +0 -1308
  20. package/dist/components/ai-email-editor/view-html-modal.d.ts +0 -9
  21. package/dist/components/ai-email-editor/view-html-modal.js +0 -37
  22. package/dist/lib/ai-stream-contract.d.ts +0 -99
  23. package/dist/lib/ai-stream-contract.js +0 -35
  24. package/dist/lib/build-default-system-prompt.d.ts +0 -2
  25. package/dist/lib/build-default-system-prompt.js +0 -37
  26. package/dist/lib/capture-email-preview.d.ts +0 -5
  27. package/dist/lib/capture-email-preview.js +0 -73
  28. package/dist/lib/cn.d.ts +0 -2
  29. package/dist/lib/cn.js +0 -5
  30. package/dist/lib/merge-tag-validation.d.ts +0 -3
  31. package/dist/lib/merge-tag-validation.js +0 -45
  32. package/dist/lib/rasterize-image-client.d.ts +0 -4
  33. package/dist/lib/rasterize-image-client.js +0 -47
  34. package/dist/lib/strip-html-code-fences.d.ts +0 -1
  35. package/dist/lib/strip-html-code-fences.js +0 -6
  36. package/dist/schemas/aiEmail.d.ts +0 -224
  37. package/dist/schemas/aiEmail.js +0 -29
  38. package/dist/schemas/aiEmailResponse.d.ts +0 -15
  39. package/dist/schemas/aiEmailResponse.js +0 -15
  40. package/dist/types.d.ts +0 -57
  41. package/dist/types.js +0 -1
  42. package/dist/ui/button.d.ts +0 -11
  43. package/dist/ui/button.js +0 -34
  44. package/dist/ui/dialog.d.ts +0 -33
  45. package/dist/ui/dialog.js +0 -39
  46. package/dist/ui/dropdown-menu.d.ts +0 -8
  47. package/dist/ui/dropdown-menu.js +0 -23
  48. package/dist/ui/input.d.ts +0 -2
  49. package/dist/ui/input.js +0 -6
  50. package/dist/ui/textarea.d.ts +0 -2
  51. package/dist/ui/textarea.js +0 -7
  52. package/src/styles.css +0 -197
@@ -1,29 +0,0 @@
1
- import { z } from "zod";
2
- export const AiEmailImageSchema = z.object({
3
- id: z.string().min(1),
4
- url: z.string().min(1),
5
- name: z.string().optional(),
6
- });
7
- export const AiEmailChatMessageSchema = z.object({
8
- id: z.string().min(1),
9
- role: z.enum(["user", "assistant"]),
10
- content: z.string(),
11
- contextImages: z.array(AiEmailImageSchema).optional(),
12
- appliedHtml: z.boolean().optional(),
13
- snapshotId: z.string().optional(),
14
- selectedBlockIds: z.array(z.string()).optional(),
15
- phase: z.enum(["thinking", "planning", "applying"]).optional(),
16
- timestamp: z.number(),
17
- });
18
- export const AiEmailHtmlSnapshotSchema = z.object({
19
- id: z.string().min(1),
20
- html: z.string(),
21
- label: z.string().optional(),
22
- timestamp: z.number(),
23
- });
24
- export const AiEmailSessionSchema = z.object({
25
- messages: z.array(AiEmailChatMessageSchema).default([]),
26
- snapshots: z.array(AiEmailHtmlSnapshotSchema).default([]),
27
- snapshotIndex: z.number().int().min(0).default(0),
28
- contextImages: z.array(AiEmailImageSchema).default([]),
29
- });
@@ -1,15 +0,0 @@
1
- import { z } from "zod";
2
- export declare const AiEmailResponseSchema: z.ZodObject<{
3
- plan: z.ZodArray<z.ZodString, "many">;
4
- suggestions: z.ZodArray<z.ZodString, "many">;
5
- html: z.ZodString;
6
- }, "strip", z.ZodTypeAny, {
7
- html: string;
8
- plan: string[];
9
- suggestions: string[];
10
- }, {
11
- html: string;
12
- plan: string[];
13
- suggestions: string[];
14
- }>;
15
- export type AiEmailResponse = z.infer<typeof AiEmailResponseSchema>;
@@ -1,15 +0,0 @@
1
- import { z } from "zod";
2
- export const AiEmailResponseSchema = z.object({
3
- plan: z
4
- .array(z.string())
5
- .min(2)
6
- .max(4)
7
- .describe("2-4 first-person present-tense bullets describing each change being made to the email"),
8
- suggestions: z
9
- .array(z.string())
10
- .length(3)
11
- .describe("Exactly 3 short follow-up prompts the user might send next, each under 12 words and specific to this email"),
12
- html: z
13
- .string()
14
- .describe("The complete updated HTML document with inline CSS. No markdown, code fences, or commentary."),
15
- });
package/dist/types.d.ts DELETED
@@ -1,57 +0,0 @@
1
- import type { AiEmailSession } from "./schemas/aiEmail";
2
- export type AIEmailEditorMode = "email" | "landing";
3
- export type AIEmailEditorErrorSource = "stream" | "upload" | "save" | "image" | "html" | "send";
4
- export interface AIEmailEditorErrorContext {
5
- source: AIEmailEditorErrorSource;
6
- }
7
- export type AIEmailEditorSuccessSource = "upload" | "save" | "image" | "html" | "undo" | "revert" | "send";
8
- export interface AIEmailEditorSuccessContext {
9
- source: AIEmailEditorSuccessSource;
10
- message: string;
11
- }
12
- export interface SendTestEmailInput {
13
- to: string;
14
- subject: string;
15
- html: string;
16
- mergeTagValues: Record<string, string>;
17
- }
18
- export interface AIEmailModelOption {
19
- id: string;
20
- label: string;
21
- hint?: string;
22
- }
23
- export interface StoredEmailRecord {
24
- id: string;
25
- name: string;
26
- html: string;
27
- createdAt: number;
28
- updatedAt: number;
29
- aiSession?: AiEmailSession;
30
- }
31
- export interface AIEmailEditorProps {
32
- name: string;
33
- savedTemplate: StoredEmailRecord | null;
34
- onSave: (record: StoredEmailRecord) => Promise<void> | void;
35
- streamRoute: string;
36
- mergeTags: string[];
37
- defaultMergeTagValues?: Record<string, string>;
38
- mode?: AIEmailEditorMode;
39
- systemPrompt?: string;
40
- onUploadImage: (file: File | Blob) => Promise<{
41
- url: string;
42
- }>;
43
- onDeleteImage: (url: string) => Promise<void>;
44
- onSendTestEmail?: (input: SendTestEmailInput) => Promise<void>;
45
- defaultTestEmailRecipient?: string;
46
- defaultTestEmailSubject?: string;
47
- onError: (error: Error, context: AIEmailEditorErrorContext) => void;
48
- onSuccess?: (context: AIEmailEditorSuccessContext) => void;
49
- open?: boolean;
50
- onOpenChange?: (open: boolean) => void;
51
- brandLabel?: string;
52
- brandIconUrl?: string;
53
- productLabel?: string;
54
- models?: readonly AIEmailModelOption[];
55
- defaultModel?: string;
56
- initialSuggestions?: readonly string[];
57
- }
package/dist/types.js DELETED
@@ -1 +0,0 @@
1
- export {};
@@ -1,11 +0,0 @@
1
- import { type VariantProps } from "class-variance-authority";
2
- import type { ButtonHTMLAttributes } from "react";
3
- declare const buttonVariants: (props?: ({
4
- variant?: "default" | "destructive" | "outline" | "secondary" | "ghost" | "link" | null | undefined;
5
- size?: "default" | "sm" | "xs" | "icon" | "icon-sm" | "icon-xs" | null | undefined;
6
- } & import("class-variance-authority/types").ClassProp) | undefined) => string;
7
- type ButtonProps = ButtonHTMLAttributes<HTMLButtonElement> & VariantProps<typeof buttonVariants> & {
8
- asChild?: boolean;
9
- };
10
- export declare function Button({ className, variant, size, asChild, type, ...props }: ButtonProps): import("react").JSX.Element;
11
- export { buttonVariants };
package/dist/ui/button.js DELETED
@@ -1,34 +0,0 @@
1
- "use client";
2
- import { jsx as _jsx } from "react/jsx-runtime";
3
- import { Slot } from "@radix-ui/react-slot";
4
- import { cva } from "class-variance-authority";
5
- import { cn } from "../lib/cn";
6
- const buttonVariants = cva("inline-flex shrink-0 items-center justify-center gap-2 rounded-md text-sm font-medium whitespace-nowrap transition-all outline-none focus-visible:border-ring focus-visible:ring-[3px] focus-visible:ring-ring/50 disabled:pointer-events-none disabled:opacity-50 aria-invalid:border-destructive aria-invalid:ring-destructive/20 [&_svg]:pointer-events-none [&_svg]:shrink-0 [&_svg:not([class*='size-'])]:size-4", {
7
- variants: {
8
- variant: {
9
- default: "bg-primary text-primary-foreground hover:bg-primary/90",
10
- destructive: "bg-destructive text-white hover:bg-destructive/90 focus-visible:ring-destructive/20",
11
- outline: "border border-border bg-background shadow-xs hover:bg-accent hover:text-accent-foreground",
12
- secondary: "bg-secondary text-secondary-foreground hover:bg-secondary/80",
13
- ghost: "hover:bg-accent hover:text-accent-foreground",
14
- link: "text-primary underline-offset-4 hover:underline",
15
- },
16
- size: {
17
- default: "h-9 px-4 py-2",
18
- sm: "h-8 gap-1.5 rounded-md px-3 text-xs",
19
- xs: "h-7 gap-1 rounded-md px-2 text-xs",
20
- icon: "size-9",
21
- "icon-sm": "size-8",
22
- "icon-xs": "size-7",
23
- },
24
- },
25
- defaultVariants: {
26
- variant: "default",
27
- size: "default",
28
- },
29
- });
30
- export function Button({ className, variant = "default", size = "default", asChild = false, type = "button", ...props }) {
31
- const Comp = asChild ? Slot : "button";
32
- return (_jsx(Comp, { type: asChild ? undefined : type, "data-slot": "button", className: cn(buttonVariants({ variant, size, className })), ...props }));
33
- }
34
- export { buttonVariants };
@@ -1,33 +0,0 @@
1
- import { type ReactNode } from "react";
2
- export declare function Dialog({ open, onOpenChange, children, }: {
3
- open: boolean;
4
- onOpenChange: (open: boolean) => void;
5
- children: ReactNode;
6
- }): import("react").JSX.Element | null;
7
- export declare function DialogContent({ children, className, fullscreen, showCloseButton, onClose, }: {
8
- children: ReactNode;
9
- className?: string;
10
- fullscreen?: boolean;
11
- showCloseButton?: boolean;
12
- onClose?: () => void;
13
- }): import("react").JSX.Element;
14
- export declare function DialogHeader({ children, className }: {
15
- children: ReactNode;
16
- className?: string;
17
- }): import("react").JSX.Element;
18
- export declare function DialogTitle({ children, className }: {
19
- children: ReactNode;
20
- className?: string;
21
- }): import("react").JSX.Element;
22
- export declare function DialogDescription({ children, className }: {
23
- children: ReactNode;
24
- className?: string;
25
- }): import("react").JSX.Element;
26
- export declare function DialogFooter({ children, className }: {
27
- children: ReactNode;
28
- className?: string;
29
- }): import("react").JSX.Element;
30
- export declare function DialogPanel({ children, className }: {
31
- children: ReactNode;
32
- className?: string;
33
- }): import("react").JSX.Element;
package/dist/ui/dialog.js DELETED
@@ -1,39 +0,0 @@
1
- "use client";
2
- import { Fragment as _Fragment, jsx as _jsx, jsxs as _jsxs } from "react/jsx-runtime";
3
- import { useEffect } from "react";
4
- import { X } from "lucide-react";
5
- import { cn } from "../lib/cn";
6
- import { Button } from "./button";
7
- export function Dialog({ open, onOpenChange, children, }) {
8
- useEffect(() => {
9
- if (!open)
10
- return;
11
- const onKey = (event) => {
12
- if (event.key === "Escape")
13
- onOpenChange(false);
14
- };
15
- window.addEventListener("keydown", onKey);
16
- return () => window.removeEventListener("keydown", onKey);
17
- }, [open, onOpenChange]);
18
- if (!open)
19
- return null;
20
- return _jsx(_Fragment, { children: children });
21
- }
22
- export function DialogContent({ children, className, fullscreen = false, showCloseButton = true, onClose, }) {
23
- return (_jsxs("div", { className: "fixed inset-0 z-50 flex items-center justify-center p-4", children: [_jsx("div", { className: "absolute inset-0 bg-black/40 backdrop-blur-sm", onClick: onClose, "aria-hidden": true }), _jsxs("div", { className: cn("relative z-10 flex max-h-[90vh] w-full max-w-lg flex-col overflow-hidden rounded-2xl border border-border bg-background shadow-xl", fullscreen && "h-full max-h-none max-w-none rounded-none", className), children: [showCloseButton && onClose && (_jsx(Button, { variant: "ghost", size: "icon", className: "absolute right-2 top-2", onClick: onClose, "aria-label": "Close", children: _jsx(X, { className: "h-4 w-4" }) })), children] })] }));
24
- }
25
- export function DialogHeader({ children, className }) {
26
- return _jsx("div", { className: cn("flex flex-col gap-2 p-6", className), children: children });
27
- }
28
- export function DialogTitle({ children, className }) {
29
- return _jsx("h2", { className: cn("text-lg font-semibold", className), children: children });
30
- }
31
- export function DialogDescription({ children, className }) {
32
- return _jsx("p", { className: cn("text-sm text-muted-foreground", className), children: children });
33
- }
34
- export function DialogFooter({ children, className }) {
35
- return (_jsx("div", { className: cn("flex flex-col-reverse gap-2 border-t border-border p-4 sm:flex-row sm:justify-end", className), children: children }));
36
- }
37
- export function DialogPanel({ children, className }) {
38
- return _jsx("div", { className: cn("min-h-0 flex-1 overflow-y-auto p-6", className), children: children });
39
- }
@@ -1,8 +0,0 @@
1
- import * as DropdownMenuPrimitive from "@radix-ui/react-dropdown-menu";
2
- import type { ComponentProps } from "react";
3
- export declare function DropdownMenu({ ...props }: ComponentProps<typeof DropdownMenuPrimitive.Root>): import("react").JSX.Element;
4
- export declare function DropdownMenuTrigger({ ...props }: ComponentProps<typeof DropdownMenuPrimitive.Trigger>): import("react").JSX.Element;
5
- export declare function DropdownMenuContent({ className, sideOffset, ...props }: ComponentProps<typeof DropdownMenuPrimitive.Content>): import("react").JSX.Element;
6
- export declare function DropdownMenuLabel({ className, ...props }: ComponentProps<typeof DropdownMenuPrimitive.Label>): import("react").JSX.Element;
7
- export declare function DropdownMenuRadioGroup({ ...props }: ComponentProps<typeof DropdownMenuPrimitive.RadioGroup>): import("react").JSX.Element;
8
- export declare function DropdownMenuRadioItem({ className, children, ...props }: ComponentProps<typeof DropdownMenuPrimitive.RadioItem>): import("react").JSX.Element;
@@ -1,23 +0,0 @@
1
- "use client";
2
- import { jsx as _jsx, jsxs as _jsxs } from "react/jsx-runtime";
3
- import * as DropdownMenuPrimitive from "@radix-ui/react-dropdown-menu";
4
- import { Check } from "lucide-react";
5
- import { cn } from "../lib/cn";
6
- export function DropdownMenu({ ...props }) {
7
- return _jsx(DropdownMenuPrimitive.Root, { "data-slot": "dropdown-menu", ...props });
8
- }
9
- export function DropdownMenuTrigger({ ...props }) {
10
- return _jsx(DropdownMenuPrimitive.Trigger, { "data-slot": "dropdown-menu-trigger", ...props });
11
- }
12
- export function DropdownMenuContent({ className, sideOffset = 4, ...props }) {
13
- return (_jsx(DropdownMenuPrimitive.Portal, { children: _jsx(DropdownMenuPrimitive.Content, { "data-slot": "dropdown-menu-content", sideOffset: sideOffset, className: cn("z-50 max-h-(--radix-dropdown-menu-content-available-height) min-w-44 origin-(--radix-dropdown-menu-content-transform-origin) overflow-x-hidden overflow-y-auto rounded-lg border bg-popover/95 p-1 text-popover-foreground shadow-md ring-1 ring-foreground/10 backdrop-blur-xl", "data-[side=bottom]:slide-in-from-top-2 data-[side=left]:slide-in-from-right-2 data-[side=right]:slide-in-from-left-2 data-[side=top]:slide-in-from-bottom-2 data-[state=closed]:animate-out data-[state=closed]:fade-out-0 data-[state=closed]:zoom-out-95 data-[state=open]:animate-in data-[state=open]:fade-in-0 data-[state=open]:zoom-in-95", className), ...props }) }));
14
- }
15
- export function DropdownMenuLabel({ className, ...props }) {
16
- return (_jsx(DropdownMenuPrimitive.Label, { "data-slot": "dropdown-menu-label", className: cn("px-2 py-1.5 text-xs text-muted-foreground", className), ...props }));
17
- }
18
- export function DropdownMenuRadioGroup({ ...props }) {
19
- return (_jsx(DropdownMenuPrimitive.RadioGroup, { "data-slot": "dropdown-menu-radio-group", ...props }));
20
- }
21
- export function DropdownMenuRadioItem({ className, children, ...props }) {
22
- return (_jsxs(DropdownMenuPrimitive.RadioItem, { "data-slot": "dropdown-menu-radio-item", className: cn("relative flex min-h-7 cursor-default items-center gap-2 rounded-md py-1.5 pr-8 pl-2 text-xs outline-hidden select-none focus:bg-accent focus:text-accent-foreground data-disabled:pointer-events-none data-disabled:opacity-50 [&_svg]:pointer-events-none [&_svg]:shrink-0 [&_svg:not([class*='size-'])]:size-3.5", className), ...props, children: [_jsx("span", { "data-slot": "dropdown-menu-radio-item-indicator", className: "pointer-events-none absolute right-2 flex items-center justify-center", children: _jsx(DropdownMenuPrimitive.ItemIndicator, { children: _jsx(Check, { className: "size-3.5" }) }) }), children] }));
23
- }
@@ -1,2 +0,0 @@
1
- import type { InputHTMLAttributes } from "react";
2
- export declare function Input({ className, ...props }: InputHTMLAttributes<HTMLInputElement>): import("react").JSX.Element;
package/dist/ui/input.js DELETED
@@ -1,6 +0,0 @@
1
- "use client";
2
- import { jsx as _jsx } from "react/jsx-runtime";
3
- import { cn } from "../lib/cn";
4
- export function Input({ className, ...props }) {
5
- return (_jsx("input", { className: cn("flex h-9 w-full rounded-lg border border-border bg-background px-3 text-sm outline-none focus-visible:ring-2 focus-visible:ring-cyan-500/40", className), ...props }));
6
- }
@@ -1,2 +0,0 @@
1
- import { type TextareaHTMLAttributes } from "react";
2
- export declare const Textarea: import("react").ForwardRefExoticComponent<TextareaHTMLAttributes<HTMLTextAreaElement> & import("react").RefAttributes<HTMLTextAreaElement>>;
@@ -1,7 +0,0 @@
1
- "use client";
2
- import { jsx as _jsx } from "react/jsx-runtime";
3
- import { forwardRef } from "react";
4
- import { cn } from "../lib/cn";
5
- export const Textarea = forwardRef(function Textarea({ className, ...props }, ref) {
6
- return (_jsx("textarea", { ref: ref, className: cn("flex min-h-20 w-full rounded-lg border border-border bg-background px-3 py-2 text-sm outline-none focus-visible:ring-2 focus-visible:ring-cyan-500/40", className), ...props }));
7
- });
package/src/styles.css DELETED
@@ -1,197 +0,0 @@
1
- @import "tailwindcss";
2
-
3
- :root {
4
- --background: #ffffff;
5
- --foreground: #0f172a;
6
- --card: #ffffff;
7
- --card-foreground: #0f172a;
8
- --popover: #ffffff;
9
- --popover-foreground: #0f172a;
10
- --primary: #0891b2;
11
- --primary-foreground: #ffffff;
12
- --secondary: #f1f5f9;
13
- --secondary-foreground: #0f172a;
14
- --muted: #f1f5f9;
15
- --muted-foreground: #64748b;
16
- --accent: #f1f5f9;
17
- --accent-foreground: #0f172a;
18
- --destructive: #dc2626;
19
- --destructive-foreground: #ffffff;
20
- --border: #e2e8f0;
21
- --input: #e2e8f0;
22
- --ring: #0891b2;
23
- }
24
-
25
- @media (prefers-color-scheme: dark) {
26
- :root {
27
- --background: #0b1220;
28
- --foreground: #f8fafc;
29
- --card: #0f172a;
30
- --card-foreground: #f8fafc;
31
- --popover: #0f172a;
32
- --popover-foreground: #f8fafc;
33
- --primary: #22d3ee;
34
- --primary-foreground: #082f49;
35
- --secondary: #1e293b;
36
- --secondary-foreground: #f8fafc;
37
- --muted: #1e293b;
38
- --muted-foreground: #94a3b8;
39
- --accent: #1e293b;
40
- --accent-foreground: #f8fafc;
41
- --destructive: #ef4444;
42
- --destructive-foreground: #ffffff;
43
- --border: #334155;
44
- --input: #334155;
45
- --ring: #22d3ee;
46
- }
47
- }
48
-
49
- body {
50
- background: var(--background);
51
- color: var(--foreground);
52
- }
53
-
54
- .bg-background {
55
- background-color: var(--background);
56
- }
57
-
58
- .bg-card {
59
- background-color: var(--card);
60
- }
61
-
62
- .bg-popover\/95 {
63
- background-color: color-mix(in srgb, var(--popover) 95%, transparent);
64
- }
65
-
66
- .bg-primary {
67
- background-color: var(--primary);
68
- }
69
-
70
- .bg-secondary {
71
- background-color: var(--secondary);
72
- }
73
-
74
- .bg-muted {
75
- background-color: var(--muted);
76
- }
77
-
78
- .bg-muted\/20 {
79
- background-color: color-mix(in srgb, var(--muted) 20%, transparent);
80
- }
81
-
82
- .bg-muted\/40 {
83
- background-color: color-mix(in srgb, var(--muted) 40%, transparent);
84
- }
85
-
86
- .bg-muted\/60 {
87
- background-color: color-mix(in srgb, var(--muted) 60%, transparent);
88
- }
89
-
90
- .bg-muted\/90 {
91
- background-color: color-mix(in srgb, var(--muted) 90%, transparent);
92
- }
93
-
94
- .text-foreground {
95
- color: var(--foreground);
96
- }
97
-
98
- .text-primary {
99
- color: var(--primary);
100
- }
101
-
102
- .text-primary-foreground {
103
- color: var(--primary-foreground);
104
- }
105
-
106
- .text-muted-foreground {
107
- color: var(--muted-foreground);
108
- }
109
-
110
- .text-popover-foreground {
111
- color: var(--popover-foreground);
112
- }
113
-
114
- .text-accent-foreground {
115
- color: var(--accent-foreground);
116
- }
117
-
118
- .text-secondary-foreground {
119
- color: var(--secondary-foreground);
120
- }
121
-
122
- .border-border {
123
- border-color: var(--border);
124
- }
125
-
126
- .border-primary\/30 {
127
- border-color: color-mix(in srgb, var(--primary) 30%, transparent);
128
- }
129
-
130
- .ring-foreground\/10 {
131
- --tw-ring-color: color-mix(in srgb, var(--foreground) 10%, transparent);
132
- }
133
-
134
- .ring-ring\/50 {
135
- --tw-ring-color: color-mix(in srgb, var(--ring) 50%, transparent);
136
- }
137
-
138
- .bg-primary\/10 {
139
- background-color: color-mix(in srgb, var(--primary) 10%, transparent);
140
- }
141
-
142
- .hover\:bg-primary\/15:hover {
143
- background-color: color-mix(in srgb, var(--primary) 15%, transparent);
144
- }
145
-
146
- .hover\:bg-primary\/90:hover {
147
- background-color: color-mix(in srgb, var(--primary) 90%, transparent);
148
- }
149
-
150
- .hover\:bg-accent:hover {
151
- background-color: var(--accent);
152
- }
153
-
154
- .hover\:text-accent-foreground:hover {
155
- color: var(--accent-foreground);
156
- }
157
-
158
- .focus\:bg-accent:focus {
159
- background-color: var(--accent);
160
- }
161
-
162
- .focus\:text-accent-foreground:focus {
163
- color: var(--accent-foreground);
164
- }
165
-
166
- .focus-visible\:border-ring:focus-visible {
167
- border-color: var(--ring);
168
- }
169
-
170
- .focus-visible\:ring-ring\/50:focus-visible {
171
- --tw-ring-color: color-mix(in srgb, var(--ring) 50%, transparent);
172
- }
173
-
174
- .data-\[state\=open\]\:bg-accent[data-state="open"] {
175
- background-color: var(--accent);
176
- }
177
-
178
- .data-\[state\=open\]\:text-accent-foreground[data-state="open"] {
179
- color: var(--accent-foreground);
180
- }
181
-
182
- .hover\:bg-destructive:hover {
183
- background-color: var(--destructive);
184
- }
185
-
186
- .hover\:text-destructive-foreground:hover {
187
- color: var(--destructive-foreground);
188
- }
189
-
190
- .scrollbar-hidden {
191
- scrollbar-width: none;
192
- -ms-overflow-style: none;
193
- }
194
-
195
- .scrollbar-hidden::-webkit-scrollbar {
196
- display: none;
197
- }