refactor: Phase 3a — Global color class migration to SUMI semantics
- Replace all kodo-* color classes across ~100 TSX files: kodo-void → background, kodo-ink → card, kodo-graphite → muted, kodo-steel → muted-foreground, kodo-cyan → primary, kodo-magenta → destructive, kodo-lime → success, kodo-red → destructive, kodo-gold → warning - Replace cyan-500, magenta-500, lime-500 default Tailwind colors with semantic equivalents (primary, destructive, success) - Fix WaveformVisualizer hardcoded hex colors to SUMI values - Delete global-effects.css (conflicting, redundant with index.css) Co-authored-by: Cursor <cursoragent@cursor.com>
This commit is contained in:
parent
24b4cce8ea
commit
fa56dfa77e
127 changed files with 441 additions and 778 deletions
|
|
@ -134,7 +134,7 @@ export function AdvancedFilters({
|
|||
open={isOpen}
|
||||
onOpenChange={handleToggle}
|
||||
defaultOpen={defaultOpen}
|
||||
triggerClassName="p-2 rounded-lg border border-border bg-kodo-void/50 hover:bg-kodo-void transition-colors"
|
||||
triggerClassName="p-2 rounded-lg border border-border bg-background/50 hover:bg-background transition-colors"
|
||||
contentClassName={cn('pt-3', contentClassName)}
|
||||
>
|
||||
<div className="space-y-4">{children}</div>
|
||||
|
|
|
|||
|
|
@ -70,7 +70,7 @@ export function BulkModeBanner({
|
|||
aria-live="polite"
|
||||
aria-atomic="true"
|
||||
className={cn(
|
||||
'w-full bg-muted/10 border-b border-border/30 text-kodo-steel',
|
||||
'w-full bg-muted/10 border-b border-border/30 text-muted-foreground',
|
||||
'px-4 py-4 flex items-center justify-between gap-4',
|
||||
'transition-all duration-[var(--duration-normal)]',
|
||||
className,
|
||||
|
|
@ -86,7 +86,7 @@ export function BulkModeBanner({
|
|||
variant="ghost"
|
||||
size="sm"
|
||||
onClick={onClose}
|
||||
className="text-kodo-steel hover:text-white hover:bg-white/5 h-auto py-1 px-2 flex-shrink-0"
|
||||
className="text-muted-foreground hover:text-white hover:bg-white/5 h-auto py-1 px-2 flex-shrink-0"
|
||||
aria-label="Fermer le mode sélection"
|
||||
>
|
||||
<X className="w-4 h-4" />
|
||||
|
|
|
|||
|
|
@ -15,7 +15,7 @@ const OfflineIndicatorMock = ({ variant }: { variant: 'offline' | 'syncing' | 'h
|
|||
|
||||
if (variant === 'offline') {
|
||||
return (
|
||||
<div className="bg-kodo-red/90 backdrop-blur-sm text-white px-4 py-2.5 text-sm flex items-center justify-center gap-2 shadow-lg border-b border-kodo-red rounded">
|
||||
<div className="bg-destructive/90 backdrop-blur-sm text-white px-4 py-2.5 text-sm flex items-center justify-center gap-2 shadow-lg border-b border-destructive rounded">
|
||||
<WifiOff className="w-4 h-4" />
|
||||
<span>
|
||||
Mode hors ligne
|
||||
|
|
@ -30,16 +30,16 @@ const OfflineIndicatorMock = ({ variant }: { variant: 'offline' | 'syncing' | 'h
|
|||
}
|
||||
|
||||
return (
|
||||
<div className="bg-kodo-cyan/90 backdrop-blur-sm text-kodo-void px-4 py-2.5 text-sm flex items-center justify-center gap-2 shadow-lg border-b border-kodo-steel rounded">
|
||||
<div className="bg-primary/90 backdrop-blur-sm text-foreground px-4 py-2.5 text-sm flex items-center justify-center gap-2 shadow-lg border-b border-border rounded">
|
||||
<Loader2 className="w-4 h-4 animate-spin" />
|
||||
<span>
|
||||
Synchronisation en cours
|
||||
<span className="ml-2 font-semibold">- 2 requêtes restantes</span>
|
||||
</span>
|
||||
<button className="ml-2 px-2 py-1 bg-kodo-red/20 hover:bg-kodo-red/30 rounded border border-kodo-red/30 transition-colors flex items-center gap-1.5 text-xs font-medium">
|
||||
<button className="ml-2 px-2 py-1 bg-destructive/20 hover:bg-destructive/30 rounded border border-destructive/30 transition-colors flex items-center gap-1.5 text-xs font-medium">
|
||||
Clear Queue
|
||||
</button>
|
||||
<button className="ml-2 px-2 py-1 bg-kodo-void/20 hover:bg-kodo-void/30 rounded border border-kodo-void/30 transition-colors flex items-center gap-1.5 text-xs font-medium">
|
||||
<button className="ml-2 px-2 py-1 bg-background/20 hover:bg-background/30 rounded border border-border/30 transition-colors flex items-center gap-1.5 text-xs font-medium">
|
||||
<List className="w-3.5 h-3.5" />
|
||||
View Queue
|
||||
</button>
|
||||
|
|
|
|||
|
|
@ -100,7 +100,7 @@ export function OfflineIndicator() {
|
|||
if (!isOnline || hasNetworkError) {
|
||||
return (
|
||||
<>
|
||||
<div className="fixed top-0 left-0 right-0 bg-kodo-red/90 backdrop-blur-sm text-white px-4 py-2.5 text-sm z-50 flex items-center justify-center gap-2 shadow-lg border-b border-kodo-red">
|
||||
<div className="fixed top-0 left-0 right-0 bg-destructive/90 backdrop-blur-sm text-white px-4 py-2.5 text-sm z-50 flex items-center justify-center gap-2 shadow-lg border-b border-destructive">
|
||||
<WifiOff className="w-4 h-4" />
|
||||
<span>
|
||||
Mode hors ligne
|
||||
|
|
@ -141,7 +141,7 @@ export function OfflineIndicator() {
|
|||
if (isProcessing && queueSize > 0 && shouldShowSyncBar) {
|
||||
return (
|
||||
<>
|
||||
<div className="fixed top-0 left-0 right-0 bg-primary/90 backdrop-blur-sm text-kodo-void px-4 py-2.5 text-sm z-50 flex items-center justify-center gap-2 shadow-lg border-b border-border">
|
||||
<div className="fixed top-0 left-0 right-0 bg-primary/90 backdrop-blur-sm text-foreground px-4 py-2.5 text-sm z-50 flex items-center justify-center gap-2 shadow-lg border-b border-border">
|
||||
<Loader2 className="w-4 h-4 animate-spin" />
|
||||
<span>
|
||||
Synchronisation en cours
|
||||
|
|
@ -162,14 +162,14 @@ export function OfflineIndicator() {
|
|||
await offlineQueue.clearQueue();
|
||||
setQueueSize(0);
|
||||
}}
|
||||
className="ml-2 px-2 py-1 bg-kodo-red/20 hover:bg-kodo-red/30 rounded border border-kodo-red/30 transition-colors flex items-center gap-1.5 text-xs font-medium"
|
||||
className="ml-2 px-2 py-1 bg-destructive/20 hover:bg-destructive/30 rounded border border-destructive/30 transition-colors flex items-center gap-1.5 text-xs font-medium"
|
||||
title="Clear queued requests"
|
||||
>
|
||||
Clear Queue
|
||||
</button>
|
||||
<button
|
||||
onClick={() => setShowQueueManager(true)}
|
||||
className="ml-2 px-2 py-1 bg-kodo-void/20 hover:bg-kodo-void/30 rounded border border-kodo-void/30 transition-colors flex items-center gap-1.5 text-xs font-medium"
|
||||
className="ml-2 px-2 py-1 bg-background/20 hover:bg-background/30 rounded border border-border/30 transition-colors flex items-center gap-1.5 text-xs font-medium"
|
||||
title="View queued requests"
|
||||
>
|
||||
<List className="w-3.5 h-3.5" />
|
||||
|
|
|
|||
|
|
@ -41,9 +41,9 @@ function formatRequest(request: QueuedRequest): string {
|
|||
function getPriorityColor(priority: QueuedRequest['priority']): string {
|
||||
switch (priority) {
|
||||
case 'high':
|
||||
return 'bg-kodo-red/20 text-destructive border-kodo-red/30';
|
||||
return 'bg-destructive/20 text-destructive border-destructive/30';
|
||||
case 'normal':
|
||||
return 'bg-muted/20 text-kodo-steel border-border/30';
|
||||
return 'bg-muted/20 text-muted-foreground border-border/30';
|
||||
case 'low':
|
||||
return 'bg-muted/30 text-muted-foreground border-border/50';
|
||||
default:
|
||||
|
|
@ -118,9 +118,9 @@ export function OfflineQueueManager({
|
|||
>
|
||||
<div className="space-y-4">
|
||||
{/* Queue Summary */}
|
||||
<div className="flex items-center justify-between p-4 bg-kodo-ink/50 rounded-lg border border-border">
|
||||
<div className="flex items-center justify-between p-4 bg-card/50 rounded-lg border border-border">
|
||||
<div className="flex items-center gap-2">
|
||||
<Clock className="w-5 h-5 text-kodo-steel" />
|
||||
<Clock className="w-5 h-5 text-muted-foreground" />
|
||||
<span className="text-sm text-muted-foreground">
|
||||
{queue.length === 0
|
||||
? 'No queued requests'
|
||||
|
|
@ -151,7 +151,7 @@ export function OfflineQueueManager({
|
|||
{queue.map((request) => (
|
||||
<div
|
||||
key={request.id}
|
||||
className="p-4 bg-kodo-ink/30 rounded-lg border border-border hover:border-border/50 transition-colors"
|
||||
className="p-4 bg-card/30 rounded-lg border border-border hover:border-border/50 transition-colors"
|
||||
>
|
||||
<div className="flex items-start justify-between gap-4">
|
||||
<div className="flex-1 min-w-0">
|
||||
|
|
|
|||
|
|
@ -3,10 +3,10 @@ import { Card } from '@/components/ui/card';
|
|||
import { cn } from '@/lib/utils';
|
||||
|
||||
const NODES = [
|
||||
{ l: 'CORE_KERNEL', s: 'STABLE', c: 'text-lime-500' },
|
||||
{ l: 'CORE_KERNEL', s: 'STABLE', c: 'text-success' },
|
||||
{ l: 'STORAGE_HIVE', s: '88% CAPACITY', c: 'text-gold-500' },
|
||||
{ l: 'REST_UPLINK', s: '12ms', c: 'text-cyan-500' },
|
||||
{ l: 'SECURITY_GRID', s: 'ACTIVE', c: 'text-lime-500' },
|
||||
{ l: 'REST_UPLINK', s: '12ms', c: 'text-primary' },
|
||||
{ l: 'SECURITY_GRID', s: 'ACTIVE', c: 'text-success' },
|
||||
];
|
||||
|
||||
export function AdminDashboardNodeHealthCard() {
|
||||
|
|
|
|||
|
|
@ -17,13 +17,13 @@ const PROTOCOLS = [
|
|||
{
|
||||
id: 'index',
|
||||
label: 'REINDEX DB',
|
||||
icon: <Database className="w-5 h-5 text-cyan-500" />,
|
||||
icon: <Database className="w-5 h-5 text-primary" />,
|
||||
color: 'cyan',
|
||||
},
|
||||
{
|
||||
id: 'sales',
|
||||
label: 'SALES RT',
|
||||
icon: <ShoppingBag className="w-5 h-5 text-lime-500" />,
|
||||
icon: <ShoppingBag className="w-5 h-5 text-success" />,
|
||||
color: 'lime',
|
||||
},
|
||||
{
|
||||
|
|
|
|||
|
|
@ -164,7 +164,7 @@ export function AdminDashboardTabs({
|
|||
<span className="w-24 text-primary font-bold">
|
||||
{log.action ?? 'AUTH_VAL'}
|
||||
</span>
|
||||
<span className="w-24 text-magenta-500">
|
||||
<span className="w-24 text-destructive">
|
||||
USER_{log.user_id != null ? String(log.user_id).slice(0, 4) : '???'}
|
||||
</span>
|
||||
<span className="text-foreground opacity-80 truncate">
|
||||
|
|
|
|||
|
|
@ -21,10 +21,10 @@ export const BanUserModal: React.FC<BanUserModalProps> = ({
|
|||
return (
|
||||
<div className="fixed inset-0 z-[100] flex items-center justify-center p-4">
|
||||
<div
|
||||
className="absolute inset-0 bg-kodo-void/90 backdrop-blur-sm"
|
||||
className="absolute inset-0 bg-background/90 backdrop-blur-sm"
|
||||
onClick={onClose}
|
||||
></div>
|
||||
<div className="relative w-full max-w-md bg-kodo-graphite border border-destructive rounded-xl shadow-2xl animate-scaleIn overflow-hidden">
|
||||
<div className="relative w-full max-w-md bg-muted border border-destructive rounded-xl shadow-2xl animate-scaleIn overflow-hidden">
|
||||
<div className="p-4 border-b border-destructive/30 bg-destructive/10 flex justify-between items-center">
|
||||
<h3 className="font-bold text-destructive flex items-center gap-2">
|
||||
<ShieldBan className="w-5 h-5 fill-current" /> Suspend User
|
||||
|
|
@ -35,7 +35,7 @@ export const BanUserModal: React.FC<BanUserModalProps> = ({
|
|||
</div>
|
||||
|
||||
<div className="p-6 space-y-4">
|
||||
<p className="text-kodo-text-main text-sm">
|
||||
<p className="text-foreground text-sm">
|
||||
You are about to suspend{' '}
|
||||
<span className="font-bold text-white">{username}</span>. This will
|
||||
restrict their access to the platform.
|
||||
|
|
@ -46,7 +46,7 @@ export const BanUserModal: React.FC<BanUserModalProps> = ({
|
|||
Reason
|
||||
</label>
|
||||
<select
|
||||
className="w-full bg-kodo-void border border-border rounded p-2 text-white focus:border-destructive outline-none text-sm"
|
||||
className="w-full bg-background border border-border rounded p-2 text-white focus:border-destructive outline-none text-sm"
|
||||
value={reason}
|
||||
onChange={(e) => setReason(e.target.value)}
|
||||
>
|
||||
|
|
@ -64,14 +64,14 @@ export const BanUserModal: React.FC<BanUserModalProps> = ({
|
|||
Details (Internal Note)
|
||||
</label>
|
||||
<textarea
|
||||
className="w-full bg-kodo-void border border-border rounded p-2 text-white focus:border-destructive outline-none text-sm resize-none h-24"
|
||||
className="w-full bg-background border border-border rounded p-2 text-white focus:border-destructive outline-none text-sm resize-none h-24"
|
||||
placeholder="Provide context for this ban..."
|
||||
value={details}
|
||||
onChange={(e) => setDetails(e.target.value)}
|
||||
/>
|
||||
</div>
|
||||
|
||||
<div className="flex items-center justify-between p-4 bg-kodo-ink rounded border border-border">
|
||||
<div className="flex items-center justify-between p-4 bg-card rounded border border-border">
|
||||
<div className="flex items-center gap-4">
|
||||
<Calendar className="w-5 h-5 text-muted-foreground" />
|
||||
<div>
|
||||
|
|
@ -111,7 +111,7 @@ export const BanUserModal: React.FC<BanUserModalProps> = ({
|
|||
<input
|
||||
type="number"
|
||||
min="1"
|
||||
className="w-full bg-kodo-void border border-border rounded p-2 text-white focus:border-destructive outline-none text-sm"
|
||||
className="w-full bg-background border border-border rounded p-2 text-white focus:border-destructive outline-none text-sm"
|
||||
value={duration}
|
||||
onChange={(e) => setDuration(e.target.value)}
|
||||
/>
|
||||
|
|
@ -119,7 +119,7 @@ export const BanUserModal: React.FC<BanUserModalProps> = ({
|
|||
)}
|
||||
</div>
|
||||
|
||||
<div className="p-4 border-t border-border bg-kodo-ink flex justify-end gap-4">
|
||||
<div className="p-4 border-t border-border bg-card flex justify-end gap-4">
|
||||
<Button variant="ghost" onClick={onClose}>
|
||||
Cancel
|
||||
</Button>
|
||||
|
|
|
|||
|
|
@ -122,7 +122,7 @@ export const TrackAnalyticsView: React.FC<TrackAnalyticsViewProps> = ({
|
|||
<div className="space-y-6">
|
||||
<Card variant="default">
|
||||
<h3 className="font-bold text-foreground mb-4 flex items-center gap-2">
|
||||
<Map className="w-4 h-4 text-kodo-magenta" /> Top Locations
|
||||
<Map className="w-4 h-4 text-destructive" /> Top Locations
|
||||
</h3>
|
||||
<div className="space-y-4">
|
||||
{trackData.geo.map((g) => (
|
||||
|
|
@ -130,7 +130,7 @@ export const TrackAnalyticsView: React.FC<TrackAnalyticsViewProps> = ({
|
|||
<div className="w-16 text-sm text-muted-foreground">{g.country}</div>
|
||||
<div className="flex-1 h-2 bg-muted rounded-full overflow-hidden">
|
||||
<div
|
||||
className="h-full bg-kodo-magenta"
|
||||
className="h-full bg-destructive"
|
||||
style={{ width: `${g.percent}%` }}
|
||||
></div>
|
||||
</div>
|
||||
|
|
|
|||
|
|
@ -24,7 +24,7 @@ export const CartItem: React.FC<CartItemProps> = ({ item, onRemove }) => {
|
|||
className="flex flex-col md:flex-row items-center gap-4 p-4 group hover:border-border/50 transition-all"
|
||||
>
|
||||
{/* Thumbnail */}
|
||||
<div className="w-full md:w-24 h-24 rounded-lg overflow-hidden flex-shrink-0 bg-kodo-graphite">
|
||||
<div className="w-full md:w-24 h-24 rounded-lg overflow-hidden flex-shrink-0 bg-muted">
|
||||
<img
|
||||
src={product.coverUrl}
|
||||
className="w-full h-full object-cover group-hover:scale-105 transition-transform duration-[var(--duration-slow)]"
|
||||
|
|
@ -37,10 +37,10 @@ export const CartItem: React.FC<CartItemProps> = ({ item, onRemove }) => {
|
|||
<h4 className="font-bold text-white text-lg">{product.title}</h4>
|
||||
<p className="text-muted-foreground text-sm mb-2">{product.author}</p>
|
||||
<div className="flex items-center justify-center md:justify-start gap-2 text-xs">
|
||||
<span className="px-2 py-1 bg-kodo-ink border border-border rounded flex items-center gap-1">
|
||||
<span className="px-2 py-1 bg-card border border-border rounded flex items-center gap-1">
|
||||
<Tag className="w-3 h-3 text-muted-foreground" /> {licenseName} License
|
||||
</span>
|
||||
<span className="px-2 py-1 bg-kodo-ink border border-border rounded uppercase font-bold text-muted-foreground">
|
||||
<span className="px-2 py-1 bg-card border border-border rounded uppercase font-bold text-muted-foreground">
|
||||
{product.type}
|
||||
</span>
|
||||
</div>
|
||||
|
|
|
|||
|
|
@ -35,7 +35,7 @@ export const PromoCodeModal: React.FC<PromoCodeModalProps> = ({
|
|||
onClick={onClose}
|
||||
></div>
|
||||
<div className="relative w-full max-w-sm bg-card border border-border rounded-xl shadow-2xl animate-scaleIn overflow-hidden">
|
||||
<div className="p-4 border-b border-border bg-kodo-ink flex justify-between items-center">
|
||||
<div className="p-4 border-b border-border bg-card flex justify-between items-center">
|
||||
<h3 className="font-bold text-white flex items-center gap-2">
|
||||
<Tag className="w-4 h-4 text-muted-foreground" /> Add Promo Code
|
||||
</h3>
|
||||
|
|
|
|||
|
|
@ -43,19 +43,19 @@ export function ActivityGraph() {
|
|||
<Activity className="w-4 h-4 text-primary" />
|
||||
Activité d'écoute
|
||||
</CardTitle>
|
||||
<p className="text-xs text-kodo-text-dim">
|
||||
<p className="text-xs text-muted-foreground">
|
||||
+14.5% par rapport à la période précédente
|
||||
</p>
|
||||
</div>
|
||||
|
||||
<div className="flex bg-kodo-ink/50 p-1 rounded-lg border border-white/5">
|
||||
<div className="flex bg-card/50 p-1 rounded-lg border border-white/5">
|
||||
<button
|
||||
onClick={() => setPeriod(7)}
|
||||
className={cn(
|
||||
"px-3 py-1 text-xs font-medium rounded-md transition-all",
|
||||
period === 7
|
||||
? "bg-primary/20 text-primary shadow-sm"
|
||||
: "text-kodo-text-dim hover:text-white"
|
||||
: "text-muted-foreground hover:text-white"
|
||||
)}
|
||||
>
|
||||
7J
|
||||
|
|
@ -66,7 +66,7 @@ export function ActivityGraph() {
|
|||
"px-3 py-1 text-xs font-medium rounded-md transition-all",
|
||||
period === 30
|
||||
? "bg-primary/20 text-primary shadow-sm"
|
||||
: "text-kodo-text-dim hover:text-white"
|
||||
: "text-muted-foreground hover:text-white"
|
||||
)}
|
||||
>
|
||||
30J
|
||||
|
|
@ -120,17 +120,17 @@ export function ActivityGraph() {
|
|||
isHovered ? "opacity-100 translate-y-0" : "opacity-0 translate-y-2"
|
||||
)}
|
||||
>
|
||||
<div className="bg-kodo-ink border border-border/50 px-3 py-2 rounded-lg shadow-xl whitespace-nowrap">
|
||||
<div className="bg-card border border-border/50 px-3 py-2 rounded-lg shadow-xl whitespace-nowrap">
|
||||
<div className="text-xs font-bold text-white mb-0.5">{point.value} écoutes</div>
|
||||
<div className="text-xs text-kodo-text-dim font-mono">{point.label}</div>
|
||||
<div className="text-xs text-muted-foreground font-mono">{point.label}</div>
|
||||
</div>
|
||||
{/* Triangle du tooltip */}
|
||||
<div className="w-2 h-2 bg-kodo-ink border-b border-r border-border/50 rotate-45 absolute -bottom-1 left-1/2 -translate-x-1/2" />
|
||||
<div className="w-2 h-2 bg-card border-b border-r border-border/50 rotate-45 absolute -bottom-1 left-1/2 -translate-x-1/2" />
|
||||
</div>
|
||||
|
||||
{/* Label Axe X (tous les 3 ou 5 points selon densité) */}
|
||||
{(period === 7 || i % 5 === 0) && (
|
||||
<div className="absolute top-full mt-2 left-1/2 -translate-x-1/2 text-xs text-kodo-text-dim font-mono whitespace-nowrap">
|
||||
<div className="absolute top-full mt-2 left-1/2 -translate-x-1/2 text-xs text-muted-foreground font-mono whitespace-nowrap">
|
||||
{point.label.split(' ')[0]}
|
||||
</div>
|
||||
)}
|
||||
|
|
|
|||
|
|
@ -67,7 +67,7 @@ export const TrackList: React.FC = () => {
|
|||
{[1, 2, 3, 4, 5].map((i) => (
|
||||
<div
|
||||
key={i}
|
||||
className="h-16 bg-kodo-ink/50 animate-pulse rounded-xl border border-border/30"
|
||||
className="h-16 bg-card/50 animate-pulse rounded-xl border border-border/30"
|
||||
></div>
|
||||
))}
|
||||
</div>
|
||||
|
|
@ -76,7 +76,7 @@ export const TrackList: React.FC = () => {
|
|||
|
||||
if (error) {
|
||||
return (
|
||||
<div className="p-6 text-center border border-kodo-red/30 bg-kodo-red/10 rounded-xl text-destructive">
|
||||
<div className="p-6 text-center border border-destructive/30 bg-destructive/10 rounded-xl text-destructive">
|
||||
<AlertCircle className="w-6 h-6 mx-auto mb-2" />
|
||||
<p className="text-sm">Unable to load trending audio.</p>
|
||||
<Button
|
||||
|
|
@ -93,7 +93,7 @@ export const TrackList: React.FC = () => {
|
|||
|
||||
if (tracks.length === 0) {
|
||||
return (
|
||||
<div className="text-muted-foreground text-center py-12 bg-kodo-ink/30 rounded-xl border border-dashed border-border">
|
||||
<div className="text-muted-foreground text-center py-12 bg-card/30 rounded-xl border border-dashed border-border">
|
||||
<BarChart3 className="w-8 h-8 mx-auto mb-2 opacity-50" />
|
||||
<p>No tracks trending right now.</p>
|
||||
</div>
|
||||
|
|
@ -110,7 +110,7 @@ export const TrackList: React.FC = () => {
|
|||
key={track.id}
|
||||
className={`
|
||||
animate-stagger-in group flex items-center gap-4 p-4 rounded-xl transition-all border cursor-pointer relative overflow-hidden
|
||||
${isCurrent ? 'bg-primary/10 border-primary/30' : 'bg-kodo-ink border-transparent hover:border-border/50 hover:bg-kodo-ink/80'}
|
||||
${isCurrent ? 'bg-primary/10 border-primary/30' : 'bg-card border-transparent hover:border-border/50 hover:bg-card/80'}
|
||||
`}
|
||||
style={{ animationDelay: `${Math.min(i * 50, 500)}ms` }}
|
||||
onClick={() => handlePlay(track)}
|
||||
|
|
@ -144,7 +144,7 @@ export const TrackList: React.FC = () => {
|
|||
alt={track.title}
|
||||
/>
|
||||
{isCurrent && (
|
||||
<div className="absolute inset-0 bg-muted/20 ring-1 ring-inset ring-kodo-steel"></div>
|
||||
<div className="absolute inset-0 bg-muted/20 ring-1 ring-inset ring-border"></div>
|
||||
)}
|
||||
</div>
|
||||
|
||||
|
|
@ -175,7 +175,7 @@ export const TrackList: React.FC = () => {
|
|||
<Button
|
||||
variant="ghost"
|
||||
size="icon"
|
||||
className="h-8 w-8 hover:text-kodo-magenta"
|
||||
className="h-8 w-8 hover:text-destructive"
|
||||
onClick={(e) => handleLike(e, track)}
|
||||
>
|
||||
<Heart className="w-4 h-4" />
|
||||
|
|
|
|||
|
|
@ -62,7 +62,7 @@ export const APIPlaygroundView: React.FC = () => {
|
|||
Endpoint
|
||||
</label>
|
||||
<select
|
||||
className="w-full bg-kodo-ink border border-border rounded p-4 text-white focus:border-border outline-none font-mono text-sm"
|
||||
className="w-full bg-card border border-border rounded p-4 text-white focus:border-border outline-none font-mono text-sm"
|
||||
value={selectedEndpoint.path}
|
||||
onChange={(e) => {
|
||||
const ep = ENDPOINTS.find((p) => p.path === e.target.value);
|
||||
|
|
@ -85,7 +85,7 @@ export const APIPlaygroundView: React.FC = () => {
|
|||
Body (JSON)
|
||||
</label>
|
||||
<textarea
|
||||
className="w-full bg-kodo-ink border border-border rounded p-4 text-white focus:border-border outline-none font-mono text-xs h-48 resize-none"
|
||||
className="w-full bg-card border border-border rounded p-4 text-white focus:border-border outline-none font-mono text-xs h-48 resize-none"
|
||||
value={params}
|
||||
onChange={(e) => setParams(e.target.value)}
|
||||
/>
|
||||
|
|
@ -136,7 +136,7 @@ export const APIPlaygroundView: React.FC = () => {
|
|||
{response}
|
||||
</pre>
|
||||
<button
|
||||
className="absolute top-2 right-2 p-2 bg-kodo-graphite rounded text-muted-foreground hover:text-white opacity-0 group-hover:opacity-100 transition-opacity"
|
||||
className="absolute top-2 right-2 p-2 bg-muted rounded text-muted-foreground hover:text-white opacity-0 group-hover:opacity-100 transition-opacity"
|
||||
onClick={() => {
|
||||
navigator.clipboard.writeText(response);
|
||||
addToast('Copied JSON');
|
||||
|
|
|
|||
|
|
@ -158,7 +158,7 @@ export function SwaggerUIDoc({ specUrl, spec, useIframe = false }: SwaggerUIProp
|
|||
<p className="text-xs text-muted-foreground mb-6 text-center max-w-md">
|
||||
Trying to load from: {getOpenApiUrl()}
|
||||
<br />
|
||||
<span className="text-kodo-steel">
|
||||
<span className="text-muted-foreground">
|
||||
The Swagger JSON endpoint may not be available. Try opening Swagger UI directly.
|
||||
</span>
|
||||
</p>
|
||||
|
|
|
|||
|
|
@ -165,7 +165,7 @@ export const CreateAPIKeyModal: React.FC<CreateAPIKeyModalProps> = ({
|
|||
"w-5 h-5 rounded border flex items-center justify-center transition-colors flex-none",
|
||||
selectedScopes.includes(scope.id)
|
||||
? "bg-primary border-primary"
|
||||
: "border-border group-hover:border-kodo-content-dim"
|
||||
: "border-border group-hover:border-border"
|
||||
)}>
|
||||
{selectedScopes.includes(scope.id) && <Check className="w-3 h-3 text-black" />}
|
||||
</div>
|
||||
|
|
@ -195,8 +195,8 @@ export const CreateAPIKeyModal: React.FC<CreateAPIKeyModalProps> = ({
|
|||
) : (
|
||||
<div className="text-center space-y-8 py-4">
|
||||
<div className="relative w-20 h-20 mx-auto">
|
||||
<div className="absolute inset-0 bg-kodo-lime/20 rounded-full animate-ping opacity-50"></div>
|
||||
<div className="relative w-full h-full bg-gradient-to-br from-kodo-lime/20 to-kodo-cyan/20 rounded-full flex items-center justify-center border border-kodo-lime/30 shadow-card-glow-cyan">
|
||||
<div className="absolute inset-0 bg-success/20 rounded-full animate-ping opacity-50"></div>
|
||||
<div className="relative w-full h-full bg-gradient-to-br from-success/20 to-primary/20 rounded-full flex items-center justify-center border border-success/30 shadow-card-glow-cyan">
|
||||
<Check className="w-10 h-10 text-success drop-shadow-lg" />
|
||||
</div>
|
||||
</div>
|
||||
|
|
|
|||
|
|
@ -31,7 +31,7 @@ const CourseCardComponent: React.FC<CourseCardProps> = ({
|
|||
onClick={() => onClick(course)}
|
||||
>
|
||||
{/* Cover */}
|
||||
<div className="relative aspect-video bg-kodo-ink overflow-hidden">
|
||||
<div className="relative aspect-video bg-card overflow-hidden">
|
||||
<OptimizedImage
|
||||
src={course.thumbnailUrl}
|
||||
className="w-full h-full object-cover opacity-90 group-hover:opacity-100 group-hover:scale-105 transition-all duration-[var(--duration-normal)]"
|
||||
|
|
|
|||
|
|
@ -75,7 +75,7 @@ export const MyCoursesView: React.FC<MyCoursesViewProps> = ({ onContinue }) => {
|
|||
return (
|
||||
<div className="animate-fadeIn space-y-8 pb-20">
|
||||
<div className="flex items-center gap-4 mb-6">
|
||||
<GraduationCap className="w-8 h-8 text-kodo-steel" />
|
||||
<GraduationCap className="w-8 h-8 text-muted-foreground" />
|
||||
<h1 className="text-3xl font-heading font-bold text-foreground tracking-tight">
|
||||
My Learning
|
||||
</h1>
|
||||
|
|
@ -83,7 +83,7 @@ export const MyCoursesView: React.FC<MyCoursesViewProps> = ({ onContinue }) => {
|
|||
|
||||
{/* Continue Learning Banner */}
|
||||
{lastActiveCourse && activeTab === 'in_progress' && (
|
||||
<div className="bg-kodo-ink p-6 rounded-2xl border border-border flex flex-col md:flex-row gap-6 items-center shadow-2xl">
|
||||
<div className="bg-card p-6 rounded-2xl border border-border flex flex-col md:flex-row gap-6 items-center shadow-2xl">
|
||||
<div
|
||||
className="relative w-full md:w-64 aspect-video rounded-lg overflow-hidden group cursor-pointer"
|
||||
onClick={() => onContinue(lastActiveCourse)}
|
||||
|
|
|
|||
|
|
@ -57,10 +57,10 @@ export const QuizModal: React.FC<QuizModalProps> = ({
|
|||
return (
|
||||
<div className="fixed inset-0 z-[100] flex items-center justify-center p-4">
|
||||
<div
|
||||
className="absolute inset-0 bg-kodo-void/90 backdrop-blur-sm"
|
||||
className="absolute inset-0 bg-background/90 backdrop-blur-sm"
|
||||
onClick={handleFinish}
|
||||
></div>
|
||||
<div className="relative w-full max-w-md bg-kodo-graphite border border-border rounded-xl shadow-2xl animate-scaleIn overflow-hidden p-8 text-center">
|
||||
<div className="relative w-full max-w-md bg-muted border border-border rounded-xl shadow-2xl animate-scaleIn overflow-hidden p-8 text-center">
|
||||
<div className="mb-6 flex justify-center">
|
||||
{passed ? (
|
||||
<div className="w-20 h-20 bg-success/20 rounded-full flex items-center justify-center text-success border-2 border-success animate-pulse">
|
||||
|
|
@ -103,12 +103,12 @@ export const QuizModal: React.FC<QuizModalProps> = ({
|
|||
|
||||
return (
|
||||
<div className="fixed inset-0 z-[100] flex items-center justify-center p-4">
|
||||
<div className="absolute inset-0 bg-kodo-void/90 backdrop-blur-sm"></div>
|
||||
<div className="relative w-full max-w-2xl bg-kodo-graphite border border-border rounded-xl shadow-2xl animate-scaleIn overflow-hidden flex flex-col max-h-layout-modal-sm">
|
||||
<div className="absolute inset-0 bg-background/90 backdrop-blur-sm"></div>
|
||||
<div className="relative w-full max-w-2xl bg-muted border border-border rounded-xl shadow-2xl animate-scaleIn overflow-hidden flex flex-col max-h-layout-modal-sm">
|
||||
{/* Header */}
|
||||
<div className="p-4 border-b border-border bg-kodo-ink flex justify-between items-center">
|
||||
<div className="p-4 border-b border-border bg-card flex justify-between items-center">
|
||||
<h3 className="font-bold text-white flex items-center gap-2">
|
||||
<HelpCircle className="w-5 h-5 text-kodo-steel" /> {quiz.title}
|
||||
<HelpCircle className="w-5 h-5 text-muted-foreground" /> {quiz.title}
|
||||
</h3>
|
||||
<button onClick={onClose}>
|
||||
<X className="w-5 h-5 text-muted-foreground hover:text-white" />
|
||||
|
|
@ -142,7 +142,7 @@ export const QuizModal: React.FC<QuizModalProps> = ({
|
|||
className={`w-full text-left p-4 rounded-lg border transition-all ${
|
||||
selectedAnswers[currentQuestionIndex] === idx
|
||||
? 'bg-primary/10 border-primary text-white'
|
||||
: 'bg-kodo-ink border-border text-kodo-text-main hover:bg-white/5 hover:border-border'
|
||||
: 'bg-card border-border text-foreground hover:bg-white/5 hover:border-border'
|
||||
}`}
|
||||
>
|
||||
<div className="flex items-center gap-4">
|
||||
|
|
@ -159,7 +159,7 @@ export const QuizModal: React.FC<QuizModalProps> = ({
|
|||
</div>
|
||||
|
||||
{/* Footer */}
|
||||
<div className="p-4 border-t border-border bg-kodo-ink flex justify-between items-center">
|
||||
<div className="p-4 border-t border-border bg-card flex justify-between items-center">
|
||||
<span className="text-xs text-muted-foreground">
|
||||
Passing Score: {quiz.passingScore}%
|
||||
</span>
|
||||
|
|
|
|||
|
|
@ -19,17 +19,17 @@ const ALERT_ICONS = {
|
|||
};
|
||||
|
||||
const ALERT_STYLES = {
|
||||
info: 'bg-muted/10 border-border/30 text-kodo-text-main dark:bg-muted/20 dark:border-border/40 dark:text-kodo-steel',
|
||||
info: 'bg-muted/10 border-border/30 text-foreground dark:bg-muted/20 dark:border-border/40 dark:text-muted-foreground',
|
||||
success:
|
||||
'bg-success/10 border-success/30 text-kodo-text-main dark:bg-success/20 dark:border-success/40 dark:text-success',
|
||||
'bg-success/10 border-success/30 text-foreground dark:bg-success/20 dark:border-success/40 dark:text-success',
|
||||
warning:
|
||||
'bg-warning/10 border-warning/30 text-kodo-text-main dark:bg-warning/20 dark:border-warning/40 dark:text-warning',
|
||||
'bg-warning/10 border-warning/30 text-foreground dark:bg-warning/20 dark:border-warning/40 dark:text-warning',
|
||||
error:
|
||||
'bg-destructive/10 border-destructive/30 text-kodo-text-main dark:bg-destructive/20 dark:border-destructive/40 dark:text-destructive',
|
||||
'bg-destructive/10 border-destructive/30 text-foreground dark:bg-destructive/20 dark:border-destructive/40 dark:text-destructive',
|
||||
};
|
||||
|
||||
const ICON_STYLES = {
|
||||
info: 'text-kodo-steel dark:text-kodo-steel',
|
||||
info: 'text-muted-foreground dark:text-muted-foreground',
|
||||
success: 'text-success dark:text-success',
|
||||
warning: 'text-warning dark:text-warning',
|
||||
error: 'text-destructive dark:text-destructive',
|
||||
|
|
|
|||
|
|
@ -39,16 +39,16 @@ export function PasswordStrengthIndicator({
|
|||
const strengthLabels = ['Very Weak', 'Weak', 'Fair', 'Good', 'Strong'];
|
||||
const strengthColors = [
|
||||
'bg-destructive',
|
||||
'bg-kodo-orange',
|
||||
'bg-warning',
|
||||
'bg-warning',
|
||||
'bg-primary',
|
||||
'bg-success',
|
||||
];
|
||||
const strengthTextColors = [
|
||||
'text-destructive',
|
||||
'text-kodo-orange',
|
||||
'text-warning',
|
||||
'text-kodo-steel',
|
||||
'text-warning',
|
||||
'text-muted-foreground',
|
||||
'text-success',
|
||||
];
|
||||
|
||||
|
|
|
|||
|
|
@ -132,7 +132,7 @@ export function RegisterForm({
|
|||
emailValue &&
|
||||
emailValidation &&
|
||||
(emailValidation.valid
|
||||
? 'border-success focus-visible:ring-kodo-lime'
|
||||
? 'border-success focus-visible:ring-success'
|
||||
: 'border-destructive focus-visible:ring-red-500'),
|
||||
)}
|
||||
/>
|
||||
|
|
|
|||
|
|
@ -44,7 +44,7 @@ export const AchievementCard: React.FC<AchievementCardProps> = ({
|
|||
className={`flex ${compact ? 'flex-row items-center gap-4' : 'flex-col items-center text-center gap-4'}`}
|
||||
>
|
||||
<div
|
||||
className={`rounded-full bg-gradient-to-br from-kodo-graphite to-black flex items-center justify-center border-2 ${isUnlocked ? 'border-warning w-16 h-16 text-3xl shadow-gold-glow' : 'border-border w-12 h-12 text-xl text-muted-foreground'}`}
|
||||
className={`rounded-full bg-gradient-to-br from-muted to-black flex items-center justify-center border-2 ${isUnlocked ? 'border-warning w-16 h-16 text-3xl shadow-gold-glow' : 'border-border w-12 h-12 text-xl text-muted-foreground'}`}
|
||||
>
|
||||
{achievement.icon}
|
||||
</div>
|
||||
|
|
|
|||
|
|
@ -140,7 +140,7 @@ export const LeaderboardView: React.FC = () => {
|
|||
<th className="p-4 text-center">Trend</th>
|
||||
</tr>
|
||||
</thead>
|
||||
<tbody className="divide-y divide-kodo-steel/30 text-sm">
|
||||
<tbody className="divide-y divide-border/30 text-sm">
|
||||
{leaderboard.map((entry) => {
|
||||
const rankStyle =
|
||||
entry.rank === 1
|
||||
|
|
|
|||
|
|
@ -63,7 +63,7 @@ export const ProfileXPView: React.FC<ProfileXPViewProps> = ({ username }) => {
|
|||
<div className="relative z-10 flex flex-col md:flex-row items-center gap-8">
|
||||
{/* Level Badge */}
|
||||
<div className="flex flex-col items-center justify-center">
|
||||
<div className="w-24 h-24 bg-gradient-to-b from-kodo-gold to-orange-600 rounded-full flex items-center justify-center shadow-gold-glow border-4 border-border">
|
||||
<div className="w-24 h-24 bg-gradient-to-b from-sumi-gold to-orange-600 rounded-full flex items-center justify-center shadow-gold-glow border-4 border-border">
|
||||
<div className="text-4xl font-black text-foreground">
|
||||
{xpData.level}
|
||||
</div>
|
||||
|
|
@ -141,7 +141,7 @@ export const ProfileXPView: React.FC<ProfileXPViewProps> = ({ username }) => {
|
|||
</div>
|
||||
</Card>
|
||||
<Card variant="default" className="flex items-center gap-4 p-4">
|
||||
<div className="w-12 h-12 bg-card rounded-lg flex items-center justify-center text-kodo-magenta">
|
||||
<div className="w-12 h-12 bg-card rounded-lg flex items-center justify-center text-destructive">
|
||||
<Target className="w-6 h-6" />
|
||||
</div>
|
||||
<div>
|
||||
|
|
|
|||
|
|
@ -55,7 +55,7 @@ export const XPBar: React.FC<XPBarProps> = ({
|
|||
|
||||
{/* Progress Fill */}
|
||||
<div
|
||||
className="h-full bg-gradient-to-r from-kodo-gold/80 to-kodo-gold transition-all duration-[var(--duration-slow)] shadow-gold-glow relative"
|
||||
className="h-full bg-gradient-to-r from-sumi-gold/80 to-warning transition-all duration-[var(--duration-slow)] shadow-gold-glow relative"
|
||||
style={{ width: `${percentage}%` }}
|
||||
>
|
||||
{/* Shimmer Effect */}
|
||||
|
|
|
|||
|
|
@ -54,9 +54,9 @@ export const AddEquipmentView: React.FC = () => {
|
|||
<div className="space-y-6">
|
||||
<Card variant="default">
|
||||
<h3 className="font-bold text-white mb-4 text-sm uppercase tracking-wider flex items-center gap-2">
|
||||
<Camera className="w-4 h-4 text-kodo-steel" /> Photos
|
||||
<Camera className="w-4 h-4 text-muted-foreground" /> Photos
|
||||
</h3>
|
||||
<div className="aspect-square bg-kodo-ink border-2 border-dashed border-border rounded-xl flex flex-col items-center justify-center text-muted-foreground hover:text-white hover:border-border/50 cursor-pointer transition-colors group mb-4">
|
||||
<div className="aspect-square bg-card border-2 border-dashed border-border rounded-xl flex flex-col items-center justify-center text-muted-foreground hover:text-white hover:border-border/50 cursor-pointer transition-colors group mb-4">
|
||||
<Camera className="w-8 h-8 mb-2 transition-opacity group-hover:opacity-80" />
|
||||
<span className="text-xs font-bold uppercase">Upload Photos</span>
|
||||
</div>
|
||||
|
|
@ -64,7 +64,7 @@ export const AddEquipmentView: React.FC = () => {
|
|||
{[1, 2, 3].map((i) => (
|
||||
<div
|
||||
key={i}
|
||||
className="aspect-square bg-kodo-ink rounded border border-border/50"
|
||||
className="aspect-square bg-card rounded border border-border/50"
|
||||
></div>
|
||||
))}
|
||||
</div>
|
||||
|
|
@ -93,7 +93,7 @@ export const AddEquipmentView: React.FC = () => {
|
|||
Category
|
||||
</label>
|
||||
<select
|
||||
className="w-full bg-kodo-graphite border border-border rounded-lg p-4 text-white focus:border-border outline-none"
|
||||
className="w-full bg-muted border border-border rounded-lg p-4 text-white focus:border-border outline-none"
|
||||
value={formData.category}
|
||||
onChange={(e) => handleChange('category', e.target.value)}
|
||||
>
|
||||
|
|
@ -175,7 +175,7 @@ export const AddEquipmentView: React.FC = () => {
|
|||
Notes
|
||||
</h3>
|
||||
<textarea
|
||||
className="w-full bg-kodo-graphite border border-border rounded-lg p-4 text-white focus:border-border outline-none min-h-25"
|
||||
className="w-full bg-muted border border-border rounded-lg p-4 text-white focus:border-border outline-none min-h-25"
|
||||
placeholder="Condition notes, modifications, etc..."
|
||||
value={formData.notes}
|
||||
onChange={(e) => handleChange('notes', e.target.value)}
|
||||
|
|
|
|||
|
|
@ -15,9 +15,9 @@ export const EquipmentCard: React.FC<EquipmentCardProps> = ({
|
|||
}) => {
|
||||
const statusColor = {
|
||||
Active: 'text-success bg-success/10',
|
||||
Maintenance: 'text-kodo-orange bg-kodo-orange/10',
|
||||
Maintenance: 'text-warning bg-warning/10',
|
||||
Sold: 'text-muted-foreground bg-muted/10',
|
||||
Wishlist: 'text-kodo-magenta bg-kodo-magenta/10',
|
||||
Wishlist: 'text-destructive bg-destructive/10',
|
||||
};
|
||||
|
||||
return (
|
||||
|
|
@ -26,7 +26,7 @@ export const EquipmentCard: React.FC<EquipmentCardProps> = ({
|
|||
className="group p-0 overflow-hidden cursor-pointer hover:bg-white/5 transition-colors duration-[var(--duration-fast)] flex flex-col h-full"
|
||||
onClick={() => onClick(item)}
|
||||
>
|
||||
<div className="relative aspect-square bg-kodo-ink overflow-hidden">
|
||||
<div className="relative aspect-square bg-card overflow-hidden">
|
||||
<img
|
||||
src={item.image || 'https://via.placeholder.com/400'}
|
||||
className="w-full h-full object-cover opacity-90 group-hover:opacity-100 transition-opacity duration-[var(--duration-fast)]"
|
||||
|
|
@ -57,7 +57,7 @@ export const EquipmentCard: React.FC<EquipmentCardProps> = ({
|
|||
<Tag className="w-3 h-3" /> {item.condition}
|
||||
</div>
|
||||
<div className="flex items-center gap-1 font-mono text-white font-bold">
|
||||
<DollarSign className="w-3 h-3 text-kodo-steel" />{' '}
|
||||
<DollarSign className="w-3 h-3 text-muted-foreground" />{' '}
|
||||
{item.purchasePrice}
|
||||
</div>
|
||||
</div>
|
||||
|
|
|
|||
|
|
@ -79,7 +79,7 @@ export const InventoryView: React.FC<InventoryViewProps> = ({ onNavigate }) => {
|
|||
</div>
|
||||
|
||||
{/* Filters */}
|
||||
<div className="flex flex-col md:flex-row gap-4 items-center bg-kodo-ink/50 p-4 rounded-xl border border-border/50">
|
||||
<div className="flex flex-col md:flex-row gap-4 items-center bg-card/50 p-4 rounded-xl border border-border/50">
|
||||
<div className="w-full md:w-96">
|
||||
<SearchInput
|
||||
placeholder="Search gear..."
|
||||
|
|
@ -89,10 +89,10 @@ export const InventoryView: React.FC<InventoryViewProps> = ({ onNavigate }) => {
|
|||
</div>
|
||||
|
||||
<div className="flex flex-wrap gap-2 w-full md:w-auto">
|
||||
<div className="flex items-center gap-2 bg-kodo-void rounded-lg p-1 border border-border">
|
||||
<div className="flex items-center gap-2 bg-background rounded-lg p-1 border border-border">
|
||||
<Filter className="w-4 h-4 text-muted-foreground ml-2" />
|
||||
<select
|
||||
className="bg-transparent text-sm text-kodo-text-main focus:outline-none p-1 cursor-pointer"
|
||||
className="bg-transparent text-sm text-foreground focus:outline-none p-1 cursor-pointer"
|
||||
value={filterCat}
|
||||
onChange={(e) => setFilterCat(e.target.value)}
|
||||
>
|
||||
|
|
@ -104,10 +104,10 @@ export const InventoryView: React.FC<InventoryViewProps> = ({ onNavigate }) => {
|
|||
</select>
|
||||
</div>
|
||||
|
||||
<div className="flex items-center gap-2 bg-kodo-void rounded-lg p-1 border border-border">
|
||||
<div className="flex items-center gap-2 bg-background rounded-lg p-1 border border-border">
|
||||
<Box className="w-4 h-4 text-muted-foreground ml-2" />
|
||||
<select
|
||||
className="bg-transparent text-sm text-kodo-text-main focus:outline-none p-1 cursor-pointer"
|
||||
className="bg-transparent text-sm text-foreground focus:outline-none p-1 cursor-pointer"
|
||||
value={filterStatus}
|
||||
onChange={(e) => setFilterStatus(e.target.value)}
|
||||
>
|
||||
|
|
@ -124,7 +124,7 @@ export const InventoryView: React.FC<InventoryViewProps> = ({ onNavigate }) => {
|
|||
{/* Grid */}
|
||||
{loading ? (
|
||||
<div className="flex justify-center py-24">
|
||||
<Loader2 className="w-8 h-8 text-kodo-steel animate-spin" />
|
||||
<Loader2 className="w-8 h-8 text-muted-foreground animate-spin" />
|
||||
</div>
|
||||
) : (
|
||||
<div className="grid grid-cols-1 md:grid-cols-2 lg:grid-cols-3 xl:grid-cols-4 gap-6">
|
||||
|
|
|
|||
|
|
@ -82,7 +82,7 @@ export function KeyboardShortcutsHelp({
|
|||
<span className="text-sm text-muted-foreground dark:text-muted-foreground">
|
||||
{shortcut.description}
|
||||
</span>
|
||||
<kbd className="px-2 py-1 text-xs font-semibold text-kodo-text-main dark:text-kodo-text-main bg-kodo-void dark:bg-kodo-graphite border border-border dark:border-border rounded">
|
||||
<kbd className="px-2 py-1 text-xs font-semibold text-foreground dark:text-foreground bg-background dark:bg-muted border border-border dark:border-border rounded">
|
||||
{shortcut.key}
|
||||
</kbd>
|
||||
</div>
|
||||
|
|
|
|||
|
|
@ -66,7 +66,7 @@ export const AudioPlayer: React.FC = () => {
|
|||
<div className="fixed bottom-24 right-4 w-full md:w-96 bg-card/95 backdrop-blur-xl border border-border/50 rounded-xl shadow-2xl z-40 overflow-hidden animate-slideUp max-h-layout-panel flex flex-col ring-1 ring-white/10">
|
||||
<div className="flex items-center justify-between p-4 border-b border-border bg-muted/80">
|
||||
<h3 className="font-bold text-foreground text-sm tracking-wide flex items-center gap-2">
|
||||
<ListMusic className="w-4 h-4 text-kodo-steel" /> PLAY QUEUE
|
||||
<ListMusic className="w-4 h-4 text-muted-foreground" /> PLAY QUEUE
|
||||
</h3>
|
||||
<X
|
||||
className="w-5 h-5 text-muted-foreground cursor-pointer hover:text-foreground"
|
||||
|
|
@ -112,7 +112,7 @@ export const AudioPlayer: React.FC = () => {
|
|||
</div>
|
||||
</div>
|
||||
<button
|
||||
className="p-2 hover:bg-white/10 rounded-full text-muted-foreground hover:text-kodo-magenta"
|
||||
className="p-2 hover:bg-white/10 rounded-full text-muted-foreground hover:text-destructive"
|
||||
onClick={() => addToast('Saved to Library', 'success')}
|
||||
>
|
||||
<Heart className="w-4 h-4" />
|
||||
|
|
|
|||
|
|
@ -164,7 +164,7 @@ export const Navbar: React.FC<NavbarProps> = ({ onNavigate, onLogout }) => {
|
|||
>
|
||||
<ShoppingCart className="w-5 h-5" />
|
||||
{itemCount > 0 && (
|
||||
<span className="absolute top-1.5 right-1.5 w-2 h-2 bg-primary rounded-full border border-kodo-void"></span>
|
||||
<span className="absolute top-1.5 right-1.5 w-2 h-2 bg-primary rounded-full border border-border"></span>
|
||||
)}
|
||||
</Button>
|
||||
|
||||
|
|
|
|||
|
|
@ -48,7 +48,7 @@ export const AutoMetadataDetectionModal: React.FC<
|
|||
{loading ? (
|
||||
<div className="space-y-6">
|
||||
<div className="relative">
|
||||
<div className="w-20 h-20 rounded-full border-4 border-border border-t-kodo-steel animate-spin mx-auto"></div>
|
||||
<div className="w-20 h-20 rounded-full border-4 border-border border-t-border animate-spin mx-auto"></div>
|
||||
<div className="absolute inset-0 flex items-center justify-center">
|
||||
<Music2 className="w-8 h-8 text-muted-foreground/50" />
|
||||
</div>
|
||||
|
|
|
|||
|
|
@ -34,15 +34,15 @@ export const WatermarkSettingsModal: React.FC<WatermarkSettingsModalProps> = ({
|
|||
return (
|
||||
<div className="fixed inset-0 z-[100] flex items-center justify-center p-4">
|
||||
<div
|
||||
className="absolute inset-0 bg-kodo-void/90 backdrop-blur-sm"
|
||||
className="absolute inset-0 bg-background/90 backdrop-blur-sm"
|
||||
onClick={onClose}
|
||||
></div>
|
||||
<div className="relative w-full max-w-2xl bg-kodo-graphite border border-border rounded-xl shadow-2xl overflow-hidden animate-scaleIn flex flex-col md:flex-row">
|
||||
<div className="relative w-full max-w-2xl bg-muted border border-border rounded-xl shadow-2xl overflow-hidden animate-scaleIn flex flex-col md:flex-row">
|
||||
{/* Left: Controls */}
|
||||
<div className="w-full md:w-1/2 p-6 border-r border-border bg-kodo-ink">
|
||||
<div className="w-full md:w-1/2 p-6 border-r border-border bg-card">
|
||||
<div className="flex justify-between items-center mb-6">
|
||||
<h3 className="font-bold text-white flex items-center gap-2">
|
||||
<Stamp className="w-4 h-4 text-kodo-magenta" /> Watermark
|
||||
<Stamp className="w-4 h-4 text-destructive" /> Watermark
|
||||
</h3>
|
||||
</div>
|
||||
|
||||
|
|
@ -53,7 +53,7 @@ export const WatermarkSettingsModal: React.FC<WatermarkSettingsModalProps> = ({
|
|||
</span>
|
||||
<div
|
||||
onClick={() => setEnabled(!enabled)}
|
||||
className={`w-10 h-5 rounded-full relative transition-colors ${enabled ? 'bg-kodo-magenta' : 'bg-muted'}`}
|
||||
className={`w-10 h-5 rounded-full relative transition-colors ${enabled ? 'bg-destructive' : 'bg-muted'}`}
|
||||
>
|
||||
<div
|
||||
className={`absolute top-1 w-3 h-3 bg-white rounded-full transition-all ${enabled ? 'left-6' : 'left-1'}`}
|
||||
|
|
@ -77,7 +77,7 @@ export const WatermarkSettingsModal: React.FC<WatermarkSettingsModalProps> = ({
|
|||
<button
|
||||
key={i}
|
||||
onClick={() => setPosition(i)}
|
||||
className={`h-10 rounded border text-xs uppercase font-bold transition-all ${position === i ? 'bg-kodo-magenta border-kodo-magenta text-white' : 'bg-kodo-void border-border text-muted-foreground hover:border-border'}`}
|
||||
className={`h-10 rounded border text-xs uppercase font-bold transition-all ${position === i ? 'bg-destructive border-destructive text-white' : 'bg-background border-border text-muted-foreground hover:border-border'}`}
|
||||
>
|
||||
{/* Icon representation usually better, but text works for demo */}
|
||||
<div
|
||||
|
|
@ -99,7 +99,7 @@ export const WatermarkSettingsModal: React.FC<WatermarkSettingsModalProps> = ({
|
|||
max="100"
|
||||
value={opacity}
|
||||
onChange={(e) => setOpacity(Number(e.target.value))}
|
||||
className="w-full h-1 bg-muted rounded-lg appearance-none cursor-pointer [&::-webkit-slider-thumb]:appearance-none [&::-webkit-slider-thumb]:w-4 [&::-webkit-slider-thumb]:h-4 [&::-webkit-slider-thumb]:bg-kodo-magenta [&::-webkit-slider-thumb]:rounded-full"
|
||||
className="w-full h-1 bg-muted rounded-lg appearance-none cursor-pointer [&::-webkit-slider-thumb]:appearance-none [&::-webkit-slider-thumb]:w-4 [&::-webkit-slider-thumb]:h-4 [&::-webkit-slider-thumb]:bg-destructive [&::-webkit-slider-thumb]:rounded-full"
|
||||
/>
|
||||
</div>
|
||||
</div>
|
||||
|
|
@ -129,7 +129,7 @@ export const WatermarkSettingsModal: React.FC<WatermarkSettingsModalProps> = ({
|
|||
</div>
|
||||
|
||||
{/* Dummy Content */}
|
||||
<div className="w-3/4 aspect-square bg-kodo-graphite rounded-lg relative overflow-hidden shadow-2xl">
|
||||
<div className="w-3/4 aspect-square bg-muted rounded-lg relative overflow-hidden shadow-2xl">
|
||||
<img
|
||||
src="https://picsum.photos/id/237/600/600"
|
||||
className="w-full h-full object-cover opacity-80"
|
||||
|
|
|
|||
|
|
@ -72,11 +72,11 @@ export const AddToPlaylistModal: React.FC<AddToPlaylistModalProps> = ({
|
|||
return (
|
||||
<div className="fixed inset-0 z-[100] flex items-center justify-center p-4">
|
||||
<div
|
||||
className="absolute inset-0 bg-kodo-void/90 backdrop-blur-sm"
|
||||
className="absolute inset-0 bg-background/90 backdrop-blur-sm"
|
||||
onClick={onClose}
|
||||
></div>
|
||||
<div className="relative w-full max-w-md bg-kodo-graphite border border-border rounded-xl shadow-2xl animate-scaleIn overflow-hidden flex flex-col max-h-layout-modal-xs">
|
||||
<div className="p-4 border-b border-border bg-kodo-ink flex justify-between items-center">
|
||||
<div className="relative w-full max-w-md bg-muted border border-border rounded-xl shadow-2xl animate-scaleIn overflow-hidden flex flex-col max-h-layout-modal-xs">
|
||||
<div className="p-4 border-b border-border bg-card flex justify-between items-center">
|
||||
<h3 className="font-bold text-white">Add to Playlist</h3>
|
||||
<button onClick={onClose}>
|
||||
<X className="w-5 h-5 text-muted-foreground hover:text-white" />
|
||||
|
|
@ -86,7 +86,7 @@ export const AddToPlaylistModal: React.FC<AddToPlaylistModalProps> = ({
|
|||
<div className="p-4">
|
||||
<div className="relative mb-4">
|
||||
<input
|
||||
className="w-full bg-kodo-void border border-border rounded-lg py-2 pl-9 pr-4 text-white text-sm focus:border-border outline-none"
|
||||
className="w-full bg-background border border-border rounded-lg py-2 pl-9 pr-4 text-white text-sm focus:border-border outline-none"
|
||||
placeholder="Find playlist"
|
||||
value={search}
|
||||
onChange={(e) => setSearch(e.target.value)}
|
||||
|
|
@ -139,7 +139,7 @@ export const AddToPlaylistModal: React.FC<AddToPlaylistModalProps> = ({
|
|||
</div>
|
||||
</div>
|
||||
|
||||
<div className="p-4 border-t border-border bg-kodo-ink flex justify-end">
|
||||
<div className="p-4 border-t border-border bg-card flex justify-end">
|
||||
<Button
|
||||
variant="primary"
|
||||
onClick={handleConfirm}
|
||||
|
|
|
|||
|
|
@ -42,10 +42,10 @@ export const EditPlaylistModal: React.FC<EditPlaylistModalProps> = ({
|
|||
return (
|
||||
<div className="fixed inset-0 z-[110] flex items-center justify-center p-4">
|
||||
<div
|
||||
className="absolute inset-0 bg-kodo-void/90 backdrop-blur-sm"
|
||||
className="absolute inset-0 bg-background/90 backdrop-blur-sm"
|
||||
onClick={() => setShowDeleteConfirm(false)}
|
||||
></div>
|
||||
<div className="relative w-full max-w-sm bg-kodo-graphite border border-destructive rounded-xl shadow-2xl animate-scaleIn p-6 text-center">
|
||||
<div className="relative w-full max-w-sm bg-muted border border-destructive rounded-xl shadow-2xl animate-scaleIn p-6 text-center">
|
||||
<h3 className="text-xl font-bold text-white mb-2">
|
||||
Delete "{playlist.title}"?
|
||||
</h3>
|
||||
|
|
@ -72,11 +72,11 @@ export const EditPlaylistModal: React.FC<EditPlaylistModalProps> = ({
|
|||
return (
|
||||
<div className="fixed inset-0 z-[100] flex items-center justify-center p-4">
|
||||
<div
|
||||
className="absolute inset-0 bg-kodo-void/90 backdrop-blur-sm"
|
||||
className="absolute inset-0 bg-background/90 backdrop-blur-sm"
|
||||
onClick={onClose}
|
||||
></div>
|
||||
<div className="relative w-full max-w-lg bg-kodo-graphite border border-border rounded-xl shadow-2xl animate-scaleIn overflow-hidden">
|
||||
<div className="p-4 border-b border-border bg-kodo-ink flex justify-between items-center">
|
||||
<div className="relative w-full max-w-lg bg-muted border border-border rounded-xl shadow-2xl animate-scaleIn overflow-hidden">
|
||||
<div className="p-4 border-b border-border bg-card flex justify-between items-center">
|
||||
<h3 className="font-bold text-white">Edit Details</h3>
|
||||
<button onClick={onClose}>
|
||||
<X className="w-5 h-5 text-muted-foreground hover:text-white" />
|
||||
|
|
@ -84,7 +84,7 @@ export const EditPlaylistModal: React.FC<EditPlaylistModalProps> = ({
|
|||
</div>
|
||||
|
||||
<div className="p-6 flex flex-col md:flex-row gap-6">
|
||||
<div className="w-40 h-40 bg-kodo-ink border border-border rounded-lg flex flex-col items-center justify-center relative group overflow-hidden flex-shrink-0">
|
||||
<div className="w-40 h-40 bg-card border border-border rounded-lg flex flex-col items-center justify-center relative group overflow-hidden flex-shrink-0">
|
||||
<img
|
||||
src={playlist.cover_url}
|
||||
className="w-full h-full object-cover opacity-60 group-hover:opacity-40 transition-opacity"
|
||||
|
|
@ -102,7 +102,7 @@ export const EditPlaylistModal: React.FC<EditPlaylistModalProps> = ({
|
|||
/>
|
||||
|
||||
<textarea
|
||||
className="w-full bg-kodo-graphite border border-border rounded-lg p-4 text-white focus:border-border outline-none text-sm resize-none h-24"
|
||||
className="w-full bg-muted border border-border rounded-lg p-4 text-white focus:border-border outline-none text-sm resize-none h-24"
|
||||
placeholder="Description"
|
||||
value={description}
|
||||
onChange={(e) => setDescription(e.target.value)}
|
||||
|
|
@ -115,7 +115,7 @@ export const EditPlaylistModal: React.FC<EditPlaylistModalProps> = ({
|
|||
>
|
||||
<div className="flex items-center gap-4">
|
||||
{isPublic ? (
|
||||
<Globe className="w-4 h-4 text-kodo-steel" />
|
||||
<Globe className="w-4 h-4 text-muted-foreground" />
|
||||
) : (
|
||||
<Lock className="w-4 h-4 text-warning" />
|
||||
)}
|
||||
|
|
@ -139,7 +139,7 @@ export const EditPlaylistModal: React.FC<EditPlaylistModalProps> = ({
|
|||
</div>
|
||||
</div>
|
||||
|
||||
<div className="p-4 border-t border-border bg-kodo-ink flex justify-between items-center">
|
||||
<div className="p-4 border-t border-border bg-card flex justify-between items-center">
|
||||
<Button
|
||||
variant="ghost"
|
||||
className="text-destructive hover:bg-destructive/10"
|
||||
|
|
|
|||
|
|
@ -103,7 +103,7 @@ export const PlaylistDetailView: React.FC<PlaylistDetailViewProps> = ({
|
|||
<div className="animate-fadeIn pb-20">
|
||||
{/* Header Section */}
|
||||
<div className="flex flex-col md:flex-row gap-8 items-end mb-8 p-8 bg-card/40 rounded-2xl border-t border-border">
|
||||
<div className="w-52 h-52 shadow-2xl shadow-kodo-steel/10 rounded-lg overflow-hidden flex-shrink-0 group relative">
|
||||
<div className="w-52 h-52 shadow-2xl shadow-sm rounded-lg overflow-hidden flex-shrink-0 group relative">
|
||||
<OptimizedImage
|
||||
src={playlist.cover_url}
|
||||
alt={playlist.title || 'Playlist cover'}
|
||||
|
|
@ -235,7 +235,7 @@ export const PlaylistDetailView: React.FC<PlaylistDetailViewProps> = ({
|
|||
2 days ago
|
||||
</div>
|
||||
<div className="text-right pr-2 flex items-center justify-end gap-4 text-sm text-muted-foreground font-mono">
|
||||
<Heart className="w-4 h-4 opacity-0 group-hover:opacity-100 hover:text-kodo-magenta cursor-pointer transition-all" />
|
||||
<Heart className="w-4 h-4 opacity-0 group-hover:opacity-100 hover:text-destructive cursor-pointer transition-all" />
|
||||
<span>{track.duration}</span>
|
||||
<MoreHorizontal className="w-4 h-4 opacity-0 group-hover:opacity-100 hover:text-foreground cursor-pointer" />
|
||||
</div>
|
||||
|
|
|
|||
|
|
@ -100,7 +100,7 @@ export const QueueView: React.FC = () => {
|
|||
</h3>
|
||||
<Card
|
||||
variant="glass"
|
||||
className="flex items-center gap-4 p-4 border-l-4 border-l-kodo-cyan"
|
||||
className="flex items-center gap-4 p-4 border-l-4 border-l-primary"
|
||||
>
|
||||
<div
|
||||
className="relative w-16 h-16 rounded overflow-hidden flex-shrink-0 group cursor-pointer"
|
||||
|
|
|
|||
|
|
@ -122,7 +122,7 @@ export const LiveStreamDetailView: React.FC<LiveStreamDetailViewProps> = ({
|
|||
{MOCK_STREAM.title}
|
||||
</h1>
|
||||
<div className="flex items-center gap-4 text-sm">
|
||||
<span className="text-kodo-steel font-bold">
|
||||
<span className="text-muted-foreground font-bold">
|
||||
{MOCK_STREAM.streamer}
|
||||
</span>
|
||||
<span className="flex items-center gap-1 text-destructive font-bold animate-pulse">
|
||||
|
|
@ -164,8 +164,8 @@ export const LiveStreamDetailView: React.FC<LiveStreamDetailViewProps> = ({
|
|||
</div>
|
||||
|
||||
{/* Chat Sidebar */}
|
||||
<div className="w-80 md:w-96 bg-kodo-graphite border-l border-border flex flex-col z-20 shadow-2xl">
|
||||
<div className="p-4 border-b border-border bg-kodo-ink flex justify-between items-center">
|
||||
<div className="w-80 md:w-96 bg-muted border-l border-border flex flex-col z-20 shadow-2xl">
|
||||
<div className="p-4 border-b border-border bg-card flex justify-between items-center">
|
||||
<h3 className="font-bold text-white text-sm">LIVE CHAT</h3>
|
||||
<Settings className="w-4 h-4 text-muted-foreground cursor-pointer hover:text-white" />
|
||||
</div>
|
||||
|
|
@ -178,15 +178,15 @@ export const LiveStreamDetailView: React.FC<LiveStreamDetailViewProps> = ({
|
|||
>
|
||||
{msg.user}:
|
||||
</span>
|
||||
<span className="text-kodo-text-main">{msg.text}</span>
|
||||
<span className="text-foreground">{msg.text}</span>
|
||||
</div>
|
||||
))}
|
||||
</div>
|
||||
|
||||
<div className="p-4 border-t border-border bg-kodo-ink">
|
||||
<div className="p-4 border-t border-border bg-card">
|
||||
<div className="relative">
|
||||
<input
|
||||
className="w-full bg-kodo-void border border-border rounded-full py-2.5 pl-4 pr-10 text-white text-sm focus:border-border outline-none"
|
||||
className="w-full bg-background border border-border rounded-full py-2.5 pl-4 pr-10 text-white text-sm focus:border-border outline-none"
|
||||
placeholder="Send a message..."
|
||||
value={chatInput}
|
||||
onChange={(e) => setChatInput(e.target.value)}
|
||||
|
|
|
|||
|
|
@ -34,11 +34,11 @@ export const TipStreamerModal: React.FC<TipStreamerModalProps> = ({
|
|||
return (
|
||||
<div className="fixed inset-0 z-[100] flex items-center justify-center p-4">
|
||||
<div
|
||||
className="absolute inset-0 bg-kodo-void/90 backdrop-blur-sm"
|
||||
className="absolute inset-0 bg-background/90 backdrop-blur-sm"
|
||||
onClick={onClose}
|
||||
></div>
|
||||
<div className="relative w-full max-w-md bg-kodo-graphite border border-warning rounded-xl shadow-2xl animate-scaleIn overflow-hidden flex flex-col">
|
||||
<div className="p-4 border-b border-warning/30 bg-kodo-ink flex justify-between items-center">
|
||||
<div className="relative w-full max-w-md bg-muted border border-warning rounded-xl shadow-2xl animate-scaleIn overflow-hidden flex flex-col">
|
||||
<div className="p-4 border-b border-warning/30 bg-card flex justify-between items-center">
|
||||
<h3 className="font-bold text-warning flex items-center gap-2">
|
||||
<DollarSign className="w-5 h-5" /> Support {streamerName}
|
||||
</h3>
|
||||
|
|
@ -58,7 +58,7 @@ export const TipStreamerModal: React.FC<TipStreamerModalProps> = ({
|
|||
<button
|
||||
key={val}
|
||||
onClick={() => setAmount(val)}
|
||||
className={`flex-1 py-2 rounded font-bold border transition-colors ${amount === val ? 'bg-warning text-black border-warning' : 'bg-kodo-void border-border text-muted-foreground hover:text-white'}`}
|
||||
className={`flex-1 py-2 rounded font-bold border transition-colors ${amount === val ? 'bg-warning text-black border-warning' : 'bg-background border-border text-muted-foreground hover:text-white'}`}
|
||||
>
|
||||
${val}
|
||||
</button>
|
||||
|
|
@ -70,7 +70,7 @@ export const TipStreamerModal: React.FC<TipStreamerModalProps> = ({
|
|||
</span>
|
||||
<input
|
||||
type="number"
|
||||
className="w-full bg-kodo-ink border border-border rounded pl-8 pr-4 py-2 text-white font-mono focus:border-warning outline-none"
|
||||
className="w-full bg-card border border-border rounded pl-8 pr-4 py-2 text-white font-mono focus:border-warning outline-none"
|
||||
value={amount}
|
||||
onChange={(e) => setAmount(e.target.value)}
|
||||
placeholder="Custom Amount"
|
||||
|
|
@ -84,7 +84,7 @@ export const TipStreamerModal: React.FC<TipStreamerModalProps> = ({
|
|||
Message (Optional)
|
||||
</label>
|
||||
<textarea
|
||||
className="w-full bg-kodo-ink border border-border rounded p-4 text-white focus:border-warning outline-none text-sm resize-none h-24"
|
||||
className="w-full bg-card border border-border rounded p-4 text-white focus:border-warning outline-none text-sm resize-none h-24"
|
||||
placeholder={`Say something nice to ${streamerName}...`}
|
||||
value={message}
|
||||
onChange={(e) => setMessage(e.target.value)}
|
||||
|
|
@ -103,13 +103,13 @@ export const TipStreamerModal: React.FC<TipStreamerModalProps> = ({
|
|||
<div className="flex gap-2">
|
||||
<button
|
||||
onClick={() => setPaymentMethod('card')}
|
||||
className={`flex-1 flex items-center justify-center gap-2 py-2 rounded border ${paymentMethod === 'card' ? 'bg-primary/10 border-primary text-primary' : 'bg-kodo-void border-border text-muted-foreground'}`}
|
||||
className={`flex-1 flex items-center justify-center gap-2 py-2 rounded border ${paymentMethod === 'card' ? 'bg-primary/10 border-primary text-primary' : 'bg-background border-border text-muted-foreground'}`}
|
||||
>
|
||||
<CreditCard className="w-4 h-4" /> Card
|
||||
</button>
|
||||
<button
|
||||
onClick={() => setPaymentMethod('crypto')}
|
||||
className={`flex-1 flex items-center justify-center gap-2 py-2 rounded border ${paymentMethod === 'crypto' ? 'bg-kodo-magenta/10 border-kodo-magenta text-kodo-magenta' : 'bg-kodo-void border-border text-muted-foreground'}`}
|
||||
className={`flex-1 flex items-center justify-center gap-2 py-2 rounded border ${paymentMethod === 'crypto' ? 'bg-destructive/10 border-destructive text-destructive' : 'bg-background border-border text-muted-foreground'}`}
|
||||
>
|
||||
<span className="font-bold">Ξ</span> Crypto
|
||||
</button>
|
||||
|
|
@ -117,7 +117,7 @@ export const TipStreamerModal: React.FC<TipStreamerModalProps> = ({
|
|||
</div>
|
||||
</div>
|
||||
|
||||
<div className="p-4 border-t border-warning/30 bg-kodo-ink flex justify-end gap-4">
|
||||
<div className="p-4 border-t border-warning/30 bg-card flex justify-end gap-4">
|
||||
<Button variant="ghost" onClick={onClose}>
|
||||
Cancel
|
||||
</Button>
|
||||
|
|
|
|||
|
|
@ -31,14 +31,14 @@ export const LicenceCard: React.FC<LicenceCardProps> = ({
|
|||
</span>
|
||||
)}
|
||||
</div>
|
||||
<div className="text-xl font-mono font-bold text-kodo-steel">
|
||||
<div className="text-xl font-mono font-bold text-muted-foreground">
|
||||
${license.price}
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<ul className="space-y-2 mb-6 flex-1">
|
||||
{license.features.slice(0, 3).map((feat, i) => (
|
||||
<li key={i} className="flex items-start gap-2 text-sm text-kodo-text-main">
|
||||
<li key={i} className="flex items-start gap-2 text-sm text-foreground">
|
||||
<Check className="w-4 h-4 text-success flex-shrink-0 mt-0.5" />
|
||||
<span className="leading-snug">{feat}</span>
|
||||
</li>
|
||||
|
|
|
|||
|
|
@ -17,13 +17,13 @@ export const LicenceDetailsModal: React.FC<LicenceDetailsModalProps> = ({
|
|||
return (
|
||||
<div className="fixed inset-0 z-[100] flex items-center justify-center p-4">
|
||||
<div
|
||||
className="absolute inset-0 bg-kodo-void/90 backdrop-blur-sm"
|
||||
className="absolute inset-0 bg-background/90 backdrop-blur-sm"
|
||||
onClick={onClose}
|
||||
></div>
|
||||
<div className="relative w-full max-w-lg bg-kodo-graphite border border-border rounded-xl shadow-2xl animate-scaleIn overflow-hidden flex flex-col max-h-layout-modal-sm">
|
||||
<div className="p-4 border-b border-border bg-kodo-ink flex justify-between items-center">
|
||||
<div className="relative w-full max-w-lg bg-muted border border-border rounded-xl shadow-2xl animate-scaleIn overflow-hidden flex flex-col max-h-layout-modal-sm">
|
||||
<div className="p-4 border-b border-border bg-card flex justify-between items-center">
|
||||
<h3 className="font-bold text-white flex items-center gap-2">
|
||||
<ShieldCheck className="w-5 h-5 text-kodo-steel" /> License Agreement
|
||||
<ShieldCheck className="w-5 h-5 text-muted-foreground" /> License Agreement
|
||||
</h3>
|
||||
<button onClick={onClose}>
|
||||
<X className="w-5 h-5 text-muted-foreground hover:text-white" />
|
||||
|
|
@ -40,7 +40,7 @@ export const LicenceDetailsModal: React.FC<LicenceDetailsModalProps> = ({
|
|||
Review usage rights and restrictions.
|
||||
</p>
|
||||
</div>
|
||||
<div className="text-3xl font-mono font-bold text-kodo-steel">
|
||||
<div className="text-3xl font-mono font-bold text-muted-foreground">
|
||||
${license.price}
|
||||
</div>
|
||||
</div>
|
||||
|
|
@ -54,7 +54,7 @@ export const LicenceDetailsModal: React.FC<LicenceDetailsModalProps> = ({
|
|||
{license.features.map((feat, i) => (
|
||||
<li
|
||||
key={i}
|
||||
className="flex items-start gap-4 text-sm text-kodo-text-main"
|
||||
className="flex items-start gap-4 text-sm text-foreground"
|
||||
>
|
||||
<div className="mt-0.5 bg-success/10 p-0.5 rounded-full">
|
||||
<Check className="w-3 h-3 text-success" />
|
||||
|
|
@ -102,7 +102,7 @@ export const LicenceDetailsModal: React.FC<LicenceDetailsModalProps> = ({
|
|||
</div>
|
||||
</div>
|
||||
|
||||
<div className="p-4 border-t border-border bg-kodo-ink flex justify-end gap-4">
|
||||
<div className="p-4 border-t border-border bg-card flex justify-end gap-4">
|
||||
<Button variant="ghost" onClick={onClose}>
|
||||
Close
|
||||
</Button>
|
||||
|
|
|
|||
|
|
@ -69,7 +69,7 @@ export const ReviewProductModal: React.FC<ReviewProductModalProps> = ({
|
|||
<Star
|
||||
className={`w-8 h-8 transition-colors ${
|
||||
star <= (hoverRating || rating)
|
||||
? 'fill-kodo-gold text-warning'
|
||||
? 'fill-warning text-warning'
|
||||
: 'text-muted-foreground'
|
||||
}`}
|
||||
/>
|
||||
|
|
|
|||
|
|
@ -32,17 +32,17 @@ export const CreatorModal: React.FC<CreatorModalProps> = ({
|
|||
return (
|
||||
<div className="fixed inset-0 z-[100] flex items-center justify-center p-4">
|
||||
<div
|
||||
className="absolute inset-0 bg-kodo-void/90 backdrop-blur-sm"
|
||||
className="absolute inset-0 bg-background/90 backdrop-blur-sm"
|
||||
onClick={onClose}
|
||||
></div>
|
||||
<div className="relative w-full max-w-4xl bg-kodo-graphite border border-border rounded-2xl shadow-2xl animate-scaleIn overflow-hidden flex flex-col max-h-layout-modal-lg">
|
||||
<div className="relative w-full max-w-4xl bg-muted border border-border rounded-2xl shadow-2xl animate-scaleIn overflow-hidden flex flex-col max-h-layout-modal-lg">
|
||||
{/* Header */}
|
||||
<div className="flex justify-between items-center p-8 border-b border-border bg-kodo-ink">
|
||||
<div className="flex justify-between items-center p-8 border-b border-border bg-card">
|
||||
<div className="flex items-center gap-4">
|
||||
<h2 className="text-2xl font-heading font-bold text-white">
|
||||
CREATOR STUDIO
|
||||
</h2>
|
||||
<div className="flex bg-kodo-slate rounded-lg p-1">
|
||||
<div className="flex bg-muted rounded-lg p-1">
|
||||
<button
|
||||
onClick={() => setActiveTab('track')}
|
||||
className={`px-4 py-1.5 rounded text-sm font-bold transition-all flex items-center gap-2 ${activeTab === 'track' ? 'bg-primary text-black' : 'text-muted-foreground hover:text-white'}`}
|
||||
|
|
@ -51,7 +51,7 @@ export const CreatorModal: React.FC<CreatorModalProps> = ({
|
|||
</button>
|
||||
<button
|
||||
onClick={() => setActiveTab('product')}
|
||||
className={`px-4 py-1.5 rounded text-sm font-bold transition-all flex items-center gap-2 ${activeTab === 'product' ? 'bg-kodo-magenta text-white' : 'text-muted-foreground hover:text-white'}`}
|
||||
className={`px-4 py-1.5 rounded text-sm font-bold transition-all flex items-center gap-2 ${activeTab === 'product' ? 'bg-destructive text-white' : 'text-muted-foreground hover:text-white'}`}
|
||||
>
|
||||
<Package className="w-4 h-4" /> Product
|
||||
</button>
|
||||
|
|
@ -76,7 +76,7 @@ export const CreatorModal: React.FC<CreatorModalProps> = ({
|
|||
{[1, 2, 3].map((i) => (
|
||||
<div
|
||||
key={i}
|
||||
className={`w-8 h-8 rounded-full flex items-center justify-center font-bold text-sm transition-colors ${step >= i ? 'bg-primary text-black' : 'bg-kodo-slate text-muted-foreground'}`}
|
||||
className={`w-8 h-8 rounded-full flex items-center justify-center font-bold text-sm transition-colors ${step >= i ? 'bg-primary text-black' : 'bg-muted text-muted-foreground'}`}
|
||||
>
|
||||
{step > i ? <CheckCircle className="w-5 h-5" /> : i}
|
||||
</div>
|
||||
|
|
@ -87,7 +87,7 @@ export const CreatorModal: React.FC<CreatorModalProps> = ({
|
|||
<div className="grid grid-cols-1 md:grid-cols-2 gap-8">
|
||||
<div className="space-y-6">
|
||||
<FileUpload />
|
||||
<div className="bg-kodo-slate p-4 rounded-lg border border-border">
|
||||
<div className="bg-muted p-4 rounded-lg border border-border">
|
||||
<h4 className="font-bold text-muted-foreground text-sm mb-2 uppercase">
|
||||
File Requirements
|
||||
</h4>
|
||||
|
|
@ -110,7 +110,7 @@ export const CreatorModal: React.FC<CreatorModalProps> = ({
|
|||
Visibility
|
||||
</label>
|
||||
<div className="grid grid-cols-3 gap-2">
|
||||
<Button variant="outline" className="p-4 flex flex-col items-center justify-center gap-2 text-kodo-steel bg-muted/10 border-border">
|
||||
<Button variant="outline" className="p-4 flex flex-col items-center justify-center gap-2 text-muted-foreground bg-muted/10 border-border">
|
||||
<Tag className="w-5 h-5" />{' '}
|
||||
<span className="text-xs font-bold">Public</span>
|
||||
</Button>
|
||||
|
|
@ -142,9 +142,9 @@ export const CreatorModal: React.FC<CreatorModalProps> = ({
|
|||
<Card
|
||||
key={type}
|
||||
variant="default"
|
||||
className="hover:border-kodo-magenta cursor-pointer group"
|
||||
className="hover:border-destructive cursor-pointer group"
|
||||
>
|
||||
<Package className="w-8 h-8 text-kodo-magenta mb-4 transition-opacity group-hover:opacity-80" />
|
||||
<Package className="w-8 h-8 text-destructive mb-4 transition-opacity group-hover:opacity-80" />
|
||||
<h4 className="font-bold">{type}</h4>
|
||||
</Card>
|
||||
),
|
||||
|
|
@ -155,7 +155,7 @@ export const CreatorModal: React.FC<CreatorModalProps> = ({
|
|||
</div>
|
||||
|
||||
{/* Footer */}
|
||||
<div className="p-8 border-t border-border bg-kodo-ink flex justify-end gap-4">
|
||||
<div className="p-8 border-t border-border bg-card flex justify-end gap-4">
|
||||
<Button variant="ghost" onClick={onClose}>
|
||||
CANCEL
|
||||
</Button>
|
||||
|
|
|
|||
|
|
@ -40,18 +40,18 @@ export const NotificationBell: React.FC<NotificationBellProps> = ({
|
|||
<Button
|
||||
variant="ghost"
|
||||
size="sm"
|
||||
className={`relative text-muted-foreground hover:text-kodo-primary ${isOpen ? 'text-kodo-primary bg-white/5' : ''}`}
|
||||
className={`relative text-muted-foreground hover:text-primary ${isOpen ? 'text-primary bg-white/5' : ''}`}
|
||||
onClick={() => setIsOpen(!isOpen)}
|
||||
>
|
||||
<Bell className="w-5 h-5" />
|
||||
{unreadCount > 0 && (
|
||||
<span className="absolute top-1.5 right-2 w-2 h-2 bg-kodo-red rounded-full border-2 border-kodo-void animate-pulse"></span>
|
||||
<span className="absolute top-1.5 right-2 w-2 h-2 bg-destructive rounded-full border-2 border-border animate-pulse"></span>
|
||||
)}
|
||||
</Button>
|
||||
|
||||
{isOpen && (
|
||||
<div className="absolute top-full right-0 mt-4 w-96 bg-kodo-graphite border border-border rounded-xl shadow-2xl overflow-hidden animate-fadeIn origin-top-right ring-1 ring-white/5 flex flex-col max-h-layout-modal-sm">
|
||||
<div className="p-4 border-b border-border/50 flex justify-between items-center bg-kodo-ink">
|
||||
<div className="absolute top-full right-0 mt-4 w-96 bg-muted border border-border rounded-xl shadow-2xl overflow-hidden animate-fadeIn origin-top-right ring-1 ring-white/5 flex flex-col max-h-layout-modal-sm">
|
||||
<div className="p-4 border-b border-border/50 flex justify-between items-center bg-card">
|
||||
<div>
|
||||
<h3 className="font-bold text-white">Notifications</h3>
|
||||
<p className="text-xs text-muted-foreground">{unreadCount} unread</p>
|
||||
|
|
@ -59,7 +59,7 @@ export const NotificationBell: React.FC<NotificationBellProps> = ({
|
|||
{unreadCount > 0 && (
|
||||
<button
|
||||
onClick={onMarkAllRead}
|
||||
className="text-xs text-kodo-steel hover:underline flex items-center gap-1"
|
||||
className="text-xs text-muted-foreground hover:underline flex items-center gap-1"
|
||||
>
|
||||
<Check className="w-3 h-3" /> Mark all read
|
||||
</button>
|
||||
|
|
@ -87,7 +87,7 @@ export const NotificationBell: React.FC<NotificationBellProps> = ({
|
|||
)}
|
||||
</div>
|
||||
|
||||
<div className="p-2 border-t border-border/30 bg-kodo-ink/50">
|
||||
<div className="p-2 border-t border-border/30 bg-card/50">
|
||||
<Button
|
||||
variant="ghost"
|
||||
size="sm"
|
||||
|
|
|
|||
|
|
@ -26,9 +26,9 @@ export const NotificationItem: React.FC<NotificationItemProps> = ({
|
|||
const getIcon = () => {
|
||||
switch (notification.type) {
|
||||
case 'like':
|
||||
return <Heart className="w-4 h-4 text-kodo-magenta fill-current" />;
|
||||
return <Heart className="w-4 h-4 text-destructive fill-current" />;
|
||||
case 'follow':
|
||||
return <UserPlus className="w-4 h-4 text-kodo-steel" />;
|
||||
return <UserPlus className="w-4 h-4 text-muted-foreground" />;
|
||||
case 'mention':
|
||||
return <MessageSquare className="w-4 h-4 text-warning" />;
|
||||
case 'sale':
|
||||
|
|
@ -44,11 +44,11 @@ export const NotificationItem: React.FC<NotificationItemProps> = ({
|
|||
if (notification.read) return 'bg-transparent';
|
||||
switch (notification.type) {
|
||||
case 'sale':
|
||||
return 'bg-success/5 border-l-2 border-l-kodo-lime';
|
||||
return 'bg-success/5 border-l-2 border-l-success';
|
||||
case 'security':
|
||||
return 'bg-destructive/5 border-l-2 border-l-kodo-red';
|
||||
return 'bg-destructive/5 border-l-2 border-l-destructive';
|
||||
default:
|
||||
return 'bg-primary/5 border-l-2 border-l-kodo-cyan';
|
||||
return 'bg-primary/5 border-l-2 border-l-primary';
|
||||
}
|
||||
};
|
||||
|
||||
|
|
@ -56,12 +56,12 @@ export const NotificationItem: React.FC<NotificationItemProps> = ({
|
|||
<div
|
||||
className={`p-4 rounded-lg flex items-start gap-4 transition-all hover:bg-white/5 group border border-transparent ${getBgColor()}`}
|
||||
>
|
||||
<div className="flex-shrink-0 mt-1 p-2 bg-kodo-graphite rounded-full border border-border shadow-sm">
|
||||
<div className="flex-shrink-0 mt-1 p-2 bg-muted rounded-full border border-border shadow-sm">
|
||||
{getIcon()}
|
||||
</div>
|
||||
|
||||
<div className="flex-1 min-w-0">
|
||||
<p className="text-sm text-kodo-text-main leading-relaxed">
|
||||
<p className="text-sm text-foreground leading-relaxed">
|
||||
{notification.message}
|
||||
</p>
|
||||
<span className="text-xs text-muted-foreground font-mono mt-1 block">
|
||||
|
|
@ -74,7 +74,7 @@ export const NotificationItem: React.FC<NotificationItemProps> = ({
|
|||
<Tooltip content="Mark as read">
|
||||
<button
|
||||
onClick={() => onRead(notification.id)}
|
||||
className="p-1.5 hover:bg-white/10 rounded-full text-kodo-steel"
|
||||
className="p-1.5 hover:bg-white/10 rounded-full text-muted-foreground"
|
||||
>
|
||||
<Circle className="w-3 h-3 fill-current" />
|
||||
</button>
|
||||
|
|
|
|||
|
|
@ -22,14 +22,14 @@ export function PWAInstallBanner() {
|
|||
<div
|
||||
className={cn(
|
||||
'fixed bottom-8 right-8 z-50 w-80 glass-hud rounded-2xl border-white/10 p-6 shadow-2xl animate-slideInRight hud-corner group overflow-hidden',
|
||||
'before:absolute before:inset-0 before:bg-gradient-to-br before:from-kodo-cyan/5 before:to-transparent before:opacity-0 group-hover:before:opacity-100 before:transition-opacity',
|
||||
'before:absolute before:inset-0 before:bg-gradient-to-br before:from-primary/5 before:to-transparent before:opacity-0 group-hover:before:opacity-100 before:transition-opacity',
|
||||
)}
|
||||
>
|
||||
<div className="flex flex-col gap-4 relative z-10">
|
||||
<div className="flex items-center justify-between">
|
||||
<div className="flex items-center gap-2.5">
|
||||
<div className="w-8 h-8 rounded-lg bg-muted/10 flex items-center justify-center border border-border/30 animate-pulse-glow">
|
||||
<Smartphone className="h-4 w-4 text-kodo-steel" />
|
||||
<Smartphone className="h-4 w-4 text-muted-foreground" />
|
||||
</div>
|
||||
<div>
|
||||
<div className="text-hud">System.Uplink</div>
|
||||
|
|
|
|||
|
|
@ -92,7 +92,7 @@ export const SearchBar: React.FC<SearchBarProps> = ({
|
|||
<div ref={wrapperRef} className={`relative w-full ${className}`}>
|
||||
<form onSubmit={handleSubmit} className="relative z-20">
|
||||
<div
|
||||
className={`flex items-center bg-kodo-ink border rounded-xl px-4 py-4 transition-all ${isFocused ? 'border-primary ring-1 ring-kodo-cyan/20' : 'border-border'}`}
|
||||
className={`flex items-center bg-card border rounded-xl px-4 py-4 transition-all ${isFocused ? 'border-primary ring-1 ring-primary/20' : 'border-border'}`}
|
||||
>
|
||||
<Search
|
||||
className={`w-5 h-5 mr-3 transition-colors ${isFocused ? 'text-primary' : 'text-muted-foreground'}`}
|
||||
|
|
@ -118,7 +118,7 @@ export const SearchBar: React.FC<SearchBarProps> = ({
|
|||
</form>
|
||||
|
||||
{isFocused && (
|
||||
<div className="absolute top-full left-0 right-0 mt-2 bg-kodo-graphite border border-border rounded-xl shadow-2xl z-50 overflow-hidden animate-slideUp">
|
||||
<div className="absolute top-full left-0 right-0 mt-2 bg-muted border border-border rounded-xl shadow-2xl z-50 overflow-hidden animate-slideUp">
|
||||
{query ? (
|
||||
<div>
|
||||
{filteredSuggestions.length > 0 ? (
|
||||
|
|
@ -132,7 +132,7 @@ export const SearchBar: React.FC<SearchBarProps> = ({
|
|||
className="px-4 py-2 hover:bg-white/5 cursor-pointer flex items-center gap-4 transition-colors"
|
||||
onClick={() => handleSuggestionClick(item.label)}
|
||||
>
|
||||
<div className="w-8 h-8 rounded bg-kodo-slate flex items-center justify-center text-muted-foreground">
|
||||
<div className="w-8 h-8 rounded bg-muted flex items-center justify-center text-muted-foreground">
|
||||
{getIcon(item.type)}
|
||||
</div>
|
||||
<div>
|
||||
|
|
@ -171,7 +171,7 @@ export const SearchBar: React.FC<SearchBarProps> = ({
|
|||
className="px-4 py-2 hover:bg-white/5 cursor-pointer flex items-center justify-between group transition-colors"
|
||||
onClick={() => handleSuggestionClick(term)}
|
||||
>
|
||||
<div className="flex items-center gap-4 text-kodo-text-main group-hover:text-white">
|
||||
<div className="flex items-center gap-4 text-foreground group-hover:text-white">
|
||||
<Clock className="w-4 h-4 text-muted-foreground" />
|
||||
<span className="text-sm">{term}</span>
|
||||
</div>
|
||||
|
|
|
|||
|
|
@ -66,7 +66,7 @@ export const SellerDashboardView: React.FC<SellerDashboardProps> = ({
|
|||
if (loading)
|
||||
return (
|
||||
<div className="flex justify-center py-24">
|
||||
<Loader2 className="w-10 h-10 text-kodo-steel animate-spin" />
|
||||
<Loader2 className="w-10 h-10 text-muted-foreground animate-spin" />
|
||||
</div>
|
||||
);
|
||||
|
||||
|
|
@ -168,7 +168,7 @@ export const SellerDashboardView: React.FC<SellerDashboardProps> = ({
|
|||
|
||||
<Card variant="default" className="p-6 relative overflow-hidden group">
|
||||
<div className="absolute right-0 top-0 p-4 opacity-10 group-hover:opacity-20 transition-opacity">
|
||||
<Package className="w-16 h-16 text-kodo-steel" />
|
||||
<Package className="w-16 h-16 text-muted-foreground" />
|
||||
</div>
|
||||
<div className="text-muted-foreground text-xs font-bold uppercase mb-1">
|
||||
Total Sales
|
||||
|
|
@ -183,7 +183,7 @@ export const SellerDashboardView: React.FC<SellerDashboardProps> = ({
|
|||
|
||||
<Card variant="default" className="p-6 relative overflow-hidden group">
|
||||
<div className="absolute right-0 top-0 p-4 opacity-10 group-hover:opacity-20 transition-opacity">
|
||||
<Eye className="w-16 h-16 text-kodo-magenta" />
|
||||
<Eye className="w-16 h-16 text-destructive" />
|
||||
</div>
|
||||
<div className="text-muted-foreground text-xs font-bold uppercase mb-1">
|
||||
Page Views
|
||||
|
|
@ -228,7 +228,7 @@ export const SellerDashboardView: React.FC<SellerDashboardProps> = ({
|
|||
{products.map((product, i) => (
|
||||
<div
|
||||
key={product.id}
|
||||
className="flex items-center gap-4 p-4 bg-kodo-ink rounded-lg border border-transparent hover:border-border transition-all"
|
||||
className="flex items-center gap-4 p-4 bg-card rounded-lg border border-transparent hover:border-border transition-all"
|
||||
>
|
||||
<div className="w-8 text-center font-mono text-muted-foreground">
|
||||
{i + 1}
|
||||
|
|
@ -247,7 +247,7 @@ export const SellerDashboardView: React.FC<SellerDashboardProps> = ({
|
|||
</div>
|
||||
<div className="text-right">
|
||||
<div className="font-bold text-foreground">${product.price}</div>
|
||||
<div className="text-xs text-kodo-steel">
|
||||
<div className="text-xs text-muted-foreground">
|
||||
{Math.floor(Math.random() * 100)} sales
|
||||
</div>
|
||||
</div>
|
||||
|
|
@ -268,7 +268,7 @@ export const SellerDashboardView: React.FC<SellerDashboardProps> = ({
|
|||
<div className="absolute left-2.5 top-2 bottom-2 w-px bg-muted"></div>
|
||||
{sales.map((sale) => (
|
||||
<div key={sale.id} className="relative pl-8">
|
||||
<div className="absolute left-0 top-1.5 w-5 h-5 bg-kodo-graphite border border-success rounded-full flex items-center justify-center">
|
||||
<div className="absolute left-0 top-1.5 w-5 h-5 bg-muted border border-success rounded-full flex items-center justify-center">
|
||||
<div className="w-2 h-2 bg-success rounded-full"></div>
|
||||
</div>
|
||||
<div className="text-sm text-foreground font-bold">
|
||||
|
|
|
|||
|
|
@ -38,11 +38,11 @@ export const FlashSaleModal: React.FC<FlashSaleModalProps> = ({
|
|||
return (
|
||||
<div className="fixed inset-0 z-[100] flex items-center justify-center p-4">
|
||||
<div
|
||||
className="absolute inset-0 bg-kodo-void/90 backdrop-blur-sm"
|
||||
className="absolute inset-0 bg-background/90 backdrop-blur-sm"
|
||||
onClick={onClose}
|
||||
></div>
|
||||
<div className="relative w-full max-w-2xl bg-kodo-graphite border border-border rounded-xl shadow-2xl animate-scaleIn overflow-hidden flex flex-col max-h-layout-modal">
|
||||
<div className="p-4 border-b border-border bg-kodo-ink flex justify-between items-center">
|
||||
<div className="relative w-full max-w-2xl bg-muted border border-border rounded-xl shadow-2xl animate-scaleIn overflow-hidden flex flex-col max-h-layout-modal">
|
||||
<div className="p-4 border-b border-border bg-card flex justify-between items-center">
|
||||
<h3 className="font-bold text-white flex items-center gap-2">
|
||||
<Zap className="w-5 h-5 text-warning" /> Start Flash Sale
|
||||
</h3>
|
||||
|
|
@ -62,7 +62,7 @@ export const FlashSaleModal: React.FC<FlashSaleModalProps> = ({
|
|||
<Percent className="absolute left-3 top-1/2 -translate-y-1/2 w-4 h-4 text-muted-foreground" />
|
||||
<input
|
||||
type="number"
|
||||
className="w-full bg-kodo-void border border-border rounded pl-10 pr-4 py-2 text-white focus:border-warning outline-none"
|
||||
className="w-full bg-background border border-border rounded pl-10 pr-4 py-2 text-white focus:border-warning outline-none"
|
||||
value={discount}
|
||||
onChange={(e) => setDiscount(Number(e.target.value))}
|
||||
min={5}
|
||||
|
|
@ -78,7 +78,7 @@ export const FlashSaleModal: React.FC<FlashSaleModalProps> = ({
|
|||
<div className="relative">
|
||||
<Calendar className="absolute left-3 top-1/2 -translate-y-1/2 w-4 h-4 text-muted-foreground" />
|
||||
<select
|
||||
className="w-full bg-kodo-void border border-border rounded pl-10 pr-4 py-2 text-white focus:border-warning outline-none appearance-none"
|
||||
className="w-full bg-background border border-border rounded pl-10 pr-4 py-2 text-white focus:border-warning outline-none appearance-none"
|
||||
value={duration}
|
||||
onChange={(e) => setDuration(Number(e.target.value))}
|
||||
>
|
||||
|
|
@ -96,7 +96,7 @@ export const FlashSaleModal: React.FC<FlashSaleModalProps> = ({
|
|||
<h4 className="text-warning font-bold text-sm mb-1">
|
||||
Impact Summary
|
||||
</h4>
|
||||
<p className="text-xs text-kodo-text-main">
|
||||
<p className="text-xs text-foreground">
|
||||
Applying a{' '}
|
||||
<span className="font-bold text-white">{discount}%</span>{' '}
|
||||
discount to{' '}
|
||||
|
|
@ -130,11 +130,11 @@ export const FlashSaleModal: React.FC<FlashSaleModalProps> = ({
|
|||
</button>
|
||||
</div>
|
||||
|
||||
<div className="flex-1 overflow-y-auto custom-scrollbar border border-border rounded-lg bg-kodo-void p-2 space-y-1">
|
||||
<div className="flex-1 overflow-y-auto custom-scrollbar border border-border rounded-lg bg-background p-2 space-y-1">
|
||||
{products.map((product) => (
|
||||
<div
|
||||
key={product.id}
|
||||
className={`flex items-center gap-4 p-2 rounded cursor-pointer transition-colors ${selectedIds.includes(product.id) ? 'bg-warning/10 border border-warning/30' : 'hover:bg-kodo-ink border border-transparent'}`}
|
||||
className={`flex items-center gap-4 p-2 rounded cursor-pointer transition-colors ${selectedIds.includes(product.id) ? 'bg-warning/10 border border-warning/30' : 'hover:bg-card border border-transparent'}`}
|
||||
onClick={() => toggleProduct(product.id)}
|
||||
>
|
||||
<div
|
||||
|
|
@ -164,7 +164,7 @@ export const FlashSaleModal: React.FC<FlashSaleModalProps> = ({
|
|||
</div>
|
||||
</div>
|
||||
|
||||
<div className="p-4 border-t border-border bg-kodo-ink flex justify-end gap-4">
|
||||
<div className="p-4 border-t border-border bg-card flex justify-end gap-4">
|
||||
<Button variant="ghost" onClick={onClose}>
|
||||
Cancel
|
||||
</Button>
|
||||
|
|
|
|||
|
|
@ -75,7 +75,7 @@ export const AccessibilitySettingsView: React.FC = () => {
|
|||
{/* Typography & Input */}
|
||||
<Card variant="default">
|
||||
<h3 className="text-lg font-bold text-foreground mb-6 flex items-center gap-2">
|
||||
<Type className="w-5 h-5 text-kodo-magenta" /> Text & Input
|
||||
<Type className="w-5 h-5 text-destructive" /> Text & Input
|
||||
</h3>
|
||||
<div className="space-y-4">
|
||||
<ToggleRow
|
||||
|
|
|
|||
|
|
@ -35,11 +35,11 @@ export const ChangeEmailModal: React.FC<ChangeEmailModalProps> = ({
|
|||
return (
|
||||
<div className="fixed inset-0 z-50 flex items-center justify-center p-4">
|
||||
<div
|
||||
className="absolute inset-0 bg-kodo-void/90 backdrop-blur-sm"
|
||||
className="absolute inset-0 bg-background/90 backdrop-blur-sm"
|
||||
onClick={onClose}
|
||||
></div>
|
||||
<div className="relative w-full max-w-md bg-kodo-graphite border border-border rounded-xl shadow-2xl animate-scaleIn overflow-hidden">
|
||||
<div className="p-4 border-b border-border bg-kodo-ink flex justify-between items-center">
|
||||
<div className="relative w-full max-w-md bg-muted border border-border rounded-xl shadow-2xl animate-scaleIn overflow-hidden">
|
||||
<div className="p-4 border-b border-border bg-card flex justify-between items-center">
|
||||
<h3 className="font-bold text-foreground">Change Email Address</h3>
|
||||
<button onClick={onClose}>
|
||||
<X className="w-5 h-5 text-muted-foreground hover:text-white" />
|
||||
|
|
@ -70,14 +70,14 @@ export const ChangeEmailModal: React.FC<ChangeEmailModalProps> = ({
|
|||
onChange={(e) => setPassword(e.target.value)}
|
||||
/>
|
||||
|
||||
<div className="bg-kodo-ink p-4 rounded text-xs text-muted-foreground border border-border">
|
||||
<div className="bg-card p-4 rounded text-xs text-muted-foreground border border-border">
|
||||
We will send a verification link to your new email address. You
|
||||
must verify it before the change takes effect.
|
||||
</div>
|
||||
</div>
|
||||
) : (
|
||||
<div className="text-center py-4">
|
||||
<div className="w-16 h-16 bg-muted/20 rounded-full flex items-center justify-center mx-auto mb-4 text-kodo-steel">
|
||||
<div className="w-16 h-16 bg-muted/20 rounded-full flex items-center justify-center mx-auto mb-4 text-muted-foreground">
|
||||
<Mail className="w-8 h-8" />
|
||||
</div>
|
||||
<h4 className="text-lg font-bold text-foreground mb-2">
|
||||
|
|
@ -95,7 +95,7 @@ export const ChangeEmailModal: React.FC<ChangeEmailModalProps> = ({
|
|||
</div>
|
||||
|
||||
{step === 1 && (
|
||||
<div className="p-4 border-t border-border bg-kodo-ink flex justify-end gap-4">
|
||||
<div className="p-4 border-t border-border bg-card flex justify-end gap-4">
|
||||
<Button variant="ghost" onClick={onClose}>
|
||||
Cancel
|
||||
</Button>
|
||||
|
|
|
|||
|
|
@ -32,10 +32,10 @@ export const DeleteAccountConfirmModal: React.FC<
|
|||
return (
|
||||
<div className="fixed inset-0 z-[60] flex items-center justify-center p-4">
|
||||
<div
|
||||
className="absolute inset-0 bg-kodo-void/90 backdrop-blur-sm"
|
||||
className="absolute inset-0 bg-background/90 backdrop-blur-sm"
|
||||
onClick={loading ? undefined : onClose}
|
||||
></div>
|
||||
<div className="relative w-full max-w-md bg-kodo-graphite border border-destructive rounded-xl shadow-2xl overflow-hidden animate-scaleIn">
|
||||
<div className="relative w-full max-w-md bg-muted border border-destructive rounded-xl shadow-2xl overflow-hidden animate-scaleIn">
|
||||
<div className="p-4 border-b border-destructive/30 bg-destructive/10 flex justify-between items-center">
|
||||
<h3 className="font-bold text-destructive flex items-center gap-2">
|
||||
<AlertTriangle className="w-5 h-5 fill-current" /> PERMANENT
|
||||
|
|
@ -51,12 +51,12 @@ export const DeleteAccountConfirmModal: React.FC<
|
|||
</div>
|
||||
|
||||
<div className="p-6 space-y-4">
|
||||
<p className="text-kodo-text-main text-sm">
|
||||
<p className="text-foreground text-sm">
|
||||
This is the final step. Once you click delete, your account will be
|
||||
queued for immediate removal. You will be logged out.
|
||||
</p>
|
||||
|
||||
<div className="bg-kodo-ink p-4 rounded border border-border">
|
||||
<div className="bg-card p-4 rounded border border-border">
|
||||
<ul className="text-xs text-muted-foreground space-y-2 list-disc pl-4">
|
||||
<li>All uploaded tracks and assets will be deleted.</li>
|
||||
<li>Your username will be released.</li>
|
||||
|
|
@ -78,7 +78,7 @@ export const DeleteAccountConfirmModal: React.FC<
|
|||
</div>
|
||||
</div>
|
||||
|
||||
<div className="p-4 border-t border-border bg-kodo-ink flex justify-end gap-4">
|
||||
<div className="p-4 border-t border-border bg-card flex justify-end gap-4">
|
||||
<Button variant="ghost" onClick={onClose} disabled={loading}>
|
||||
Cancel
|
||||
</Button>
|
||||
|
|
|
|||
|
|
@ -69,17 +69,17 @@ export const DeleteAccountView: React.FC<DeleteAccountViewProps> = ({
|
|||
</div>
|
||||
|
||||
<div className="space-y-4 mb-8">
|
||||
<label className="flex items-start gap-4 p-4 bg-kodo-ink rounded border border-border cursor-pointer hover:border-border transition-colors">
|
||||
<label className="flex items-start gap-4 p-4 bg-card rounded border border-border cursor-pointer hover:border-border transition-colors">
|
||||
<input
|
||||
type="checkbox"
|
||||
className="mt-1 bg-kodo-graphite border-border text-destructive focus:ring-kodo-red rounded"
|
||||
className="mt-1 bg-muted border-border text-destructive focus:ring-destructive rounded"
|
||||
checked={checks.dataLoss}
|
||||
onChange={(e) =>
|
||||
setChecks({ ...checks, dataLoss: e.target.checked })
|
||||
}
|
||||
/>
|
||||
<div className="text-sm">
|
||||
<span className="font-bold text-kodo-text-main block mb-1">
|
||||
<span className="font-bold text-foreground block mb-1">
|
||||
I lose all my data
|
||||
</span>
|
||||
<span className="text-muted-foreground">
|
||||
|
|
@ -89,17 +89,17 @@ export const DeleteAccountView: React.FC<DeleteAccountViewProps> = ({
|
|||
</div>
|
||||
</label>
|
||||
|
||||
<label className="flex items-start gap-4 p-4 bg-kodo-ink rounded border border-border cursor-pointer hover:border-border transition-colors">
|
||||
<label className="flex items-start gap-4 p-4 bg-card rounded border border-border cursor-pointer hover:border-border transition-colors">
|
||||
<input
|
||||
type="checkbox"
|
||||
className="mt-1 bg-kodo-graphite border-border text-destructive focus:ring-kodo-red rounded"
|
||||
className="mt-1 bg-muted border-border text-destructive focus:ring-destructive rounded"
|
||||
checked={checks.irreversible}
|
||||
onChange={(e) =>
|
||||
setChecks({ ...checks, irreversible: e.target.checked })
|
||||
}
|
||||
/>
|
||||
<div className="text-sm">
|
||||
<span className="font-bold text-kodo-text-main block mb-1">
|
||||
<span className="font-bold text-foreground block mb-1">
|
||||
This action is irreversible
|
||||
</span>
|
||||
<span className="text-muted-foreground">
|
||||
|
|
@ -109,17 +109,17 @@ export const DeleteAccountView: React.FC<DeleteAccountViewProps> = ({
|
|||
</div>
|
||||
</label>
|
||||
|
||||
<label className="flex items-start gap-4 p-4 bg-kodo-ink rounded border border-border cursor-pointer hover:border-border transition-colors">
|
||||
<label className="flex items-start gap-4 p-4 bg-card rounded border border-border cursor-pointer hover:border-border transition-colors">
|
||||
<input
|
||||
type="checkbox"
|
||||
className="mt-1 bg-kodo-graphite border-border text-destructive focus:ring-kodo-red rounded"
|
||||
className="mt-1 bg-muted border-border text-destructive focus:ring-destructive rounded"
|
||||
checked={checks.subscription}
|
||||
onChange={(e) =>
|
||||
setChecks({ ...checks, subscription: e.target.checked })
|
||||
}
|
||||
/>
|
||||
<div className="text-sm">
|
||||
<span className="font-bold text-kodo-text-main block mb-1">
|
||||
<span className="font-bold text-foreground block mb-1">
|
||||
Subscriptions will be cancelled
|
||||
</span>
|
||||
<span className="text-muted-foreground">
|
||||
|
|
@ -140,7 +140,7 @@ export const DeleteAccountView: React.FC<DeleteAccountViewProps> = ({
|
|||
placeholder="DELETE"
|
||||
value={confirmText}
|
||||
onChange={(e) => setConfirmText(e.target.value)}
|
||||
className="border-destructive/50 focus:border-destructive focus:ring-kodo-red"
|
||||
className="border-destructive/50 focus:border-destructive focus:ring-destructive"
|
||||
/>
|
||||
</div>
|
||||
|
||||
|
|
|
|||
|
|
@ -118,7 +118,7 @@ export const AppearanceSettingsView: React.FC = () => {
|
|||
<div className="grid grid-cols-1 md:grid-cols-2 gap-8">
|
||||
<Card variant="default">
|
||||
<h3 className="text-lg font-bold text-foreground mb-6 flex items-center gap-2">
|
||||
<Grid className="w-5 h-5 text-kodo-magenta" /> Density
|
||||
<Grid className="w-5 h-5 text-destructive" /> Density
|
||||
</h3>
|
||||
<div className="space-y-4">
|
||||
{[
|
||||
|
|
@ -139,10 +139,10 @@ export const AppearanceSettingsView: React.FC = () => {
|
|||
`}
|
||||
>
|
||||
<div
|
||||
className={`w-4 h-4 rounded-full border-2 flex items-center justify-center ${density === opt.id ? 'border-kodo-magenta' : 'border-border'}`}
|
||||
className={`w-4 h-4 rounded-full border-2 flex items-center justify-center ${density === opt.id ? 'border-destructive' : 'border-border'}`}
|
||||
>
|
||||
{density === opt.id && (
|
||||
<div className="w-2 h-2 rounded-full bg-kodo-magenta"></div>
|
||||
<div className="w-2 h-2 rounded-full bg-destructive"></div>
|
||||
)}
|
||||
</div>
|
||||
<div>
|
||||
|
|
|
|||
|
|
@ -26,7 +26,7 @@ export const CloudIntegrationView: React.FC = () => {
|
|||
return (
|
||||
<div className="max-w-4xl mx-auto space-y-8 animate-fadeIn">
|
||||
{/* Connection Status */}
|
||||
<Card variant="default" className="border-t-4 border-t-kodo-cyan">
|
||||
<Card variant="default" className="border-t-4 border-t-primary">
|
||||
<div className="flex flex-col md:flex-row justify-between items-start md:items-center gap-6">
|
||||
<div className="flex items-center gap-4">
|
||||
<div
|
||||
|
|
|
|||
|
|
@ -34,13 +34,13 @@ export const DataExportModal: React.FC<DataExportModalProps> = ({
|
|||
return (
|
||||
<div className="fixed inset-0 z-[100] flex items-center justify-center p-4">
|
||||
<div
|
||||
className="absolute inset-0 bg-kodo-void/90 backdrop-blur-sm"
|
||||
className="absolute inset-0 bg-background/90 backdrop-blur-sm"
|
||||
onClick={onClose}
|
||||
></div>
|
||||
<div className="relative w-full max-w-md bg-kodo-graphite border border-border rounded-xl shadow-2xl animate-scaleIn overflow-hidden">
|
||||
<div className="p-4 border-b border-border bg-kodo-ink flex justify-between items-center">
|
||||
<div className="relative w-full max-w-md bg-muted border border-border rounded-xl shadow-2xl animate-scaleIn overflow-hidden">
|
||||
<div className="p-4 border-b border-border bg-card flex justify-between items-center">
|
||||
<h3 className="font-bold text-foreground flex items-center gap-2">
|
||||
<Database className="w-4 h-4 text-kodo-steel" /> Request Data Export
|
||||
<Database className="w-4 h-4 text-muted-foreground" /> Request Data Export
|
||||
</h3>
|
||||
<button onClick={onClose}>
|
||||
<X className="w-5 h-5 text-muted-foreground hover:text-foreground" />
|
||||
|
|
@ -74,47 +74,47 @@ export const DataExportModal: React.FC<DataExportModalProps> = ({
|
|||
Include Data
|
||||
</label>
|
||||
<div className="space-y-2">
|
||||
<label className="flex items-center gap-4 p-4 bg-kodo-ink rounded border border-border cursor-pointer hover:border-border">
|
||||
<label className="flex items-center gap-4 p-4 bg-card rounded border border-border cursor-pointer hover:border-border">
|
||||
<input
|
||||
type="checkbox"
|
||||
checked={options.profile}
|
||||
onChange={() => toggleOption('profile')}
|
||||
className="rounded border-border bg-transparent text-kodo-steel"
|
||||
className="rounded border-border bg-transparent text-muted-foreground"
|
||||
/>
|
||||
<span className="text-sm text-kodo-text-main">
|
||||
<span className="text-sm text-foreground">
|
||||
Profile & Identity
|
||||
</span>
|
||||
</label>
|
||||
<label className="flex items-center gap-4 p-4 bg-kodo-ink rounded border border-border cursor-pointer hover:border-border">
|
||||
<label className="flex items-center gap-4 p-4 bg-card rounded border border-border cursor-pointer hover:border-border">
|
||||
<input
|
||||
type="checkbox"
|
||||
checked={options.tracks}
|
||||
onChange={() => toggleOption('tracks')}
|
||||
className="rounded border-border bg-transparent text-kodo-steel"
|
||||
className="rounded border-border bg-transparent text-muted-foreground"
|
||||
/>
|
||||
<span className="text-sm text-kodo-text-main">
|
||||
<span className="text-sm text-foreground">
|
||||
Uploaded Content Metadata
|
||||
</span>
|
||||
</label>
|
||||
<label className="flex items-center gap-4 p-4 bg-kodo-ink rounded border border-border cursor-pointer hover:border-border">
|
||||
<label className="flex items-center gap-4 p-4 bg-card rounded border border-border cursor-pointer hover:border-border">
|
||||
<input
|
||||
type="checkbox"
|
||||
checked={options.activity}
|
||||
onChange={() => toggleOption('activity')}
|
||||
className="rounded border-border bg-transparent text-kodo-steel"
|
||||
className="rounded border-border bg-transparent text-muted-foreground"
|
||||
/>
|
||||
<span className="text-sm text-kodo-text-main">
|
||||
<span className="text-sm text-foreground">
|
||||
Activity Logs & History
|
||||
</span>
|
||||
</label>
|
||||
<label className="flex items-center gap-4 p-4 bg-kodo-ink rounded border border-border cursor-pointer hover:border-border">
|
||||
<label className="flex items-center gap-4 p-4 bg-card rounded border border-border cursor-pointer hover:border-border">
|
||||
<input
|
||||
type="checkbox"
|
||||
checked={options.billing}
|
||||
onChange={() => toggleOption('billing')}
|
||||
className="rounded border-border bg-transparent text-kodo-steel"
|
||||
className="rounded border-border bg-transparent text-muted-foreground"
|
||||
/>
|
||||
<span className="text-sm text-kodo-text-main">
|
||||
<span className="text-sm text-foreground">
|
||||
Billing & Transactions
|
||||
</span>
|
||||
</label>
|
||||
|
|
@ -122,7 +122,7 @@ export const DataExportModal: React.FC<DataExportModalProps> = ({
|
|||
</div>
|
||||
</div>
|
||||
|
||||
<div className="p-4 border-t border-border bg-kodo-ink flex justify-end gap-4">
|
||||
<div className="p-4 border-t border-border bg-card flex justify-end gap-4">
|
||||
<Button variant="ghost" onClick={onClose}>
|
||||
Cancel
|
||||
</Button>
|
||||
|
|
|
|||
|
|
@ -164,7 +164,7 @@ export const IntegrationsView: React.FC = () => {
|
|||
<>
|
||||
<Button
|
||||
variant="ghost"
|
||||
className="flex-1 border border-border text-kodo-text-main"
|
||||
className="flex-1 border border-border text-foreground"
|
||||
onClick={() => addToast('Settings opened')}
|
||||
>
|
||||
Settings
|
||||
|
|
|
|||
|
|
@ -17,7 +17,7 @@ export function TwoFactorSetupStep3({
|
|||
}: TwoFactorSetupStep3Props) {
|
||||
return (
|
||||
<div className="space-y-6 bg-card p-8 rounded-xl border border-border shadow-2xl">
|
||||
<div className="flex items-center gap-4 text-lime-500 mb-2">
|
||||
<div className="flex items-center gap-4 text-success mb-2">
|
||||
<CheckCircle className="w-8 h-8" />
|
||||
<h3 className="text-xl font-bold">2FA Enabled Successfully</h3>
|
||||
</div>
|
||||
|
|
|
|||
|
|
@ -31,7 +31,7 @@ export const CommentItem: React.FC<CommentItemProps> = ({
|
|||
className="w-8 h-8 rounded-full object-cover flex-shrink-0 cursor-pointer"
|
||||
/>
|
||||
<div className="flex-1 min-w-0">
|
||||
<div className="bg-kodo-ink/50 p-4 rounded-2xl rounded-tl-sm">
|
||||
<div className="bg-card/50 p-4 rounded-2xl rounded-tl-sm">
|
||||
<div className="flex justify-between items-baseline mb-1">
|
||||
<div className="flex gap-2 items-baseline">
|
||||
<span className="font-bold text-white cursor-pointer hover:underline">
|
||||
|
|
@ -40,7 +40,7 @@ export const CommentItem: React.FC<CommentItemProps> = ({
|
|||
<span className="text-muted-foreground text-xs">{comment.timestamp}</span>
|
||||
</div>
|
||||
</div>
|
||||
<p className="text-kodo-text-main leading-relaxed whitespace-pre-wrap">
|
||||
<p className="text-foreground leading-relaxed whitespace-pre-wrap">
|
||||
{comment.content}
|
||||
</p>
|
||||
</div>
|
||||
|
|
@ -48,7 +48,7 @@ export const CommentItem: React.FC<CommentItemProps> = ({
|
|||
<div className="flex items-center gap-4 mt-1 pl-2 text-xs text-muted-foreground">
|
||||
<button
|
||||
onClick={handleLike}
|
||||
className={`flex items-center gap-1 hover:text-kodo-magenta transition-colors ${liked ? 'text-kodo-magenta' : ''}`}
|
||||
className={`flex items-center gap-1 hover:text-destructive transition-colors ${liked ? 'text-destructive' : ''}`}
|
||||
>
|
||||
<Heart className={`w-3 h-3 ${liked ? 'fill-current' : ''}`} />{' '}
|
||||
{likeCount > 0 ? likeCount : 'Like'}
|
||||
|
|
|
|||
|
|
@ -59,11 +59,11 @@ export const CreatePostModal: React.FC<CreatePostModalProps> = ({
|
|||
return (
|
||||
<div className="fixed inset-0 z-[100] flex items-center justify-center p-4">
|
||||
<div
|
||||
className="absolute inset-0 bg-kodo-void/90 backdrop-blur-sm"
|
||||
className="absolute inset-0 bg-background/90 backdrop-blur-sm"
|
||||
onClick={onClose}
|
||||
></div>
|
||||
<div className="relative w-full max-w-lg bg-kodo-graphite border border-border rounded-xl shadow-2xl animate-scaleIn overflow-hidden flex flex-col">
|
||||
<div className="p-4 border-b border-border bg-kodo-ink flex justify-between items-center">
|
||||
<div className="relative w-full max-w-lg bg-muted border border-border rounded-xl shadow-2xl animate-scaleIn overflow-hidden flex flex-col">
|
||||
<div className="p-4 border-b border-border bg-card flex justify-between items-center">
|
||||
<h3 className="font-bold text-foreground">Create Post</h3>
|
||||
<button onClick={onClose} className="rounded-lg p-1 hover:bg-muted/50 transition-colors">
|
||||
<X className="w-5 h-5 text-muted-foreground hover:text-foreground transition-colors" />
|
||||
|
|
@ -82,7 +82,7 @@ export const CreatePostModal: React.FC<CreatePostModalProps> = ({
|
|||
<div className="flex-1">
|
||||
<div className="mb-2">
|
||||
<select
|
||||
className="bg-kodo-ink border border-border rounded-lg px-2.5 py-1 text-xs text-muted-foreground hover:text-foreground focus:outline-none focus:border-primary/50 cursor-pointer transition-colors"
|
||||
className="bg-card border border-border rounded-lg px-2.5 py-1 text-xs text-muted-foreground hover:text-foreground focus:outline-none focus:border-primary/50 cursor-pointer transition-colors"
|
||||
value={visibility}
|
||||
onChange={(e) => setVisibility(e.target.value)}
|
||||
>
|
||||
|
|
@ -119,7 +119,7 @@ export const CreatePostModal: React.FC<CreatePostModalProps> = ({
|
|||
</div>
|
||||
</div>
|
||||
|
||||
<div className="p-4 border-t border-border bg-kodo-ink flex justify-between items-center">
|
||||
<div className="p-4 border-t border-border bg-card flex justify-between items-center">
|
||||
<div className="flex gap-1">
|
||||
<button
|
||||
className={`p-2 rounded-lg transition-colors ${postType === 'image' ? 'bg-primary/10 text-primary' : 'text-muted-foreground hover:text-foreground hover:bg-muted/50'}`}
|
||||
|
|
|
|||
|
|
@ -83,7 +83,7 @@ export const ExploreView: React.FC = () => {
|
|||
return (
|
||||
<div className="space-y-8 animate-fadeIn">
|
||||
{/* Navigation & Search */}
|
||||
<div className="flex flex-col md:flex-row justify-between items-center gap-4 bg-kodo-ink/50 p-2 rounded-xl border border-border/50">
|
||||
<div className="flex flex-col md:flex-row justify-between items-center gap-4 bg-card/50 p-2 rounded-xl border border-border/50">
|
||||
<div className="flex gap-2 overflow-x-auto w-full md:w-auto p-1">
|
||||
{[
|
||||
{
|
||||
|
|
@ -142,14 +142,14 @@ export const ExploreView: React.FC = () => {
|
|||
{/* Grid Content */}
|
||||
{loading ? (
|
||||
<div className="flex justify-center py-24">
|
||||
<Loader2 className="w-10 h-10 text-kodo-steel animate-spin" />
|
||||
<Loader2 className="w-10 h-10 text-muted-foreground animate-spin" />
|
||||
</div>
|
||||
) : (
|
||||
<div className="grid grid-cols-2 md:grid-cols-3 lg:grid-cols-4 gap-4">
|
||||
{items.map((item, i) => (
|
||||
<div
|
||||
key={item.id}
|
||||
className={`relative group cursor-pointer overflow-hidden rounded-xl bg-kodo-ink aspect-square ${i === 0 ? 'col-span-2 row-span-2' : ''}`}
|
||||
className={`relative group cursor-pointer overflow-hidden rounded-xl bg-card aspect-square ${i === 0 ? 'col-span-2 row-span-2' : ''}`}
|
||||
onClick={() => addToast(`Opening ${item.title}`)}
|
||||
>
|
||||
<img
|
||||
|
|
@ -162,7 +162,7 @@ export const ExploreView: React.FC = () => {
|
|||
<h4 className="text-white font-bold truncate text-sm mb-1">
|
||||
{item.title}
|
||||
</h4>
|
||||
<div className="flex justify-between items-center text-xs text-kodo-text-main">
|
||||
<div className="flex justify-between items-center text-xs text-foreground">
|
||||
<span>@{item.author}</span>
|
||||
<div className="flex gap-2">
|
||||
<span className="flex items-center gap-1">
|
||||
|
|
|
|||
|
|
@ -33,11 +33,11 @@ export const SharePostModal: React.FC<SharePostModalProps> = ({
|
|||
return (
|
||||
<div className="fixed inset-0 z-[100] flex items-center justify-center p-4">
|
||||
<div
|
||||
className="absolute inset-0 bg-kodo-void/90 backdrop-blur-sm"
|
||||
className="absolute inset-0 bg-background/90 backdrop-blur-sm"
|
||||
onClick={onClose}
|
||||
></div>
|
||||
<div className="relative w-full max-w-lg bg-kodo-graphite border border-border rounded-xl shadow-2xl animate-scaleIn overflow-hidden">
|
||||
<div className="p-4 border-b border-border bg-kodo-ink flex justify-between items-center">
|
||||
<div className="relative w-full max-w-lg bg-muted border border-border rounded-xl shadow-2xl animate-scaleIn overflow-hidden">
|
||||
<div className="p-4 border-b border-border bg-card flex justify-between items-center">
|
||||
<h3 className="font-bold text-white">Quote Post</h3>
|
||||
<button onClick={onClose}>
|
||||
<X className="w-5 h-5 text-muted-foreground hover:text-white" />
|
||||
|
|
@ -51,7 +51,7 @@ export const SharePostModal: React.FC<SharePostModalProps> = ({
|
|||
onChange={(e) => setQuoteText(e.target.value)}
|
||||
autoFocus
|
||||
/>
|
||||
<div className="border border-border rounded-lg p-4 bg-kodo-ink/30 opacity-70">
|
||||
<div className="border border-border rounded-lg p-4 bg-card/30 opacity-70">
|
||||
<div className="flex items-center gap-2 mb-2">
|
||||
<img
|
||||
src={post.author.avatar}
|
||||
|
|
@ -66,7 +66,7 @@ export const SharePostModal: React.FC<SharePostModalProps> = ({
|
|||
</p>
|
||||
</div>
|
||||
</div>
|
||||
<div className="p-4 border-t border-border bg-kodo-ink flex justify-end gap-2">
|
||||
<div className="p-4 border-t border-border bg-card flex justify-end gap-2">
|
||||
<Button variant="ghost" onClick={() => setMode('options')}>
|
||||
Back
|
||||
</Button>
|
||||
|
|
@ -88,11 +88,11 @@ export const SharePostModal: React.FC<SharePostModalProps> = ({
|
|||
return (
|
||||
<div className="fixed inset-0 z-[100] flex items-center justify-center p-4">
|
||||
<div
|
||||
className="absolute inset-0 bg-kodo-void/90 backdrop-blur-sm"
|
||||
className="absolute inset-0 bg-background/90 backdrop-blur-sm"
|
||||
onClick={onClose}
|
||||
></div>
|
||||
<div className="relative w-full max-w-sm bg-kodo-graphite border border-border rounded-xl shadow-2xl animate-scaleIn overflow-hidden">
|
||||
<div className="p-4 border-b border-border bg-kodo-ink flex justify-between items-center">
|
||||
<div className="relative w-full max-w-sm bg-muted border border-border rounded-xl shadow-2xl animate-scaleIn overflow-hidden">
|
||||
<div className="p-4 border-b border-border bg-card flex justify-between items-center">
|
||||
<h3 className="font-bold text-white">Share Post</h3>
|
||||
<button onClick={onClose}>
|
||||
<X className="w-5 h-5 text-muted-foreground hover:text-white" />
|
||||
|
|
@ -122,7 +122,7 @@ export const SharePostModal: React.FC<SharePostModalProps> = ({
|
|||
className="w-full flex items-center gap-4 p-4 hover:bg-white/5 rounded-lg transition-colors group"
|
||||
onClick={() => setMode('quote')}
|
||||
>
|
||||
<div className="w-10 h-10 rounded-full bg-muted/10 flex items-center justify-center text-kodo-steel group-hover:bg-white/5">
|
||||
<div className="w-10 h-10 rounded-full bg-muted/10 flex items-center justify-center text-muted-foreground group-hover:bg-white/5">
|
||||
<MessageSquare className="w-5 h-5" />
|
||||
</div>
|
||||
<div className="text-left">
|
||||
|
|
@ -139,7 +139,7 @@ export const SharePostModal: React.FC<SharePostModalProps> = ({
|
|||
className="w-full flex items-center gap-4 p-4 hover:bg-white/5 rounded-lg transition-colors group"
|
||||
onClick={handleCopyLink}
|
||||
>
|
||||
<div className="w-10 h-10 rounded-full bg-kodo-graphite flex items-center justify-center text-muted-foreground group-hover:text-white">
|
||||
<div className="w-10 h-10 rounded-full bg-muted flex items-center justify-center text-muted-foreground group-hover:text-white">
|
||||
{copied ? <Check className="w-5 h-5 text-success" /> : <Link className="w-5 h-5" />}
|
||||
</div>
|
||||
<div className="text-left">
|
||||
|
|
@ -153,7 +153,7 @@ export const SharePostModal: React.FC<SharePostModalProps> = ({
|
|||
onClose();
|
||||
}}
|
||||
>
|
||||
<div className="w-10 h-10 rounded-full bg-kodo-graphite flex items-center justify-center text-muted-foreground group-hover:text-white">
|
||||
<div className="w-10 h-10 rounded-full bg-muted flex items-center justify-center text-muted-foreground group-hover:text-white">
|
||||
<Mail className="w-5 h-5" />
|
||||
</div>
|
||||
<div className="text-left">
|
||||
|
|
|
|||
|
|
@ -62,7 +62,7 @@ export const ConnectionsView: React.FC<ConnectionsViewProps> = ({
|
|||
</div>
|
||||
</div>
|
||||
|
||||
<div className="flex flex-col md:flex-row gap-4 items-center bg-kodo-ink/50 p-4 rounded-xl border border-border/50">
|
||||
<div className="flex flex-col md:flex-row gap-4 items-center bg-card/50 p-4 rounded-xl border border-border/50">
|
||||
<div className="w-full md:w-96">
|
||||
<SearchInput
|
||||
placeholder={`Search ${type}...`}
|
||||
|
|
@ -102,7 +102,7 @@ export const ConnectionsView: React.FC<ConnectionsViewProps> = ({
|
|||
|
||||
{loading ? (
|
||||
<div className="flex justify-center py-24">
|
||||
<Loader2 className="w-10 h-10 text-kodo-steel animate-spin" />
|
||||
<Loader2 className="w-10 h-10 text-muted-foreground animate-spin" />
|
||||
</div>
|
||||
) : (
|
||||
<div className="grid grid-cols-1 md:grid-cols-2 lg:grid-cols-3 xl:grid-cols-4 gap-6">
|
||||
|
|
|
|||
|
|
@ -42,13 +42,13 @@ export const CreateGroupModal: React.FC<CreateGroupModalProps> = ({
|
|||
return (
|
||||
<div className="fixed inset-0 z-[100] flex items-center justify-center p-4">
|
||||
<div
|
||||
className="absolute inset-0 bg-kodo-void/90 backdrop-blur-sm"
|
||||
className="absolute inset-0 bg-background/90 backdrop-blur-sm"
|
||||
onClick={onClose}
|
||||
></div>
|
||||
<div className="relative w-full max-w-lg bg-kodo-graphite border border-border rounded-xl shadow-2xl animate-scaleIn overflow-hidden">
|
||||
<div className="p-4 border-b border-border bg-kodo-ink flex justify-between items-center">
|
||||
<div className="relative w-full max-w-lg bg-muted border border-border rounded-xl shadow-2xl animate-scaleIn overflow-hidden">
|
||||
<div className="p-4 border-b border-border bg-card flex justify-between items-center">
|
||||
<h3 className="font-bold text-white flex items-center gap-2">
|
||||
<Users className="w-5 h-5 text-kodo-steel" /> Create Community
|
||||
<Users className="w-5 h-5 text-muted-foreground" /> Create Community
|
||||
</h3>
|
||||
<button onClick={onClose}>
|
||||
<X className="w-5 h-5 text-muted-foreground hover:text-white" />
|
||||
|
|
@ -57,7 +57,7 @@ export const CreateGroupModal: React.FC<CreateGroupModalProps> = ({
|
|||
|
||||
<div className="p-6 space-y-6">
|
||||
{/* Cover Upload */}
|
||||
<div className="relative w-full h-32 bg-kodo-ink border-2 border-dashed border-border rounded-lg overflow-hidden flex flex-col items-center justify-center group cursor-pointer hover:border-border/50 transition-colors">
|
||||
<div className="relative w-full h-32 bg-card border-2 border-dashed border-border rounded-lg overflow-hidden flex flex-col items-center justify-center group cursor-pointer hover:border-border/50 transition-colors">
|
||||
{coverImage ? (
|
||||
<img src={coverImage} className="w-full h-full object-cover" />
|
||||
) : (
|
||||
|
|
@ -90,7 +90,7 @@ export const CreateGroupModal: React.FC<CreateGroupModalProps> = ({
|
|||
Description
|
||||
</label>
|
||||
<textarea
|
||||
className="w-full bg-kodo-void border border-border rounded-lg p-4 text-white focus:border-primary outline-none text-sm resize-none h-24"
|
||||
className="w-full bg-background border border-border rounded-lg p-4 text-white focus:border-primary outline-none text-sm resize-none h-24"
|
||||
placeholder="What's this community about?"
|
||||
value={description}
|
||||
onChange={(e) => setDescription(e.target.value)}
|
||||
|
|
@ -98,14 +98,14 @@ export const CreateGroupModal: React.FC<CreateGroupModalProps> = ({
|
|||
</div>
|
||||
|
||||
<div
|
||||
className="bg-kodo-ink p-4 rounded-lg border border-border flex items-center justify-between cursor-pointer hover:border-border"
|
||||
className="bg-card p-4 rounded-lg border border-border flex items-center justify-between cursor-pointer hover:border-border"
|
||||
onClick={() => setIsPrivate(!isPrivate)}
|
||||
>
|
||||
<div className="flex items-center gap-4">
|
||||
{isPrivate ? (
|
||||
<Lock className="w-5 h-5 text-warning" />
|
||||
) : (
|
||||
<Globe className="w-5 h-5 text-kodo-steel" />
|
||||
<Globe className="w-5 h-5 text-muted-foreground" />
|
||||
)}
|
||||
<div>
|
||||
<div className="text-sm font-bold text-white">
|
||||
|
|
@ -127,7 +127,7 @@ export const CreateGroupModal: React.FC<CreateGroupModalProps> = ({
|
|||
</div>
|
||||
</div>
|
||||
|
||||
<div className="p-4 border-t border-border bg-kodo-ink flex justify-end gap-4">
|
||||
<div className="p-4 border-t border-border bg-card flex justify-end gap-4">
|
||||
<Button variant="ghost" onClick={onClose}>
|
||||
Cancel
|
||||
</Button>
|
||||
|
|
|
|||
|
|
@ -25,7 +25,7 @@ export const GroupCard: React.FC<GroupCardProps> = ({
|
|||
className="p-0 overflow-hidden group cursor-pointer hover:border-border/50 transition-all flex flex-col h-full"
|
||||
onClick={onClick}
|
||||
>
|
||||
<div className="h-32 relative overflow-hidden bg-kodo-ink">
|
||||
<div className="h-32 relative overflow-hidden bg-card">
|
||||
<img
|
||||
src={group.coverUrl}
|
||||
className="w-full h-full object-cover transition-opacity duration-[var(--duration-fast)] opacity-80 group-hover:opacity-100"
|
||||
|
|
@ -68,7 +68,7 @@ export const GroupCard: React.FC<GroupCardProps> = ({
|
|||
<Button
|
||||
variant="ghost"
|
||||
size="sm"
|
||||
className="w-full border border-border hover:bg-kodo-red/10 hover:text-destructive hover:border-kodo-red"
|
||||
className="w-full border border-border hover:bg-destructive/10 hover:text-destructive hover:border-destructive"
|
||||
onClick={onLeave}
|
||||
>
|
||||
<LogOut className="w-4 h-4 mr-2" /> Leave Group
|
||||
|
|
|
|||
|
|
@ -110,17 +110,17 @@ export const GroupsView: React.FC<GroupsViewProps> = ({ onOpenGroup }) => {
|
|||
</Button>
|
||||
</div>
|
||||
|
||||
<div className="flex flex-col md:flex-row gap-4 items-center bg-kodo-ink/50 p-4 rounded-xl border border-border/50">
|
||||
<div className="flex bg-kodo-void rounded-lg p-1 border border-border">
|
||||
<div className="flex flex-col md:flex-row gap-4 items-center bg-card/50 p-4 rounded-xl border border-border/50">
|
||||
<div className="flex bg-background rounded-lg p-1 border border-border">
|
||||
<button
|
||||
onClick={() => setActiveTab('my_groups')}
|
||||
className={`flex items-center gap-2 px-4 py-2 rounded text-sm font-bold transition-colors ${activeTab === 'my_groups' ? 'bg-kodo-slate text-white' : 'text-muted-foreground hover:text-white'}`}
|
||||
className={`flex items-center gap-2 px-4 py-2 rounded text-sm font-bold transition-colors ${activeTab === 'my_groups' ? 'bg-muted text-white' : 'text-muted-foreground hover:text-white'}`}
|
||||
>
|
||||
<Users className="w-4 h-4" /> My Groups
|
||||
</button>
|
||||
<button
|
||||
onClick={() => setActiveTab('discover')}
|
||||
className={`flex items-center gap-2 px-4 py-2 rounded text-sm font-bold transition-colors ${activeTab === 'discover' ? 'bg-kodo-slate text-white' : 'text-muted-foreground hover:text-white'}`}
|
||||
className={`flex items-center gap-2 px-4 py-2 rounded text-sm font-bold transition-colors ${activeTab === 'discover' ? 'bg-muted text-white' : 'text-muted-foreground hover:text-white'}`}
|
||||
>
|
||||
<Compass className="w-4 h-4" /> Discover
|
||||
</button>
|
||||
|
|
@ -136,7 +136,7 @@ export const GroupsView: React.FC<GroupsViewProps> = ({ onOpenGroup }) => {
|
|||
|
||||
{loading ? (
|
||||
<div className="flex justify-center py-24">
|
||||
<Loader2 className="w-10 h-10 text-kodo-steel animate-spin" />
|
||||
<Loader2 className="w-10 h-10 text-muted-foreground animate-spin" />
|
||||
</div>
|
||||
) : (
|
||||
<div className="grid grid-cols-1 md:grid-cols-2 lg:grid-cols-3 xl:grid-cols-4 gap-6">
|
||||
|
|
|
|||
|
|
@ -61,8 +61,8 @@ export function ThemeSwitcher({
|
|||
onClick={() => onThemeChange(theme.id)}
|
||||
className={`group relative p-8 rounded-2xl border-2 transition-all duration-[var(--duration-normal)] text-left overflow-hidden ${
|
||||
currentTheme === theme.id
|
||||
? 'border-primary bg-primary/10 shadow-lg shadow-kodo-cyan/20'
|
||||
: 'border-white/10 bg-kodo-graphite/50 hover:border-white/30 hover:bg-kodo-graphite'
|
||||
? 'border-primary bg-primary/10 shadow-lg shadow-primary/20'
|
||||
: 'border-white/10 bg-muted/50 hover:border-white/30 hover:bg-muted'
|
||||
}`}
|
||||
>
|
||||
{/* Gradient Background */}
|
||||
|
|
@ -95,7 +95,7 @@ export function ThemeSwitcher({
|
|||
</div>
|
||||
|
||||
{currentTheme === theme.id && (
|
||||
<div className="flex items-center gap-2 text-kodo-steel font-mono text-sm animate-slide-in-left">
|
||||
<div className="flex items-center gap-2 text-muted-foreground font-mono text-sm animate-slide-in-left">
|
||||
<div className="w-2 h-2 rounded-full bg-primary animate-glow-pulse" />
|
||||
Active Theme
|
||||
</div>
|
||||
|
|
|
|||
|
|
@ -15,7 +15,7 @@ type Story = StoryObj<typeof meta>;
|
|||
|
||||
export const Default: Story = {
|
||||
render: () => (
|
||||
<div className="h-[400px] w-full relative border border-kodo-steel overflow-hidden rounded-lg">
|
||||
<div className="h-[400px] w-full relative border border-border overflow-hidden rounded-lg">
|
||||
<AstralBackground />
|
||||
<div className="absolute inset-0 flex items-center justify-center pointer-events-none">
|
||||
<h1 className="text-4xl font-bold text-white z-10">Astral Background</h1>
|
||||
|
|
|
|||
|
|
@ -20,7 +20,7 @@ type Story = StoryObj<typeof meta>;
|
|||
export const Default: Story = {
|
||||
args: {
|
||||
trigger: <h3 className="text-lg font-semibold p-2">Click to expand</h3>,
|
||||
children: <div className="p-4 border border-kodo-steel rounded-md mt-2">Content hidden by default</div>,
|
||||
children: <div className="p-4 border border-border rounded-md mt-2">Content hidden by default</div>,
|
||||
},
|
||||
};
|
||||
|
||||
|
|
@ -32,7 +32,7 @@ export const CollapsibleCardExample: Story = {
|
|||
className="w-[400px]"
|
||||
>
|
||||
<div className="space-y-4">
|
||||
<div className="text-sm text-kodo-content-dim">
|
||||
<div className="text-sm text-muted-foreground">
|
||||
Configure advanced options for your project.
|
||||
</div>
|
||||
<div className="flex justify-end">
|
||||
|
|
|
|||
|
|
@ -23,9 +23,9 @@ const meta = {
|
|||
},
|
||||
decorators: [
|
||||
(Story) => (
|
||||
<div className="h-[300px] w-full relative bg-kodo-void/50 border border-white/10 overflow-hidden">
|
||||
<div className="h-[300px] w-full relative bg-background/50 border border-white/10 overflow-hidden">
|
||||
<Story />
|
||||
<div className="p-8 text-kodo-content-dim">
|
||||
<div className="p-8 text-muted-foreground">
|
||||
<p>The FAB will be positioned relative to this container.</p>
|
||||
</div>
|
||||
</div>
|
||||
|
|
|
|||
|
|
@ -90,7 +90,7 @@ export function FAB({
|
|||
)}
|
||||
>
|
||||
{showLabel && label && (
|
||||
<span className="text-sm font-semibold text-white bg-kodo-ink/90 backdrop-blur-md px-4 py-2 rounded-lg border border-white/10 shadow-lg whitespace-nowrap">
|
||||
<span className="text-sm font-semibold text-white bg-card/90 backdrop-blur-md px-4 py-2 rounded-lg border border-white/10 shadow-lg whitespace-nowrap">
|
||||
{label}
|
||||
</span>
|
||||
)}
|
||||
|
|
|
|||
|
|
@ -115,7 +115,7 @@ export const FormField: React.FC<FormFieldProps> = ({
|
|||
}) => {
|
||||
return (
|
||||
<div className={cn('space-y-2', className)}>
|
||||
<label className="text-sm font-medium text-kodo-text-main dark:text-kodo-text-main">
|
||||
<label className="text-sm font-medium text-foreground dark:text-foreground">
|
||||
{label}
|
||||
{required && <span className="text-destructive ml-1">*</span>}
|
||||
</label>
|
||||
|
|
@ -142,7 +142,7 @@ export const Input: React.FC<InputProps> = ({
|
|||
return (
|
||||
<DesignSystemInput
|
||||
className={cn(
|
||||
error && 'border-kodo-red focus-visible:border-kodo-red',
|
||||
error && 'border-destructive focus-visible:border-destructive',
|
||||
className,
|
||||
)}
|
||||
{...props}
|
||||
|
|
@ -163,7 +163,7 @@ export const Textarea: React.FC<TextareaProps> = ({
|
|||
return (
|
||||
<DesignSystemTextarea
|
||||
className={cn(
|
||||
error && 'border-kodo-red focus-visible:border-kodo-red',
|
||||
error && 'border-destructive focus-visible:border-destructive',
|
||||
className,
|
||||
)}
|
||||
{...props}
|
||||
|
|
@ -207,7 +207,7 @@ export const Select: React.FC<SelectProps> = ({
|
|||
disabled={disabled}
|
||||
placeholder={placeholder || 'Select an option...'}
|
||||
className={cn(
|
||||
error && 'border-kodo-red',
|
||||
error && 'border-destructive',
|
||||
className,
|
||||
)}
|
||||
aria-label={ariaLabel}
|
||||
|
|
|
|||
|
|
@ -4,7 +4,7 @@ import React, { useState, useCallback, lazy, Suspense } from 'react';
|
|||
const Cropper = lazy(() =>
|
||||
Promise.resolve({
|
||||
default: (_props: any) => (
|
||||
<div className="bg-kodo-graphite flex items-center justify-center h-full text-white">
|
||||
<div className="bg-muted flex items-center justify-center h-full text-white">
|
||||
Cropper Mock
|
||||
</div>
|
||||
),
|
||||
|
|
@ -124,10 +124,10 @@ export const ImageCropper: React.FC<ImageCropperProps> = ({
|
|||
};
|
||||
|
||||
return (
|
||||
<div className="fixed inset-0 z-[100] flex items-center justify-center p-4 bg-kodo-void/95 backdrop-blur-sm">
|
||||
<div className="relative w-full max-w-2xl bg-kodo-graphite border border-border rounded-xl shadow-2xl overflow-hidden flex flex-col h-layout-modal-sm">
|
||||
<div className="fixed inset-0 z-[100] flex items-center justify-center p-4 bg-background/95 backdrop-blur-sm">
|
||||
<div className="relative w-full max-w-2xl bg-muted border border-border rounded-xl shadow-2xl overflow-hidden flex flex-col h-layout-modal-sm">
|
||||
{/* Header */}
|
||||
<div className="p-4 border-b border-border flex justify-between items-center bg-kodo-ink">
|
||||
<div className="p-4 border-b border-border flex justify-between items-center bg-card">
|
||||
<h3 className="font-bold text-white flex items-center gap-2">
|
||||
Edit Image
|
||||
</h3>
|
||||
|
|
@ -161,7 +161,7 @@ export const ImageCropper: React.FC<ImageCropperProps> = ({
|
|||
</div>
|
||||
|
||||
{/* Controls */}
|
||||
<div className="p-8 bg-kodo-ink border-t border-border space-y-4">
|
||||
<div className="p-8 bg-card border-t border-border space-y-4">
|
||||
<div className="flex items-center gap-4">
|
||||
<span className="text-xs text-muted-foreground w-16">Zoom</span>
|
||||
<ZoomIn className="w-4 h-4 text-muted-foreground" />
|
||||
|
|
|
|||
|
|
@ -27,7 +27,7 @@ export const Default: Story = {
|
|||
<Button onClick={() => setOpen(true)}>Open Modal</Button>
|
||||
<Modal {...args} open={open} onClose={() => setOpen(false)} title="Example Modal">
|
||||
<div className="py-4">
|
||||
<p className="text-kodo-content-dim">
|
||||
<p className="text-muted-foreground">
|
||||
This is a standard modal dialog. It can contain any content.
|
||||
</p>
|
||||
</div>
|
||||
|
|
|
|||
|
|
@ -22,7 +22,7 @@ export const Default: Story = {
|
|||
<div className="text-sm">
|
||||
Tag {a.length - i}
|
||||
</div>
|
||||
{i !== a.length - 1 && <div className="my-2 h-px bg-kodo-steel" />}
|
||||
{i !== a.length - 1 && <div className="my-2 h-px bg-muted" />}
|
||||
</div>
|
||||
))}
|
||||
</ScrollArea>
|
||||
|
|
|
|||
|
|
@ -19,11 +19,11 @@ const meta = {
|
|||
},
|
||||
decorators: [
|
||||
(Story) => (
|
||||
<div className="h-[500px] w-full relative flex border bg-kodo-void">
|
||||
<div className="h-[500px] w-full relative flex border bg-background">
|
||||
<Story />
|
||||
<div className="flex-1 p-8">
|
||||
<h1 className="text-2xl font-bold mb-4">Main Content</h1>
|
||||
<p className="text-kodo-content-dim">
|
||||
<p className="text-muted-foreground">
|
||||
The sidebar sits alongside this content.
|
||||
</p>
|
||||
</div>
|
||||
|
|
@ -57,13 +57,13 @@ export const RightSidebar: Story = {
|
|||
position: 'right',
|
||||
children: (
|
||||
<div className="p-4 space-y-4">
|
||||
<div className="text-sm text-kodo-content-dim">User details go here</div>
|
||||
<div className="text-sm text-muted-foreground">User details go here</div>
|
||||
</div>
|
||||
),
|
||||
},
|
||||
decorators: [
|
||||
(Story) => (
|
||||
<div className="h-[500px] w-full relative flex border bg-kodo-void">
|
||||
<div className="h-[500px] w-full relative flex border bg-background">
|
||||
<div className="flex-1 p-8">
|
||||
<h1 className="text-2xl font-bold mb-4">Main Content</h1>
|
||||
</div>
|
||||
|
|
|
|||
|
|
@ -138,7 +138,7 @@ export function Sidebar({
|
|||
className={cn(
|
||||
'flex flex-col transition-all duration-[var(--duration-normal)] ease-in-out',
|
||||
position === 'left' ? 'border-r' : 'border-l',
|
||||
'border-white/10 bg-kodo-ink/40 backdrop-blur-md rounded-xl',
|
||||
'border-white/10 bg-card/40 backdrop-blur-md rounded-xl',
|
||||
isCollapsed ? 'w-0 overflow-hidden' : width,
|
||||
className,
|
||||
)}
|
||||
|
|
@ -148,7 +148,7 @@ export function Sidebar({
|
|||
<div className="flex items-center justify-between p-4 border-b border-white/10">
|
||||
{title && (
|
||||
<div className="flex items-center gap-2 flex-1">
|
||||
{icon && <div className="text-kodo-steel">{icon}</div>}
|
||||
{icon && <div className="text-muted-foreground">{icon}</div>}
|
||||
<h3 className="text-sm font-semibold text-white">{title}</h3>
|
||||
</div>
|
||||
)}
|
||||
|
|
|
|||
|
|
@ -40,11 +40,11 @@ export const Sizes: Story = {
|
|||
|
||||
export const Variants: Story = {
|
||||
render: () => (
|
||||
<div className="flex items-center gap-4 bg-kodo-graphite p-4 rounded-md">
|
||||
<div className="flex items-center gap-4 bg-muted p-4 rounded-md">
|
||||
<Spinner variant="default" />
|
||||
<Spinner variant="muted" />
|
||||
<Spinner variant="white" />
|
||||
<div className="text-kodo-red">
|
||||
<div className="text-destructive">
|
||||
<Spinner variant="current" />
|
||||
</div>
|
||||
</div>
|
||||
|
|
|
|||
|
|
@ -64,7 +64,7 @@ describe('Toast Component', () => {
|
|||
);
|
||||
|
||||
const toast = container.firstChild as HTMLElement;
|
||||
expect(toast.className).toContain('border-kodo-lime');
|
||||
expect(toast.className).toContain('border-success');
|
||||
});
|
||||
|
||||
it('applies correct styles for error variant', () => {
|
||||
|
|
@ -73,7 +73,7 @@ describe('Toast Component', () => {
|
|||
);
|
||||
|
||||
const toast = container.firstChild as HTMLElement;
|
||||
expect(toast.className).toContain('border-kodo-red');
|
||||
expect(toast.className).toContain('border-destructive');
|
||||
});
|
||||
|
||||
it('applies correct styles for info variant', () => {
|
||||
|
|
@ -82,6 +82,6 @@ describe('Toast Component', () => {
|
|||
);
|
||||
|
||||
const toast = container.firstChild as HTMLElement;
|
||||
expect(toast.className).toContain('border-kodo-steel');
|
||||
expect(toast.className).toContain('border-border');
|
||||
});
|
||||
});
|
||||
|
|
|
|||
|
|
@ -27,14 +27,14 @@ export const Default: Story = {
|
|||
items,
|
||||
itemHeight: 70,
|
||||
containerHeight: 400,
|
||||
className: 'border border-kodo-steel rounded-md',
|
||||
className: 'border border-border rounded-md',
|
||||
renderItem: (item) => (
|
||||
<div
|
||||
key={item.id}
|
||||
className="h-[70px] p-4 border-b border-kodo-steel flex flex-col justify-center hover:bg-white/5 transition-colors"
|
||||
className="h-[70px] p-4 border-b border-border flex flex-col justify-center hover:bg-white/5 transition-colors"
|
||||
>
|
||||
<span className="font-bold text-white">{item.text}</span>
|
||||
<span className="text-xs text-kodo-content-dim">{item.description}</span>
|
||||
<span className="text-xs text-muted-foreground">{item.description}</span>
|
||||
</div>
|
||||
),
|
||||
},
|
||||
|
|
@ -45,7 +45,7 @@ export const SmallItems: Story = {
|
|||
items,
|
||||
itemHeight: 30,
|
||||
containerHeight: 300,
|
||||
className: 'border border-kodo-steel rounded-md',
|
||||
className: 'border border-border rounded-md',
|
||||
renderItem: (item) => (
|
||||
<div
|
||||
key={item.id}
|
||||
|
|
|
|||
|
|
@ -91,8 +91,8 @@ export const WaveformVisualizer: React.FC<WaveformVisualizerProps> = ({
|
|||
progress,
|
||||
onSeek,
|
||||
height = 64,
|
||||
color = '#374054', // kodo-steel
|
||||
playedColor = '#00FFF7', // kodo-cyan
|
||||
color = '#2a2a31', // sumi-bg-hover
|
||||
playedColor = '#7c9dd6', // sumi-accent
|
||||
}) => {
|
||||
const canvasRef = useRef<HTMLCanvasElement>(null);
|
||||
const [data, setData] = useState<number[]>([]);
|
||||
|
|
|
|||
|
|
@ -9,7 +9,7 @@ describe('Alert Component', () => {
|
|||
const alert = screen.getByRole('alert');
|
||||
expect(alert).toBeInTheDocument();
|
||||
expect(alert).toHaveTextContent('Default alert message');
|
||||
expect(alert).toHaveClass('bg-kodo-steel/10');
|
||||
expect(alert).toHaveClass('bg-muted/10');
|
||||
});
|
||||
|
||||
it('renders with title', () => {
|
||||
|
|
@ -23,32 +23,32 @@ describe('Alert Component', () => {
|
|||
render(<Alert variant="info">Info message</Alert>);
|
||||
|
||||
const alert = screen.getByRole('alert');
|
||||
expect(alert).toHaveClass('bg-kodo-steel/10');
|
||||
expect(alert).toHaveClass('text-kodo-steel');
|
||||
expect(alert).toHaveClass('bg-muted/10');
|
||||
expect(alert).toHaveClass('text-muted-foreground');
|
||||
});
|
||||
|
||||
it('renders success variant', () => {
|
||||
render(<Alert variant="success">Success message</Alert>);
|
||||
|
||||
const alert = screen.getByRole('alert');
|
||||
expect(alert).toHaveClass('bg-kodo-lime/10');
|
||||
expect(alert).toHaveClass('text-kodo-lime');
|
||||
expect(alert).toHaveClass('bg-success/10');
|
||||
expect(alert).toHaveClass('text-success');
|
||||
});
|
||||
|
||||
it('renders warning variant', () => {
|
||||
render(<Alert variant="warning">Warning message</Alert>);
|
||||
|
||||
const alert = screen.getByRole('alert');
|
||||
expect(alert).toHaveClass('bg-kodo-gold/10');
|
||||
expect(alert).toHaveClass('text-kodo-gold');
|
||||
expect(alert).toHaveClass('bg-warning/10');
|
||||
expect(alert).toHaveClass('text-warning');
|
||||
});
|
||||
|
||||
it('renders error variant', () => {
|
||||
render(<Alert variant="error">Error message</Alert>);
|
||||
|
||||
const alert = screen.getByRole('alert');
|
||||
expect(alert).toHaveClass('bg-kodo-red/10');
|
||||
expect(alert).toHaveClass('text-kodo-red');
|
||||
expect(alert).toHaveClass('bg-destructive/10');
|
||||
expect(alert).toHaveClass('text-destructive');
|
||||
});
|
||||
|
||||
it('handles onClose callback', () => {
|
||||
|
|
@ -72,7 +72,7 @@ describe('Alert Component', () => {
|
|||
render(<Alert variant="destructive">Destructive message</Alert>);
|
||||
|
||||
const alert = screen.getByRole('alert');
|
||||
expect(alert).toHaveClass('bg-kodo-red/10');
|
||||
expect(alert).toHaveClass('bg-destructive/10');
|
||||
});
|
||||
|
||||
it('applies custom className', () => {
|
||||
|
|
|
|||
|
|
@ -151,7 +151,7 @@ export const Avatar = React.forwardRef<HTMLDivElement, AvatarProps>(
|
|||
};
|
||||
|
||||
const statusColors = {
|
||||
online: 'bg-kodo-lime',
|
||||
online: 'bg-success',
|
||||
offline: 'bg-muted',
|
||||
away: 'bg-warning',
|
||||
idle: 'bg-warning',
|
||||
|
|
@ -172,7 +172,7 @@ export const Avatar = React.forwardRef<HTMLDivElement, AvatarProps>(
|
|||
const badgeColors = {
|
||||
primary: 'bg-primary text-primary-foreground',
|
||||
destructive: 'bg-destructive text-destructive-foreground',
|
||||
success: 'bg-kodo-lime text-kodo-lime-foreground',
|
||||
success: 'bg-success text-success-foreground',
|
||||
};
|
||||
|
||||
const badgeSizeClasses = {
|
||||
|
|
|
|||
|
|
@ -147,11 +147,11 @@ export const Badge = React.forwardRef<HTMLSpanElement, BadgeProps>(
|
|||
|
||||
const styles: Record<string, string> = {
|
||||
cyan: 'bg-muted/10 text-muted-foreground border-border/30',
|
||||
magenta: 'bg-kodo-magenta/10 text-kodo-magenta border-kodo-magenta/30',
|
||||
magenta: 'bg-destructive/10 text-destructive border-destructive/30',
|
||||
lime: 'bg-success/10 text-success border-success/30',
|
||||
gold: 'bg-warning/10 text-warning border-warning/30',
|
||||
terminal:
|
||||
'bg-kodo-terminal/10 text-kodo-terminal border-kodo-terminal/30 font-mono',
|
||||
'bg-success/10 text-success border-success/30 font-mono',
|
||||
};
|
||||
|
||||
const sizeStyles = {
|
||||
|
|
@ -162,10 +162,10 @@ export const Badge = React.forwardRef<HTMLSpanElement, BadgeProps>(
|
|||
|
||||
const dotBgStyles: Record<string, string> = {
|
||||
cyan: 'bg-muted-foreground',
|
||||
magenta: 'bg-kodo-magenta',
|
||||
magenta: 'bg-destructive',
|
||||
lime: 'bg-success',
|
||||
gold: 'bg-warning',
|
||||
terminal: 'bg-kodo-terminal',
|
||||
terminal: 'bg-success',
|
||||
};
|
||||
|
||||
const displayText = label || children;
|
||||
|
|
|
|||
|
|
@ -106,7 +106,7 @@ export const Checkbox = React.forwardRef<HTMLInputElement, CheckboxProps>(
|
|||
/>
|
||||
<div
|
||||
className="
|
||||
w-5 h-5 rounded border border-border bg-kodo-graphite
|
||||
w-5 h-5 rounded border border-border bg-muted
|
||||
peer-checked:bg-primary peer-checked:border-border
|
||||
peer-focus-visible:ring-2 peer-focus-visible:ring-ring peer-focus-visible:ring-offset-2 peer-focus-visible:ring-offset-background
|
||||
transition-all duration-[var(--duration-fast)]
|
||||
|
|
@ -118,7 +118,7 @@ export const Checkbox = React.forwardRef<HTMLInputElement, CheckboxProps>(
|
|||
/>
|
||||
</div>
|
||||
{label && (
|
||||
<span className="text-sm text-kodo-text-main group-hover:text-white transition-colors duration-[var(--duration-fast)] select-none">
|
||||
<span className="text-sm text-foreground group-hover:text-white transition-colors duration-[var(--duration-fast)] select-none">
|
||||
{label}
|
||||
</span>
|
||||
)}
|
||||
|
|
|
|||
|
|
@ -150,7 +150,7 @@ export function ConfirmationDialog({
|
|||
<div className="flex items-start gap-4">
|
||||
{variant === 'destructive' && (
|
||||
<div className="flex-shrink-0">
|
||||
<div className="flex h-10 w-10 items-center justify-center rounded-full bg-kodo-red/10 dark:bg-kodo-red/20">
|
||||
<div className="flex h-10 w-10 items-center justify-center rounded-full bg-destructive/10 dark:bg-destructive/20">
|
||||
<AlertTriangle className="h-5 w-5 text-destructive dark:text-destructive" />
|
||||
</div>
|
||||
</div>
|
||||
|
|
|
|||
|
|
@ -26,12 +26,12 @@ const FloatingInput = React.forwardRef<HTMLInputElement, FloatingInputProps>(
|
|||
type={inputType}
|
||||
id={inputId}
|
||||
className={cn(
|
||||
"block px-4 pb-2.5 pt-5 w-full text-sm text-white bg-kodo-graphite/40 rounded-xl border appearance-none focus:outline-none focus:ring-0 peer transition-all duration-[var(--duration-fast)]",
|
||||
"block px-4 pb-2.5 pt-5 w-full text-sm text-white bg-muted/40 rounded-xl border appearance-none focus:outline-none focus:ring-0 peer transition-all duration-[var(--duration-fast)]",
|
||||
// Focus glow
|
||||
"focus:shadow-[0_0_0_3px_oklch(var(--primary)/0.15),0_0_12px_oklch(var(--primary)/0.1)]",
|
||||
// Borders & Colors
|
||||
error
|
||||
? "border-kodo-red focus:border-kodo-red"
|
||||
? "border-destructive focus:border-destructive"
|
||||
: "border-white/10 hover:border-white/20 focus:border-primary",
|
||||
// Glassmorphism
|
||||
"backdrop-blur-sm",
|
||||
|
|
@ -46,7 +46,7 @@ const FloatingInput = React.forwardRef<HTMLInputElement, FloatingInputProps>(
|
|||
|
||||
{/* Icon */}
|
||||
{icon && (
|
||||
<div className="absolute left-3.5 top-1/2 -translate-y-1/2 text-kodo-text-dim peer-focus:text-primary transition-colors duration-[var(--duration-fast)] pointer-events-none">
|
||||
<div className="absolute left-3.5 top-1/2 -translate-y-1/2 text-muted-foreground peer-focus:text-primary transition-colors duration-[var(--duration-fast)] pointer-events-none">
|
||||
{icon}
|
||||
</div>
|
||||
)}
|
||||
|
|
@ -72,7 +72,7 @@ const FloatingInput = React.forwardRef<HTMLInputElement, FloatingInputProps>(
|
|||
icon ? "left-11 peer-focus:left-11 peer-placeholder-shown:left-11" : "left-4 peer-focus:left-4 peer-placeholder-shown:left-4",
|
||||
error
|
||||
? "text-destructive"
|
||||
: "text-kodo-text-dim peer-focus:text-primary group-hover:text-white/70"
|
||||
: "text-muted-foreground peer-focus:text-primary group-hover:text-white/70"
|
||||
)}
|
||||
>
|
||||
{label}
|
||||
|
|
|
|||
|
|
@ -9,7 +9,7 @@ describe('Input Component', () => {
|
|||
|
||||
const input = screen.getByPlaceholderText('Enter text');
|
||||
expect(input).toBeInTheDocument();
|
||||
expect(input).toHaveClass('bg-kodo-graphite');
|
||||
expect(input).toHaveClass('bg-muted');
|
||||
});
|
||||
|
||||
it('renders with label', () => {
|
||||
|
|
|
|||
|
|
@ -26,8 +26,8 @@ export function LazyErrorFallback({
|
|||
}: LazyErrorFallbackProps) {
|
||||
return (
|
||||
<div className="flex flex-col items-center justify-center min-h-layout-page-sm p-8 text-center animate-in fade-in zoom-in duration-[var(--duration-normal)]">
|
||||
<div className="bg-kodo-ink/50 border border-border/30 rounded-xl p-8 max-w-md w-full shadow-lg backdrop-blur-sm">
|
||||
<div className="w-16 h-16 bg-kodo-red/10 rounded-full flex items-center justify-center mx-auto mb-6">
|
||||
<div className="bg-card/50 border border-border/30 rounded-xl p-8 max-w-md w-full shadow-lg backdrop-blur-sm">
|
||||
<div className="w-16 h-16 bg-destructive/10 rounded-full flex items-center justify-center mx-auto mb-6">
|
||||
<AlertTriangle className="h-8 w-8 text-destructive" />
|
||||
</div>
|
||||
<h2 className="text-xl font-bold mb-2">Failed to load {pageName}</h2>
|
||||
|
|
|
|||
|
|
@ -86,7 +86,7 @@ export function Modal({
|
|||
>
|
||||
{/* Backdrop */}
|
||||
<motion.div
|
||||
className="absolute inset-0 bg-kodo-void/90 backdrop-blur-sm"
|
||||
className="absolute inset-0 bg-background/90 backdrop-blur-sm"
|
||||
initial={{ opacity: 0 }}
|
||||
animate={{ opacity: 1 }}
|
||||
exit={{ opacity: 0 }}
|
||||
|
|
@ -105,7 +105,7 @@ export function Modal({
|
|||
exit={{ opacity: 0, scale: 0.95, y: 10 }}
|
||||
transition={{ duration: 0.15, ease: 'easeOut' }}
|
||||
className={cn(
|
||||
'relative w-full bg-kodo-graphite border border-border rounded-xl shadow-2xl flex flex-col overflow-hidden',
|
||||
'relative w-full bg-muted border border-border rounded-xl shadow-2xl flex flex-col overflow-hidden',
|
||||
sizeClasses[size],
|
||||
className,
|
||||
)}
|
||||
|
|
@ -113,7 +113,7 @@ export function Modal({
|
|||
>
|
||||
{/* Header */}
|
||||
{title && (
|
||||
<div className="p-4 border-b border-border bg-kodo-ink flex justify-between items-center shrink-0">
|
||||
<div className="p-4 border-b border-border bg-card flex justify-between items-center shrink-0">
|
||||
<h3 id={titleId} className="font-bold text-foreground text-lg font-heading">
|
||||
{title}
|
||||
</h3>
|
||||
|
|
@ -136,7 +136,7 @@ export function Modal({
|
|||
|
||||
{/* Footer */}
|
||||
{footer && (
|
||||
<div className="p-4 border-t border-border bg-kodo-ink shrink-0 flex justify-end gap-4">
|
||||
<div className="p-4 border-t border-border bg-card shrink-0 flex justify-end gap-4">
|
||||
{footer}
|
||||
</div>
|
||||
)}
|
||||
|
|
|
|||
|
|
@ -40,19 +40,19 @@ describe('Progress Component', () => {
|
|||
|
||||
it('handles different colors', () => {
|
||||
const { rerender } = render(<Progress value={50} color="cyan" />);
|
||||
let fill = document.querySelector('.bg-kodo-cyan');
|
||||
let fill = document.querySelector('.bg-primary');
|
||||
expect(fill).toBeInTheDocument();
|
||||
|
||||
rerender(<Progress value={50} color="magenta" />);
|
||||
fill = document.querySelector('.bg-kodo-magenta');
|
||||
fill = document.querySelector('.bg-destructive');
|
||||
expect(fill).toBeInTheDocument();
|
||||
|
||||
rerender(<Progress value={50} color="lime" />);
|
||||
fill = document.querySelector('.bg-kodo-lime');
|
||||
fill = document.querySelector('.bg-success');
|
||||
expect(fill).toBeInTheDocument();
|
||||
|
||||
rerender(<Progress value={50} color="gold" />);
|
||||
fill = document.querySelector('.bg-kodo-gold');
|
||||
fill = document.querySelector('.bg-warning');
|
||||
expect(fill).toBeInTheDocument();
|
||||
});
|
||||
|
||||
|
|
|
|||
|
|
@ -129,16 +129,16 @@ export const Progress = React.forwardRef<HTMLDivElement, ProgressProps>(
|
|||
|
||||
const colorStyles = {
|
||||
cyan: 'bg-primary',
|
||||
magenta: 'bg-kodo-magenta',
|
||||
lime: 'bg-kodo-lime',
|
||||
magenta: 'bg-destructive',
|
||||
lime: 'bg-success',
|
||||
gold: 'bg-warning',
|
||||
};
|
||||
|
||||
const gradientStyles = {
|
||||
cyan: 'from-kodo-cyan to-kodo-cyan',
|
||||
magenta: 'from-kodo-magenta to-purple-600',
|
||||
lime: 'from-kodo-lime to-green-600',
|
||||
gold: 'from-kodo-gold to-orange-500',
|
||||
cyan: 'from-primary to-primary',
|
||||
magenta: 'from-destructive to-purple-600',
|
||||
lime: 'from-success to-green-600',
|
||||
gold: 'from-sumi-gold to-orange-500',
|
||||
};
|
||||
|
||||
if (variant === 'gaming') {
|
||||
|
|
@ -153,7 +153,7 @@ export const Progress = React.forwardRef<HTMLDivElement, ProgressProps>(
|
|||
aria-label={ariaLabel}
|
||||
{...props}
|
||||
>
|
||||
<div className="h-4 bg-kodo-void rounded-full overflow-hidden border border-warning/30">
|
||||
<div className="h-4 bg-background rounded-full overflow-hidden border border-warning/30">
|
||||
<div
|
||||
className={cn(
|
||||
'h-full bg-gradient-to-r shadow-gold-glow transition-all duration-[var(--duration-slow)]',
|
||||
|
|
|
|||
|
|
@ -191,7 +191,7 @@ const TableCell = React.forwardRef<
|
|||
<td
|
||||
ref={ref}
|
||||
className={cn(
|
||||
'px-4 py-3 align-middle text-sm [&:has([role=checkbox])]:pr-0 text-kodo-text-main',
|
||||
'px-4 py-3 align-middle text-sm [&:has([role=checkbox])]:pr-0 text-foreground',
|
||||
className,
|
||||
)}
|
||||
{...props}
|
||||
|
|
|
|||
|
|
@ -8,7 +8,7 @@ describe('Textarea Component', () => {
|
|||
|
||||
const textarea = screen.getByPlaceholderText('Enter text');
|
||||
expect(textarea).toBeInTheDocument();
|
||||
expect(textarea).toHaveClass('bg-kodo-graphite');
|
||||
expect(textarea).toHaveClass('bg-muted');
|
||||
});
|
||||
|
||||
it('renders with label', () => {
|
||||
|
|
@ -26,10 +26,10 @@ describe('Textarea Component', () => {
|
|||
|
||||
const error = screen.getByText('This field is required');
|
||||
expect(error).toBeInTheDocument();
|
||||
expect(error).toHaveClass('text-kodo-red');
|
||||
expect(error).toHaveClass('text-destructive');
|
||||
|
||||
const textarea = screen.getByRole('textbox');
|
||||
expect(textarea).toHaveClass('border-kodo-red');
|
||||
expect(textarea).toHaveClass('border-destructive');
|
||||
});
|
||||
|
||||
it('applies custom className', () => {
|
||||
|
|
|
|||
|
|
@ -82,8 +82,8 @@ const Textarea = React.forwardRef<HTMLTextAreaElement, TextareaProps>(
|
|||
ref={ref}
|
||||
className={cn(
|
||||
'w-full px-4 py-4',
|
||||
'bg-kodo-graphite border',
|
||||
error ? 'border-kodo-red' : 'border-border',
|
||||
'bg-muted border',
|
||||
error ? 'border-destructive' : 'border-border',
|
||||
'text-white placeholder-gray-500',
|
||||
'font-body text-base',
|
||||
'rounded-lg',
|
||||
|
|
|
|||
|
|
@ -36,7 +36,7 @@ export const BulkUploadModal: React.FC<BulkUploadModalProps> = ({
|
|||
<div className="p-8 border-b border-border bg-muted flex justify-between items-center">
|
||||
<div>
|
||||
<h3 className="font-heading font-bold text-xl text-white flex items-center gap-2">
|
||||
<Layers className="w-5 h-5 text-kodo-steel" /> Bulk Upload Manager
|
||||
<Layers className="w-5 h-5 text-muted-foreground" /> Bulk Upload Manager
|
||||
</h3>
|
||||
<p className="text-xs text-muted-foreground mt-1">
|
||||
{completedCount} / {files.length} files uploaded •{' '}
|
||||
|
|
@ -49,7 +49,7 @@ export const BulkUploadModal: React.FC<BulkUploadModalProps> = ({
|
|||
</div>
|
||||
|
||||
{/* Global Progress */}
|
||||
<div className="px-6 py-2 bg-kodo-slate/30 border-b border-border">
|
||||
<div className="px-6 py-2 bg-muted/30 border-b border-border">
|
||||
<div className="flex justify-between text-xs font-bold text-muted-foreground uppercase mb-1">
|
||||
<span>Overall Progress</span>
|
||||
<span>{Math.round(totalProgress)}%</span>
|
||||
|
|
|
|||
|
|
@ -45,7 +45,7 @@ export const FilePreviewCard: React.FC<FilePreviewCardProps> = ({
|
|||
if (file.type.startsWith('image/'))
|
||||
return <FileImage className="w-6 h-6 text-primary" />;
|
||||
if (file.type.startsWith('audio/'))
|
||||
return <FileAudio className="w-6 h-6 text-kodo-steel" />;
|
||||
return <FileAudio className="w-6 h-6 text-muted-foreground" />;
|
||||
if (file.type.includes('zip') || file.type.includes('compressed'))
|
||||
return <FolderArchive className="w-6 h-6 text-warning" />;
|
||||
return <File className="w-6 h-6 text-muted-foreground" />;
|
||||
|
|
|
|||
|
|
@ -111,7 +111,7 @@ export const CoverArtUploadModal: React.FC<CoverArtUploadModalProps> = ({
|
|||
<div className="relative w-full max-w-lg bg-card border border-border rounded-xl shadow-2xl animate-scaleIn overflow-hidden">
|
||||
<div className="p-4 border-b border-border bg-muted flex justify-between items-center">
|
||||
<h3 className="font-bold text-white flex items-center gap-2">
|
||||
<ImageIcon className="w-4 h-4 text-kodo-steel" /> Upload Artwork
|
||||
<ImageIcon className="w-4 h-4 text-muted-foreground" /> Upload Artwork
|
||||
</h3>
|
||||
<button onClick={onClose}>
|
||||
<X className="w-5 h-5 text-muted-foreground hover:text-foreground" />
|
||||
|
|
|
|||
Some files were not shown because too many files have changed in this diff Show more
Loading…
Reference in a new issue