Add loading state and style constants, enhance API key modal with delete
This commit is contained in:
@@ -1,18 +1,12 @@
|
||||
"use client"
|
||||
|
||||
import { useState, useRef, useEffect } from "react"
|
||||
import { useState, useRef, useEffect, useMemo } from "react"
|
||||
import { Upload, X, Loader2 } from "lucide-react"
|
||||
import { Button } from "@/components/ui/button"
|
||||
import { Dialog, DialogContent, DialogHeader, DialogTitle } from "@/components/ui/dialog"
|
||||
import { useToast } from "@/hooks/use-toast"
|
||||
import { validateFileForUpload, generateFilePreview } from "@/lib/file-utils"
|
||||
|
||||
const COMIC_STYLES = [
|
||||
{ id: "american-modern", name: "American Modern" },
|
||||
{ id: "manga", name: "Manga" },
|
||||
{ id: "noir", name: "Noir" },
|
||||
{ id: "vintage", name: "Vintage" },
|
||||
]
|
||||
import { COMIC_STYLES } from "@/lib/constants"
|
||||
|
||||
interface GeneratePageModalProps {
|
||||
isOpen: boolean
|
||||
@@ -51,7 +45,11 @@ export function GeneratePageModal({
|
||||
const fileInputRef = useRef<HTMLInputElement>(null)
|
||||
const { toast } = useToast()
|
||||
|
||||
const selectedStyle = previousPageStyle || "noir"
|
||||
const selectedStyleId = previousPageStyle || "noir"
|
||||
const selectedStyle = useMemo(
|
||||
() => COMIC_STYLES.find((s) => s.id === selectedStyleId)?.name || "Noir",
|
||||
[selectedStyleId]
|
||||
)
|
||||
|
||||
useEffect(() => {
|
||||
if (previousCharacters && previousCharacters.length > 0) {
|
||||
|
||||
@@ -1,29 +1,39 @@
|
||||
"use client"
|
||||
"use client";
|
||||
|
||||
import { FileText, ImageIcon, Palette } from "lucide-react"
|
||||
import { Sheet, SheetContent, SheetHeader, SheetTitle } from "@/components/ui/sheet"
|
||||
import { FileText, ImageIcon, Palette } from "lucide-react";
|
||||
import {
|
||||
Sheet,
|
||||
SheetContent,
|
||||
SheetHeader,
|
||||
SheetTitle,
|
||||
} from "@/components/ui/sheet";
|
||||
import { COMIC_STYLES } from "@/lib/constants";
|
||||
|
||||
interface PageData {
|
||||
id: number
|
||||
title: string
|
||||
image: string
|
||||
prompt: string
|
||||
characterUploads?: string[]
|
||||
style: string
|
||||
id: number;
|
||||
title: string;
|
||||
image: string;
|
||||
prompt: string;
|
||||
characterUploads?: string[];
|
||||
style: string;
|
||||
}
|
||||
|
||||
interface PageInfoSheetProps {
|
||||
isOpen: boolean
|
||||
onClose: () => void
|
||||
page: PageData
|
||||
isOpen: boolean;
|
||||
onClose: () => void;
|
||||
page: PageData;
|
||||
}
|
||||
|
||||
export function PageInfoSheet({ isOpen, onClose, page }: PageInfoSheetProps) {
|
||||
const styleName = COMIC_STYLES.find((s) => s.id === page.style)?.name || page.style;
|
||||
|
||||
return (
|
||||
<Sheet open={isOpen} onOpenChange={onClose}>
|
||||
<SheetContent className="w-full sm:max-w-md border-l border-border/50 bg-background px-6">
|
||||
<SheetHeader className="pb-4 border-b border-border/50 px-0">
|
||||
<SheetTitle className="text-base font-medium text-white">Page {page.id} Details</SheetTitle>
|
||||
<SheetTitle className="text-base font-medium text-white">
|
||||
Page {page.id} Details
|
||||
</SheetTitle>
|
||||
</SheetHeader>
|
||||
|
||||
<div className=" space-y-6">
|
||||
@@ -34,7 +44,9 @@ export function PageInfoSheet({ isOpen, onClose, page }: PageInfoSheetProps) {
|
||||
<span>Prompt</span>
|
||||
</div>
|
||||
<div className="p-3 glass-panel rounded-lg">
|
||||
<p className="text-sm text-foreground leading-relaxed">{page.prompt}</p>
|
||||
<p className="text-sm text-foreground leading-relaxed">
|
||||
{page.prompt}
|
||||
</p>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
@@ -45,7 +57,7 @@ export function PageInfoSheet({ isOpen, onClose, page }: PageInfoSheetProps) {
|
||||
<span>Style</span>
|
||||
</div>
|
||||
<div className="inline-flex items-center px-3 py-1.5 glass-panel rounded-md">
|
||||
<span className="text-sm text-foreground">{page.style}</span>
|
||||
<span className="text-sm text-foreground">{styleName}</span>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
@@ -57,7 +69,10 @@ export function PageInfoSheet({ isOpen, onClose, page }: PageInfoSheetProps) {
|
||||
{page.characterUploads && page.characterUploads.length > 0 ? (
|
||||
<div className="flex gap-2">
|
||||
{page.characterUploads.map((upload, index) => (
|
||||
<div key={index} className="relative h-24 w-24 rounded-lg overflow-hidden glass-panel">
|
||||
<div
|
||||
key={index}
|
||||
className="relative h-24 w-24 rounded-lg overflow-hidden glass-panel"
|
||||
>
|
||||
<img
|
||||
src={upload || "/placeholder.svg"}
|
||||
alt={`Uploaded character ${index + 1}`}
|
||||
@@ -68,12 +83,14 @@ export function PageInfoSheet({ isOpen, onClose, page }: PageInfoSheetProps) {
|
||||
</div>
|
||||
) : (
|
||||
<div className="p-4 glass-panel rounded-lg text-center">
|
||||
<p className="text-sm text-muted-foreground">No characters uploaded</p>
|
||||
<p className="text-sm text-muted-foreground">
|
||||
No characters uploaded
|
||||
</p>
|
||||
</div>
|
||||
)}
|
||||
</div>
|
||||
|
||||
{/* Generated Image Preview */}
|
||||
{/* Generated Image Preview
|
||||
<div className="space-y-2">
|
||||
<div className="flex items-center gap-2 text-[10px] font-semibold uppercase tracking-wider text-muted-foreground">
|
||||
<ImageIcon className="w-3.5 h-3.5" />
|
||||
@@ -86,9 +103,9 @@ export function PageInfoSheet({ isOpen, onClose, page }: PageInfoSheetProps) {
|
||||
className="w-full h-full object-cover"
|
||||
/>
|
||||
</div>
|
||||
</div>
|
||||
</div> */}
|
||||
</div>
|
||||
</SheetContent>
|
||||
</Sheet>
|
||||
)
|
||||
);
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user