Compare commits
4 Commits
0.7.8
...
502adca81b
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
502adca81b | ||
|
|
12e8bf6e69 | ||
|
|
472574ac31 | ||
|
|
f4a7b53393 |
@@ -75,7 +75,7 @@ describe("CombatantRow", () => {
|
|||||||
it("active combatant gets active border styling", () => {
|
it("active combatant gets active border styling", () => {
|
||||||
const { container } = renderRow({ isActive: true });
|
const { container } = renderRow({ isActive: true });
|
||||||
const row = container.firstElementChild;
|
const row = container.firstElementChild;
|
||||||
expect(row?.className).toContain("border-l-accent");
|
expect(row?.className).toContain("border-accent/40");
|
||||||
});
|
});
|
||||||
|
|
||||||
it("unconscious combatant (currentHp === 0) gets dimmed styling", () => {
|
it("unconscious combatant (currentHp === 0) gets dimmed styling", () => {
|
||||||
|
|||||||
@@ -77,7 +77,7 @@ function AddModeSuggestions({
|
|||||||
onAddFromPlayerCharacter?: (pc: PlayerCharacter) => void;
|
onAddFromPlayerCharacter?: (pc: PlayerCharacter) => void;
|
||||||
}>) {
|
}>) {
|
||||||
return (
|
return (
|
||||||
<div className="absolute bottom-full z-50 mb-1 w-full max-w-xs rounded-md border border-border bg-card shadow-lg">
|
<div className="card-glow absolute bottom-full z-50 mb-1 w-full max-w-xs rounded-lg border border-border bg-card">
|
||||||
<button
|
<button
|
||||||
type="button"
|
type="button"
|
||||||
className="flex w-full items-center gap-1.5 border-border border-b px-3 py-2 text-left text-accent text-sm hover:bg-accent/20"
|
className="flex w-full items-center gap-1.5 border-border border-b px-3 py-2 text-left text-accent text-sm hover:bg-accent/20"
|
||||||
@@ -457,7 +457,7 @@ export function ActionBar({
|
|||||||
});
|
});
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<div className="flex items-center gap-3 rounded-md border border-border bg-card px-4 py-3">
|
<div className="card-glow flex items-center gap-3 rounded-lg border border-border bg-card px-4 py-3">
|
||||||
<form
|
<form
|
||||||
onSubmit={handleAdd}
|
onSubmit={handleAdd}
|
||||||
className="relative flex flex-1 items-center gap-2"
|
className="relative flex flex-1 items-center gap-2"
|
||||||
@@ -498,7 +498,7 @@ export function ActionBar({
|
|||||||
</button>
|
</button>
|
||||||
)}
|
)}
|
||||||
{browseMode && deferredSuggestions.length > 0 && (
|
{browseMode && deferredSuggestions.length > 0 && (
|
||||||
<div className="absolute bottom-full z-50 mb-1 w-full rounded-md border border-border bg-card shadow-lg">
|
<div className="card-glow absolute bottom-full z-50 mb-1 w-full rounded-lg border border-border bg-card">
|
||||||
<ul className="max-h-48 overflow-y-auto py-1">
|
<ul className="max-h-48 overflow-y-auto py-1">
|
||||||
{deferredSuggestions.map((result, i) => (
|
{deferredSuggestions.map((result, i) => (
|
||||||
<li key={creatureKey(result)}>
|
<li key={creatureKey(result)}>
|
||||||
|
|||||||
@@ -79,7 +79,7 @@ function EditableName({
|
|||||||
ref={inputRef}
|
ref={inputRef}
|
||||||
type="text"
|
type="text"
|
||||||
value={draft}
|
value={draft}
|
||||||
className="h-7 text-sm"
|
className="h-7 max-w-48 text-sm"
|
||||||
onChange={(e) => setDraft(e.target.value)}
|
onChange={(e) => setDraft(e.target.value)}
|
||||||
onBlur={commit}
|
onBlur={commit}
|
||||||
onKeyDown={(e) => {
|
onKeyDown={(e) => {
|
||||||
@@ -365,9 +365,13 @@ function rowBorderClass(
|
|||||||
isActive: boolean,
|
isActive: boolean,
|
||||||
isConcentrating: boolean | undefined,
|
isConcentrating: boolean | undefined,
|
||||||
): string {
|
): string {
|
||||||
if (isActive) return "border-l-2 border-l-accent bg-accent/10";
|
if (isActive && isConcentrating)
|
||||||
if (isConcentrating) return "border-l-2 border-l-purple-400";
|
return "border border-l-2 border-accent/40 border-l-purple-400 bg-accent/10 card-glow";
|
||||||
return "border-l-2 border-l-transparent";
|
if (isActive)
|
||||||
|
return "border border-l-2 border-accent/40 bg-accent/10 card-glow";
|
||||||
|
if (isConcentrating)
|
||||||
|
return "border border-l-2 border-transparent border-l-purple-400";
|
||||||
|
return "border border-l-2 border-transparent";
|
||||||
}
|
}
|
||||||
|
|
||||||
function concentrationIconClass(
|
function concentrationIconClass(
|
||||||
@@ -434,7 +438,7 @@ export function CombatantRow({
|
|||||||
<div
|
<div
|
||||||
ref={ref}
|
ref={ref}
|
||||||
className={cn(
|
className={cn(
|
||||||
"group rounded-md pr-3 transition-colors",
|
"group rounded-lg pr-3 transition-colors",
|
||||||
rowBorderClass(isActive, combatant.isConcentrating),
|
rowBorderClass(isActive, combatant.isConcentrating),
|
||||||
isPulsing && "animate-concentration-pulse",
|
isPulsing && "animate-concentration-pulse",
|
||||||
)}
|
)}
|
||||||
|
|||||||
@@ -97,7 +97,7 @@ export function ConditionPicker({
|
|||||||
<div
|
<div
|
||||||
ref={ref}
|
ref={ref}
|
||||||
className={cn(
|
className={cn(
|
||||||
"absolute left-0 z-10 w-fit overflow-y-auto rounded-md border border-border bg-background p-1 shadow-lg",
|
"card-glow absolute left-0 z-10 w-fit overflow-y-auto rounded-lg border border-border bg-background p-1",
|
||||||
flipped ? "bottom-full mb-1" : "top-full mt-1",
|
flipped ? "bottom-full mb-1" : "top-full mt-1",
|
||||||
)}
|
)}
|
||||||
style={maxHeight ? { maxHeight } : undefined}
|
style={maxHeight ? { maxHeight } : undefined}
|
||||||
|
|||||||
@@ -106,7 +106,7 @@ export function CreatePlayerModal({
|
|||||||
return (
|
return (
|
||||||
<dialog
|
<dialog
|
||||||
ref={dialogRef}
|
ref={dialogRef}
|
||||||
className="m-auto w-full max-w-md rounded-lg border border-border bg-card p-6 shadow-xl backdrop:bg-black/50"
|
className="card-glow m-auto w-full max-w-md rounded-lg border border-border bg-card p-6 backdrop:bg-black/50"
|
||||||
>
|
>
|
||||||
<div className="mb-4 flex items-center justify-between">
|
<div className="mb-4 flex items-center justify-between">
|
||||||
<h2 className="font-semibold text-foreground text-lg">
|
<h2 className="font-semibold text-foreground text-lg">
|
||||||
|
|||||||
@@ -87,7 +87,7 @@ export function HpAdjustPopover({ onAdjust, onClose }: HpAdjustPopoverProps) {
|
|||||||
return (
|
return (
|
||||||
<div
|
<div
|
||||||
ref={ref}
|
ref={ref}
|
||||||
className="fixed z-10 rounded-md border border-border bg-background p-2 shadow-lg"
|
className="card-glow fixed z-10 rounded-lg border border-border bg-background p-2"
|
||||||
style={
|
style={
|
||||||
pos
|
pos
|
||||||
? { top: pos.top, left: pos.left }
|
? { top: pos.top, left: pos.left }
|
||||||
|
|||||||
@@ -55,7 +55,7 @@ export function PlayerManagement({
|
|||||||
return (
|
return (
|
||||||
<dialog
|
<dialog
|
||||||
ref={dialogRef}
|
ref={dialogRef}
|
||||||
className="m-auto w-full max-w-md rounded-lg border border-border bg-card p-6 shadow-xl backdrop:bg-black/50"
|
className="card-glow m-auto w-full max-w-md rounded-lg border border-border bg-card p-6 backdrop:bg-black/50"
|
||||||
>
|
>
|
||||||
<div className="mb-4 flex items-center justify-between">
|
<div className="mb-4 flex items-center justify-between">
|
||||||
<h2 className="font-semibold text-foreground text-lg">
|
<h2 className="font-semibold text-foreground text-lg">
|
||||||
|
|||||||
@@ -155,7 +155,7 @@ function DesktopPanel({
|
|||||||
return (
|
return (
|
||||||
<div
|
<div
|
||||||
className={cn(
|
className={cn(
|
||||||
"fixed top-0 bottom-0 flex w-[400px] flex-col border-border bg-card transition-slide-panel",
|
"panel-glow fixed top-0 bottom-0 flex w-[400px] flex-col border-border bg-card transition-slide-panel",
|
||||||
sideClasses,
|
sideClasses,
|
||||||
isCollapsed ? collapsedTranslate : "translate-x-0",
|
isCollapsed ? collapsedTranslate : "translate-x-0",
|
||||||
)}
|
)}
|
||||||
@@ -201,7 +201,7 @@ function MobileDrawer({
|
|||||||
/>
|
/>
|
||||||
<div
|
<div
|
||||||
className={cn(
|
className={cn(
|
||||||
"absolute top-0 right-0 bottom-0 w-[85%] max-w-md border-border border-l bg-card shadow-xl",
|
"panel-glow absolute top-0 right-0 bottom-0 w-[85%] max-w-md border-border border-l bg-card",
|
||||||
!isSwiping && "animate-slide-in-right",
|
!isSwiping && "animate-slide-in-right",
|
||||||
)}
|
)}
|
||||||
style={
|
style={
|
||||||
|
|||||||
@@ -24,7 +24,7 @@ export function Toast({
|
|||||||
|
|
||||||
return createPortal(
|
return createPortal(
|
||||||
<div className="fixed bottom-4 left-4 z-50">
|
<div className="fixed bottom-4 left-4 z-50">
|
||||||
<div className="flex items-center gap-3 rounded-lg border border-border bg-card px-4 py-3 shadow-lg">
|
<div className="card-glow flex items-center gap-3 rounded-lg border border-border bg-card px-4 py-3">
|
||||||
<span className="text-foreground text-sm">{message}</span>
|
<span className="text-foreground text-sm">{message}</span>
|
||||||
{progress !== undefined && (
|
{progress !== undefined && (
|
||||||
<div className="h-2 w-24 overflow-hidden rounded-full bg-muted">
|
<div className="h-2 w-24 overflow-hidden rounded-full bg-muted">
|
||||||
|
|||||||
@@ -21,7 +21,7 @@ export function TurnNavigation({
|
|||||||
const activeCombatant = encounter.combatants[encounter.activeIndex];
|
const activeCombatant = encounter.combatants[encounter.activeIndex];
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<div className="flex items-center gap-3 rounded-md border border-border bg-card px-4 py-3">
|
<div className="card-glow flex items-center gap-3 rounded-lg border border-border bg-card px-4 py-3">
|
||||||
<Button
|
<Button
|
||||||
variant="outline"
|
variant="outline"
|
||||||
size="icon"
|
size="icon"
|
||||||
|
|||||||
@@ -9,7 +9,7 @@ const buttonVariants = cva(
|
|||||||
variant: {
|
variant: {
|
||||||
default: "bg-primary text-primary-foreground hover:bg-primary/90",
|
default: "bg-primary text-primary-foreground hover:bg-primary/90",
|
||||||
outline:
|
outline:
|
||||||
"border border-border bg-transparent text-foreground hover:bg-hover-neutral-bg hover:text-hover-neutral",
|
"border border-border bg-background/50 text-foreground hover:bg-hover-neutral-bg hover:text-hover-neutral",
|
||||||
ghost:
|
ghost:
|
||||||
"text-foreground hover:bg-hover-neutral-bg hover:text-hover-neutral",
|
"text-foreground hover:bg-hover-neutral-bg hover:text-hover-neutral",
|
||||||
},
|
},
|
||||||
|
|||||||
@@ -49,7 +49,7 @@ export function OverflowMenu({ items }: OverflowMenuProps) {
|
|||||||
<EllipsisVertical className="h-5 w-5" />
|
<EllipsisVertical className="h-5 w-5" />
|
||||||
</Button>
|
</Button>
|
||||||
{!!open && (
|
{!!open && (
|
||||||
<div className="absolute right-0 bottom-full z-50 mb-1 min-w-48 rounded-md border border-border bg-card py-1 shadow-lg">
|
<div className="card-glow absolute right-0 bottom-full z-50 mb-1 min-w-48 rounded-lg border border-border bg-card py-1">
|
||||||
{items.map((item) => (
|
{items.map((item) => (
|
||||||
<button
|
<button
|
||||||
key={item.label}
|
key={item.label}
|
||||||
|
|||||||
@@ -1,14 +1,14 @@
|
|||||||
@import "tailwindcss";
|
@import "tailwindcss";
|
||||||
|
|
||||||
@theme {
|
@theme {
|
||||||
--color-background: #0f172a;
|
--color-background: #0e1a2e;
|
||||||
--color-foreground: #e2e8f0;
|
--color-foreground: #e2e8f0;
|
||||||
--color-muted: #64748b;
|
--color-muted: #7a8ba4;
|
||||||
--color-muted-foreground: #94a3b8;
|
--color-muted-foreground: #94a3b8;
|
||||||
--color-card: #1e293b;
|
--color-card: #1a2e4a;
|
||||||
--color-card-foreground: #e2e8f0;
|
--color-card-foreground: #e2e8f0;
|
||||||
--color-border: #334155;
|
--color-border: #2a5088;
|
||||||
--color-input: #334155;
|
--color-input: #2a5088;
|
||||||
--color-primary: #3b82f6;
|
--color-primary: #3b82f6;
|
||||||
--color-primary-foreground: #ffffff;
|
--color-primary-foreground: #ffffff;
|
||||||
--color-accent: #3b82f6;
|
--color-accent: #3b82f6;
|
||||||
@@ -20,8 +20,8 @@
|
|||||||
--color-hover-action-bg: var(--color-muted);
|
--color-hover-action-bg: var(--color-muted);
|
||||||
--color-hover-destructive-bg: transparent;
|
--color-hover-destructive-bg: transparent;
|
||||||
--radius-sm: 0.25rem;
|
--radius-sm: 0.25rem;
|
||||||
--radius-md: 0.375rem;
|
--radius-md: 0.5rem;
|
||||||
--radius-lg: 0.5rem;
|
--radius-lg: 0.75rem;
|
||||||
--font-sans: "Inter", ui-sans-serif, system-ui, sans-serif;
|
--font-sans: "Inter", ui-sans-serif, system-ui, sans-serif;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -169,6 +169,28 @@
|
|||||||
concentration-glow 1200ms ease-out;
|
concentration-glow 1200ms ease-out;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@utility card-glow {
|
||||||
|
background-image: radial-gradient(
|
||||||
|
ellipse at 50% 50%,
|
||||||
|
oklch(0.35 0.05 250 / 0.5) 0%,
|
||||||
|
transparent 70%
|
||||||
|
);
|
||||||
|
box-shadow:
|
||||||
|
0 0 15px -2px oklch(0.623 0.214 259 / 0.2),
|
||||||
|
inset 0 1px 0 0 oklch(0.7 0.15 259 / 0.1);
|
||||||
|
}
|
||||||
|
|
||||||
|
@utility panel-glow {
|
||||||
|
background-image: linear-gradient(
|
||||||
|
to bottom,
|
||||||
|
oklch(0.35 0.05 250 / 0.4) 0%,
|
||||||
|
transparent 40%
|
||||||
|
);
|
||||||
|
box-shadow:
|
||||||
|
0 0 20px -2px oklch(0.623 0.214 259 / 0.15),
|
||||||
|
inset 0 1px 0 0 oklch(0.7 0.15 259 / 0.1);
|
||||||
|
}
|
||||||
|
|
||||||
* {
|
* {
|
||||||
scrollbar-color: var(--color-border) transparent;
|
scrollbar-color: var(--color-border) transparent;
|
||||||
scrollbar-width: thin;
|
scrollbar-width: thin;
|
||||||
|
|||||||
Reference in New Issue
Block a user