Skip to content

Commit

Permalink
Polishing Input, Area, Chip, Dropdown (#8581)
Browse files Browse the repository at this point in the history
* Fixing Dropdown with description style

* Polishing Sparkle styles

* [sparkle] - refactor: streamline handling of animated text variants

 - Abstract animated text background and text color variants into separate records for cleaner code structure
 - Use cva utility from `class-variance-authority` to manage TextArea component styles, introducing a more flexible and scalable approach to variant handling

[sparkle] - fix: mark `isBusy` prop in `Chip` component as potentially undefined

 - Adjust typings for `isBusy` prop to correctly reflect its optional nature in the `Chip` component

[sparkle] - refactor: introduce cva to refactor `TextArea` styles and variants

 - Consolidate `TextArea` styling and variant handling into a single cva call to improve readability and maintainability
 - Simplify the props destructuring in the `TextArea` component by relying on cva to handle default variants and classes

* polishing

* Hoverable

* Page

* [sparkle] - refactor: implement `cva` for className variations in `Hoverable`

 - Introduced `cva` for more scalable handling of className variations based on component variants
 - Replaced manual className construction with `cva` utility in `Hoverable` component for maintainability and readability improvements

---------

Co-authored-by: JulesBelveze <[email protected]>
  • Loading branch information
Duncid and JulesBelveze authored Nov 13, 2024
1 parent ca4c366 commit 7779c7d
Show file tree
Hide file tree
Showing 17 changed files with 217 additions and 192 deletions.
27 changes: 15 additions & 12 deletions front/components/assistant/HelpDrawer.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,6 @@ import {
Button,
ChatBubbleBottomCenterTextIcon,
FolderIcon,
Item,
LightbulbIcon,
Modal,
Page,
Expand Down Expand Up @@ -72,19 +71,23 @@ function LinksList({
title?: string;
}) {
return (
<Item.List>
{title && <Item.SectionHeader label={title} variant="secondary" />}
<div className="flex flex-col gap-2">
{title && (
<div className="text-xs font-medium text-muted-foreground">{title}</div>
)}
{linksList.map((link, index) => (
<Item.Link
icon={link.icon}
label={link.title}
link={link.href ? { href: link.href, target: "_blank" } : undefined}
onClick={link.onClick}
key={index}
description={link.description}
/>
<div key={index}>
<Button
icon={link.icon}
variant="ghost"
label={link.title}
link={link.href ? { href: link.href, target: "_blank" } : undefined}
onClick={link.onClick}
description={link.description}
/>
</div>
))}
</Item.List>
</div>
);
}

Expand Down
4 changes: 2 additions & 2 deletions sparkle/package-lock.json

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

2 changes: 1 addition & 1 deletion sparkle/package.json
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
{
"name": "@dust-tt/sparkle",
"version": "0.2.304",
"version": "0.2.305",
"scripts": {
"build": "rm -rf dist && npm run tailwind && npm run build:esm && npm run build:cjs",
"tailwind": "tailwindcss -i ./src/styles/tailwind.css -o dist/sparkle.css",
Expand Down
53 changes: 43 additions & 10 deletions sparkle/src/components/AnimatedText.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -4,29 +4,62 @@ import React from "react";

import { cn } from "@sparkle/lib/utils";

const ANIMATED_TEXT_VARIANTS = [
"muted",
"highlight",
"emerald",
"amber",
"slate",
"purple",
"warning",
"sky",
"pink",
"red",
] as const;

type AnimatedTextVariantType = (typeof ANIMATED_TEXT_VARIANTS)[number];

const animatedVariants: Record<AnimatedTextVariantType, string> = {
muted: "s-from-transparent s-via-primary-950/80 s-via-50% s-to-transparent",
highlight: "s-from-highlight s-via-highlight-800 s-via-50% s-to-highlight",
emerald: "s-from-emerald-800 s-via-emerald-950 s-via-50% s-to-emerald-800",
amber: "s-from-amber-800 s-via-amber-950 s-via-50% s-to-amber-800",
slate: "s-from-slate-600 s-via-slate-950 s-via-50% s-to-slate-600",
purple: "s-from-purple-800 s-via-purple-950 s-via-50% s-to-purple-800",
warning: "s-from-warning-800 s-via-warning-950 s-via-50% s-to-warning-800",
sky: "s-from-sky-800 s-via-sky-950 s-via-50% s-to-sky-800",
pink: "s-from-pink-800 s-via-pink-950 s-via-50% s-to-pink-800",
red: "s-from-red-800 s-via-red-950 s-via-50% s-to-red-800",
};

const animVariants = cva(
"s-relative s-mx-auto s-max-w-md s-text-black/0 s-animate-shiny-text s-bg-clip-text s-bg-no-repeat [background-position:0_0] [background-size:50%_100%] s-bg-gradient-to-r",
{
variants: {
variant: {
muted:
"s-from-transparent s-via-primary-950/80 s-via-50% s-to-transparent",
highlight:
"s-from-highlight s-via-highlight-800 s-via-50% s-to-highlight",
},
variant: animatedVariants,
},
defaultVariants: {
variant: "muted",
},
}
);

const animatedTextVariants: Record<AnimatedTextVariantType, string> = {
muted: "s-text-muted-foreground",
highlight: "s-text-highlight",
emerald: "s-text-emerald-800",
amber: "s-text-amber-800",
slate: "s-text-slate-600",
purple: "s-text-purple-800-800",
warning: "s-text-warning-800",
sky: "s-text-sky-800",
pink: "s-text-pink-800",
red: "s-text-red-800",
};

const textVariants = cva("s-absolute s-inset-0", {
variants: {
variant: {
muted: "s-text-muted-foreground",
highlight: "s-text-highlight",
},
variant: animatedTextVariants,
},
defaultVariants: {
variant: "muted",
Expand Down
11 changes: 8 additions & 3 deletions sparkle/src/components/Chip.tsx
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
import { cva } from "class-variance-authority";
import React, { ComponentType, ReactNode } from "react";

import { AnimatedText } from "@sparkle/components/";
import { cn } from "@sparkle/lib/utils";

import { Icon, IconProps } from "./Icon";
Expand Down Expand Up @@ -83,21 +84,25 @@ export function Chip({
label,
children,
className,
isBusy = false,
isBusy,
icon,
}: ChipProps) {
return (
<div
className={cn(
chipVariants({ size, background: color, text: color, isBusy }),
chipVariants({ size, background: color, text: color }),
className
)}
aria-label={label}
>
{icon && <Icon visual={icon} size={size as IconProps["size"]} />}
{label && (
<span className={cn("s-pointer s-grow s-cursor-default s-truncate")}>
{label}
{isBusy ? (
<AnimatedText variant={color}>{label}</AnimatedText>
) : (
label
)}
</span>
)}
{children}
Expand Down
4 changes: 2 additions & 2 deletions sparkle/src/components/Dropdown.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -40,7 +40,7 @@ export const menuStyleClasses = {
},
label: "s-font-semibold s-px-2 s-py-2 s-text-xs s-text-muted-foreground",
description:
"s-grow s-truncate s-text-sm s-font-regular s-text-element-700 dark:s-text-element-600-dark",
"s-grow s-truncate s-text-xs s-text-muted-foreground s-font-normal",
separator: "-s-mx-1 s-my-1 s-h-px s-bg-separator",
shortcut: "s-ml-auto s-text-xs s-tracking-widest s-text-primary-400",
};
Expand Down Expand Up @@ -85,7 +85,7 @@ const ItemWithLabelIconAndDescription = <
return (
<>
{label && (
<div className="s-grid s-grid-cols-[auto,1fr] s-gap-x-1.5">
<div className="s-grid s-grid-cols-[auto,1fr] s-items-center s-gap-x-1.5">
{icon && (
<div
className={cn(
Expand Down
37 changes: 24 additions & 13 deletions sparkle/src/components/Hoverable.tsx
Original file line number Diff line number Diff line change
@@ -1,31 +1,42 @@
import { cva, type VariantProps } from "class-variance-authority";
import React, { SyntheticEvent } from "react";
import { ReactNode } from "react";

import { classNames } from "@sparkle/lib/utils";
import { cn } from "@sparkle/lib/utils";

interface HoverableProps {
const hoverableVariants = cva(
"s-cursor-pointer s-duration-200 hover:s-underline hover:s-underline-offset-2",
{
variants: {
variant: {
invisible: "hover:s-text-highlight-light active:s-text-highlight-dark",
primary:
"s-font-medium s-text-foreground hover:s-text-highlight-light active:s-text-highlight-dark",
highlight:
"s-font-medium s-text-highlight hover:s-text-highlight-light active:s-text-highlight-dark",
},
},
defaultVariants: {
variant: "invisible",
},
}
);

interface HoverableProps extends VariantProps<typeof hoverableVariants> {
children: ReactNode;
className?: string;
onClick: (e: SyntheticEvent) => void;
variant?: "primary" | "invisible";
}

export function Hoverable({
children,
className = "",
className,
onClick,
variant = "invisible",
variant,
}: HoverableProps) {
const baseClasses = "s-cursor-pointer s-duration-300";

const variantClasses = {
invisible: "hover:s-text-action-500 active:s-text-action-600",
primary: "s-font-bold s-text-blue-500 hover:active:s-text-action-600",
};

return (
<span
className={classNames(baseClasses, variantClasses[variant], className)}
className={cn(hoverableVariants({ variant }), className)}
onClick={onClick}
>
{children}
Expand Down
9 changes: 4 additions & 5 deletions sparkle/src/components/Input.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -32,10 +32,9 @@ const messageVariantStyles: Record<MessageStatus, string> = {
};

const stateVariantStyles: Record<InputStateType, string> = {
default: "focus-visible:s-ring-ring",
disabled:
"disabled:s-cursor-not-allowed disabled:s-opacity-50 disabled:s-text-muted-foreground",
error: "s-border-border-warning focus:s-ring-ring-warning",
default: "",
disabled: "disabled:s-cursor-not-allowed disabled:s-text-muted-foreground",
error: "focus:s-ring-ring-warning",
};

const messageVariant = cva("", {
Expand All @@ -49,7 +48,7 @@ const messageVariant = cva("", {

const inputStyleClasses = cva(
cn(
"s-text-sm s-bg-background s-rounded-xl s-border s-border-border-dark s-flex s-h-9 s-w-full s-px-3 s-py-1.5 ",
"s-text-sm s-bg-background s-rounded-xl s-border s-border-border-dark/0 s-bg-muted-background s-flex s-h-9 s-w-full s-px-3 s-py-1.5 ",
"file:s-border-0 file:s-bg-transparent file:s-text-sm file:s-font-medium file:s-text-foreground",
"placeholder:s-text-muted-foreground",
"focus-visible:s-outline-none focus-visible:s-ring-2 focus-visible:s-ring-offset-2 focus-visible:s-border-border-dark"
Expand Down
36 changes: 0 additions & 36 deletions sparkle/src/components/Item.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -221,42 +221,6 @@ Item.Avatar = function ({
);
};

type NavigationListItemProps = Pick<
ItemProps,
| "action"
| "className"
| "description"
| "disabled"
| "hasAction"
| "icon"
| "label"
| "link"
| "onClick"
| "selected"
>;

Item.Navigation = function (props: NavigationListItemProps) {
return <Item {...props} style="action" spacing="md" />;
};

type LinkItemProps = Pick<
ItemProps,
"onClick" | "label" | "description" | "visual" | "icon" | "className" | "link"
>;

Item.Link = function ({ ...props }: LinkItemProps) {
return (
<Item
{...props}
// Pass down additional props as needed
style="link"
hasAction={false}
spacing="lg"
// Add any conditions or logic for additional props
/>
);
};

interface DropdownListItemBaseProps {
style?: "default" | "warning";
}
Expand Down
2 changes: 1 addition & 1 deletion sparkle/src/components/Page.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -40,7 +40,7 @@ interface PageHeaderProps {
Page.Header = function ({ title, description, icon }: PageHeaderProps) {
return (
<Page.Vertical gap="xs">
<Icon visual={icon} className="s-text-muted-foreground" size="lg" />
<Icon visual={icon} className="s-text-primary-400" size="lg" />
<Page.H variant="h3">{title}</Page.H>
{description && <Page.P variant="secondary">{description}</Page.P>}
</Page.Vertical>
Expand Down
Loading

0 comments on commit 7779c7d

Please sign in to comment.