1import{h as L,i as $,a9 as Se,aM as ne,r as o,l as v,ab as c,j as e,d as C,m as N,w as ie,n as oe,$ as M,a0 as O,a1 as R,a2 as E,aN as F,f0 as T,Q as ke}from"./main-DnofrhMJ.js";import{D as Ie}from"./dashboard-layout-D_EAeOja.js";import{u as Pe,a as De,P as ze,D as de,c as le,S as ce,v as me,b as ue,d as pe,C as he,I as fe}from"./sortable.esm-D5yCBxh3.js";import{a as q}from"./admin-middleware-BFY-mU53.js";import{b as Me,c as Oe,u as Re,f as Ee,s as ye}from"./admin-showcase-BzmcJioI.js";import{I as xe}from"./IconRefresh-DPUynl-u.js";import{I as ge}from"./IconPlus-B9mIVI_s.js";import{I as Fe}from"./IconCategory-Bk-JBLrj.js";import{I as X}from"./IconTrash-Bcm0yLOE.js";import{I as Te}from"./IconWorld-DalpFMha.js";import{I as je}from"./IconArrowsLeftRight-5hP2-2e-.js";const Le=L({method:"GET"}).middleware([q]).handler($("b73a24b961eeacb88dafb32c82bbc65b3fd31c140c92f6e67beca2b9f9d1da4d")),$e=L({method:"POST"}).middleware([q]).handler($("6089e3311b6f46ae52313afcc9b10e25be1afa37442db003e9cf9c429b1d4e41")),be=L({method:"POST"}).middleware([q]).handler($("b56f9b6201ce58ffaf92671112776a1ca649ead012dfc5b3efcd0f52d824553c")),qe=L({method:"POST"}).middleware([q]).handler($("8f7b49506ca96d4f9132c99388fecf0c6e7e5b920d9795127c19ecb8c6b29ae4")),Ge=L({method:"POST"}).middleware([q]).handler($("92b8002d66fe7dedf77da6ae61940b828f2ab0b3249a2705cb7c3d680b92cd95")),Qe=["en","zh","ja","de","fr","es","ru","ko"];function Ke(){const t=Se(),m=ne({queryKey:["admin-gallery-categories"],queryFn:()=>Le(),staleTime:3e4}),b=ne({queryKey:["admin-showcase-all"],queryFn:()=>Me(),staleTime:3e4}),u=()=>t.invalidateQueries({queryKey:["admin-gallery-categories"]}),p=()=>t.invalidateQueries({queryKey:["admin-showcase-all"]}),i=o.useMemo(()=>m.data??[],[m.data]),[l,h]=o.useState(null);o.useEffect(()=>{l||i.length===0||h(i[0].slug)},[i,l]);const n=o.useMemo(()=>i.find(s=>s.slug===l)??null,[i,l]),d=o.useMemo(()=>[...b.data??[]].filter(r=>r.category===l).sort((r,a)=>r.sortOrder-a.sortOrder),[b.data,l]),w=v({mutationFn:async s=>{await Ge({data:{orders:s.map((r,a)=>({id:r.id,sortOrder:a}))}})},onSuccess:u,onError:s=>c.error(`Reorder categories failed: ${s.message}`)}),ve=v({mutationFn:async s=>{await Oe({data:{orders:s.map((r,a)=>({id:r.id,sortOrder:a}))}})},onSuccess:p,onError:s=>c.error(`Reorder items failed: ${s.message}`)}),[f,G]=o.useState(null),[Q,J]=o.useState(""),Ne=s=>{G(s);const r=i.find(a=>a.slug!==s.category);J(r?.slug??"")},S=v({mutationFn:async()=>{!f||!Q||await Re({data:{id:f.id,category:Q}})},onSuccess:()=>{c.success("Moved"),G(null),p()},onError:s=>c.error(`Move failed: ${s.message}`)}),[K,A]=o.useState(null),k=v({mutationFn:async()=>{K&&await Ee({data:{id:K.id}})},onSuccess:()=>{c.success("Item removed from gallery"),A(null),p()},onError:s=>c.error(`Delete failed: ${s.message}`)}),Y=Pe(De(ze,{activationConstraint:{distance:4}}
1)),[Ce,H]=o.useState(!1),[U,Z]=o.useState(""),[ee,se]=o.useState(""),I=v({mutationFn:async()=>await $e({data:{slug:U.trim(),name:ee.trim()||U.trim(),isPublic:!0}}),onSuccess:s=>{c.success("Category created"),H(!1),Z(""),se(""),u();const r=m.data?.find(a=>a.id===s.id);r&&h(r.slug)},onError:s=>c.error(`Create failed: ${s.message}`)}),[P,_]=o.useState(null),[te,re]=o.useState(""),[V,ae]=o.useState({}),we=s=>{_(s),re(s.name),ae(s.nameI18n??{})},D=v({mutationFn:async()=>{P&&await be({data:{id:P.id,name:te.trim()||P.name,nameI18n:Object.keys(V).length>0?V:null}})},onSuccess:()=>{c.success("Saved"),_(null),u()},onError:s=>c.error(`Save failed: ${s.message}`)}),[x,B]=o.useState(null),z=v({mutationFn:async()=>{x&&await qe({data:{id:x.id}})},onSuccess:()=>{c.success("Category deleted");const s=x?.slug===l;B(null),u(),s&&h(null)},onError:s=>c.error(`Delete failed: ${s.message}`)});return e.jsxs("div",{className:"grid grid-cols-1 gap-4 lg:grid-cols-[320px_1fr]",children:[e.jsxs("div",{className:"rounded-xl border border-border bg-card overflow-hidden flex flex-col",children:[e.jsxs("div",{className:"flex items-center justify-between border-b border-border bg-muted/40 px-3 py-2",children:[e.jsx("span",{className:"text-sm font-semibold",children:"Categories"}),e.jsxs("div",{className:"flex items-center gap-1",children:[e.jsx("button",{type:"button",onClick:()=>t.invalidateQueries({queryKey:["admin-gallery-categories"]}),disabled:m.isFetching,className:"rounded-md border border-border bg-background p-1 hover:bg-accent disabled:opacity-50",title:"Refresh",children:e.jsx(xe,{className:C("size-3.5",m.isFetching&&"animate-spin")})}),e.jsxs("button",{type:"button",onClick:()=>H(!0),className:"inline-flex items-center gap-1 rounded-md bg-primary px-2 py-1 text-xs font-bold text-primary-foreground hover:bg-primary/90",children:[e.jsx(ge,{className:"size-3.5"})," New"]})]})]}),i.length===0?e.jsx("div",{className:"p-6 text-center text-xs text-muted-foreground",children:m.isLoading?e.jsxs("span",{className:"inline-flex items-center gap-2",children:[e.jsx(N,{className:"size-4 animate-spin"})," Loadingâ¦"]}):"No categories"}):e.jsx(de,{sensors:Y,collisionDetection:le,onDragEnd:s=>{const{active:r,over:a}=s;if(!a||r.id===a.id)return;const y=i.findIndex(j=>j.id===r.id),g=i.findIndex(j=>j.id===a.id);if(y<0||g<0)return;const W=ue(i,y,g);w.mutate(W)},children:e.jsx(ce,{items:i.map(s=>s.id),strategy:me,children:e.jsx("ul",{className:"divide-y divide-border",children:i.map(s=>e.jsx(Ae,{cat:s,selected:s.slug===l,onSelect:()=>h(s.slug)},s.id))})})})]}),e.jsxs("div",{className:"rounded-xl border border-border bg-card overflow-hidden flex flex-col",children:[e.jsxs("div",{className:"flex items-center justify-between border-b border-border bg-muted/40 px-3 py-2",children:[e.jsxs("div",{className:"flex items-center gap-2 min-w-0",children:[e.jsx(Fe,{className:"size-4 text-muted-foreground shrink-0"}),e.jsx("span",{className:"text-sm font-semibold truncate",children:n?.name??"â"}),n&&e.jsxs(e.Fragment,{children:[e.jsx("span",{className:"text-[11px] font-mono text-muted-foreground shrink-0",children:n.slug}),e.jsxs("span",{className:"text-xs text-muted-foreground shrink-0",children:["· ",d.length," item",d.length===1?"":"s"]})]})]}),e.jsx("button",{type:"button",onClick:p,disabled:b.isFetching,className:"rounded-md border border-border bg-background p-1 hover:bg-accent disabled:opacity-50",title:"Refresh items",children:e.jsx(xe,{className:C("size-3.5",b.isFetching&&"animate-spin")})})]}),n&&e.jsxs("div",{className:"flex items-center gap-2 flex-wrap border-b border-border bg-card/40 px-3 py-2",children:[e.jsxs("button",{type:"button",onClick:()=>we(n),className:"inline-flex items-center gap-1 rounded-md border border-border bg-background px-2.5 py-1 text-xs font-medium hover:bg-accent",title:"Edit name + per-locale translations",children:[e.jsx(ie,{className:"size-3.5"})," Edit name"]}),e.jsxs("button",{type:"button",onClick:()=>be({data:{id:n.id,isPublic:!n.isPublic}}).then(u),className:C("inline-flex items-center gap-1 rounded-md px-2.5 py-1 text-xs font-medium border",n.isPublic?"border-emerald-500/40 bg-emerald-500/10 text-emerald-700 dark:text-emerald-400 hover:bg-emerald-500/15":"border-border bg-background text-muted-foreground hover:bg-accent"),title:n.isPublic?"Click to hide from public gallery":"Click to publish to public gallery",children:[e.jsx(oe,{className:"size-3.5"}),n.isPublic?"Public":"Hidden"]}),e.jsxs("button",{type:"button",onClick:()=>B(n),disabled:n.itemCount>0,className:"inline-flex items-center gap-1 rounded-md border border-destructive/40 bg-destructive/5 px-2.5 py-1 text-xs font-medium text-destructive hover:bg-destructive/10 disabled:opacity-30 disabled:cursor-not-allowed",title:n.itemCount>0?"Reassign items first":"Delete this category",children:[e.jsx(X,{className:"size-3.5"})," Delete category"]})]}),n?d.length===0?e.jsx("div",{className:"p-10 text-center text-sm text-muted-foreground",children:"No items in this category yet. Add items via the asset-builder or ç´ ææä»¶ page."}):e.jsx(de,{sensors:Y,collisionDetection:le,onDragEnd:s=>{const{active:r,over:a}=s;
1if(!a||r.id===a.id)return;const y=d.findIndex(j=>j.id===r.id),g=d.findIndex(j=>j.id===a.id);if(y<0||g<0)return;const W=ue(d,y,g);ve.mutate(W)},children:e.jsx(ce,{items:d.map(s=>s.id),strategy:me,children:e.jsx("ul",{className:"divide-y divide-border",children:d.map(s=>e.jsx(He,{item:s,onMove:()=>Ne(s),onDelete:()=>A(s),canMove:i.length>1},s.id))})})}):e.jsx("div",{className:"p-10 text-center text-sm text-muted-foreground",children:"Pick a category on the left."})]}),e.jsx(M,{open:Ce,onOpenChange:s=>{!s&&!I.isPending&&H(!1)},children:e.jsxs(O,{className:"sm:max-w-md",children:[e.jsxs(R,{children:[e.jsx(E,{children:"New category"}),e.jsxs(F,{children:["Slug is the URL-safe id stored in ",e.jsx("code",{className:"text-xs",children:"showcase_item.category"}),". Lowercase, dashes only."]})]}),e.jsxs("div",{className:"space-y-3",children:[e.jsxs("div",{className:"space-y-1.5",children:[e.jsx("label",{className:"text-xs font-medium",children:"Slug"}),e.jsx("input",{type:"text",value:U,onChange:s=>Z(s.target.value),placeholder:"e.g. landscape",className:"w-full rounded-md border border-border bg-background px-2.5 py-1.5 text-sm font-mono focus:outline-none focus:ring-2 focus:ring-ring"})]}),e.jsxs("div",{className:"space-y-1.5",children:[e.jsx("label",{className:"text-xs font-medium",children:"Display name"}),e.jsx("input",{type:"text",value:ee,onChange:s=>se(s.target.value),placeholder:"(defaults to slug)",className:"w-full rounded-md border border-border bg-background px-2.5 py-1.5 text-sm focus:outline-none focus:ring-2 focus:ring-ring"})]})]}),e.jsxs(T,{children:[e.jsx("button",{type:"button",onClick:()=>H(!1),disabled:I.isPending,className:"rounded-md border border-border bg-background px-3 py-1.5 text-sm font-medium hover:bg-accent disabled:opacity-50",children:"Cancel"}),e.jsxs("button",{type:"button",onClick:()=>I.mutate(),disabled:I.isPending||!U.trim(),className:"inline-flex items-center gap-1.5 rounded-md bg-primary px-3 py-1.5 text-sm font-bold text-primary-foreground hover:bg-primary/90 disabled:opacity-50",children:[I.isPending?e.jsx(N,{className:"size-4 animate-spin"}):e.jsx(ge,{className:"size-4"}),"Create"]})]})]})}),e.jsx(M,{open:!!P,onOpenChange:s=>{!s&&!D.isPending&&_(null)},children:e.jsxs(O,{className:"sm:max-w-lg",children:[e.jsxs(R,{children:[e.jsx(E,{children:"Edit category"}),e.jsx(F,{children:"Locale overrides drop back to the base name when empty."})]}),P&&e.jsxs("div",{className:"space-y-3",children:[e.jsxs("div",{className:"space-y-1.5",children:[e.jsxs("label",{className:"text-xs font-medium flex items-center gap-1",children:[e.jsx(Te,{className:"size-3.5"})," Base name (fallback)"]}),e.jsx("input",{type:"text",value:te,onChange:s=>re(s.target.value),className:"w-full rounded-md border border-border bg-background px-2.5 py-1.5 text-sm focus:outline-none focus:ring-2 focus:ring-ring"})]}),e.jsxs("div",{className:"space-y-2",children:[e.jsxs("div",{className:"text-xs font-medium flex items-center gap-1",children:[e.jsx(ie,{className:"size-3.5"})," Per-locale overrides"]}),Qe.map(s=>e.jsxs("div",{className:"flex items-center gap-2",children:[e.jsx("span",{className:"w-12 shrink-0 text-[11px] font-mono uppercase text-muted-foreground",children:s}),e.jsx("input",{type:"text",value:V[s]??"",onChange:r=>{const a=r.target.value;ae(y=>{const g={...y};return a.trim()?g[s]=a:delete g[s],g})},placeholder:"(uses base name)",className:"flex-1 rounded-md border border-border bg-background px-2.5 py-1 text-sm focus:outline-none focus:ring-2 focus:ring-ring"})]},s))]})]}),e.jsxs(T,{children:[e.jsx("button",{type:"button",onClick:()=>_(null),disabled:D.isPending,className:"rounded-md border border-border bg-background px-3 py-1.5 text-sm font-medium hover:bg-accent disabled:opacity-50",children:"Cancel"}),e.jsxs("button",{type:"button",onClick:()=>D.mutate(),disabled:D.isPending,className:"inline-flex items-center gap-1.5 rounded-md bg-primary px-3 py-1.5 text-sm font-bold text-primary-foreground hover:bg-primary/90 disabled:opacity-50",children:[D.isPending?e.jsx(N,{className:"size-4 animate-spin"}):e.jsx(oe,{className:"size-4"}),"Save"]})]})]})}),e.jsx(M,{open:!!f,onOpenChange:s=>{!s&&!S.isPending&&G(null)},children:e.jsxs(O,{className:"sm:max-w-md",children:[e.jsxs(R,{children:[e.jsxs(E,{children:['Move "',f?.title,'"']}),e.jsx(F,{children:"Showcase items always belong to a category, so removing means moving â pick a destination."})]}),f&&e.jsxs("div",{className:"space-y-3",children:[e.jsx("div",{className:"flex justify-center",children:e.jsx("img",{src:ye(f.imageKey),alt:"",className:"max-h-32 rounded-md ring-1 ring-border"})}),e.jsxs("div",{className:"space-y-1.5",children:[e.jsx("label",{className:"text-xs font-medium",children:"Destination"}),e.jsx("select",{value:Q,onChange:s=>J(s.target.value),className:"w-full rounded-md border border-border bg-background px-2.5 py-1.5 text-sm focus:outline-none focus:ring-2 focus:ring-ring",children:i.filter(s=>s.slug!==f.category).map(s=>
1e.jsxs("option",{value:s.slug,children:[s.name," (",s.slug,")"]},s.slug))})]})]}),e.jsxs(T,{children:[e.jsx("button",{type:"button",onClick:()=>G(null),disabled:S.isPending,className:"rounded-md border border-border bg-background px-3 py-1.5 text-sm font-medium hover:bg-accent disabled:opacity-50",children:"Cancel"}),e.jsxs("button",{type:"button",onClick:()=>S.mutate(),disabled:S.isPending||!Q,className:"inline-flex items-center gap-1.5 rounded-md bg-primary px-3 py-1.5 text-sm font-bold text-primary-foreground hover:bg-primary/90 disabled:opacity-50",children:[S.isPending?e.jsx(N,{className:"size-4 animate-spin"}):e.jsx(je,{className:"size-4"}),"Move"]})]})]})}),e.jsx(M,{open:!!K,onOpenChange:s=>{!s&&!k.isPending&&A(null)},children:e.jsxs(O,{className:"sm:max-w-md",children:[e.jsxs(R,{children:[e.jsxs(E,{children:['Delete "',K?.title,'"?']}),e.jsx(F,{children:"Removes this entry from the showcase entirely. The R2 image stays â only the gallery row is dropped."})]}),e.jsxs(T,{children:[e.jsx("button",{type:"button",onClick:()=>A(null),disabled:k.isPending,className:"rounded-md border border-border bg-background px-3 py-1.5 text-sm font-medium hover:bg-accent disabled:opacity-50",children:"Cancel"}),e.jsxs("button",{type:"button",onClick:()=>k.mutate(),disabled:k.isPending,className:"inline-flex items-center gap-1.5 rounded-md bg-destructive px-3 py-1.5 text-sm font-bold text-destructive-foreground hover:bg-destructive/90 disabled:opacity-50",children:[k.isPending?e.jsx(N,{className:"size-4 animate-spin"}):e.jsx(X,{className:"size-4"}),"Delete"]})]})]})}),e.jsx(M,{open:!!x,onOpenChange:s=>{!s&&!z.isPending&&B(null)},children:e.jsxs(O,{className:"sm:max-w-md",children:[e.jsxs(R,{children:[e.jsxs(E,{children:['Delete "',x?.slug,'"?']}),e.jsx(F,{children:x&&x.itemCount>0?`This category still has ${x.itemCount} item${x.itemCount===1?"":"s"}. Reassign or delete them first â the server will refuse this request otherwise.`:"Removes the category metadata only. Showcase items keep their .category string but will be orphaned until the slug is recreated."})]}),e.jsxs(T,{children:[e.jsx("button",{type:"button",onClick:()=>B(null),disabled:z.isPending,className:"rounded-md border border-border bg-background px-3 py-1.5 text-sm font-medium hover:bg-accent disabled:opacity-50",children:"Cancel"}),e.jsxs("button",{type:"button",onClick:()=>z.mutate(),disabled:z.isPending,className:"inline-flex items-center gap-1.5 rounded-md bg-destructive px-3 py-1.5 text-sm font-bold text-destructive-foreground hover:bg-destructive/90 disabled:opacity-50",children:[z.isPending?e.jsx(N,{className:"size-4 animate-spin"}):e.jsx(ke,{className:"size-4"}),"Delete"]})]})]})})]})}function Ae({cat:t,selected:m,onSelect:b}){const{attributes:u,listeners:p,setNodeRef:i,transform:l,transition:h,isDragging:n}=pe({id:t.id}),d={transform:he.Transform.toString(l),transition:h,opacity:n?.5:1,zIndex:n?10:void 0};return e.jsxs("li",{ref:i,style:d,className:C("flex items-center gap-2 px-2 py-2 transition-colors cursor-pointer",m?"bg-primary/10":"hover:bg-muted/40"),onClick:b,children:[e.jsx("button",{type:"button",...u,...p,onClick:w=>w.stopPropagation(),className:"cursor-grab active:cursor-grabbing text-muted-foreground/40 hover:text-muted-foreground touch-none p-0.5",title:"Drag to reorder",children:e.jsx(fe,{className:"size-4"})}),e.jsxs("div",{className:"min-w-0 flex-1",children:[e.jsxs("div",{className:"flex items-center gap-1.5 min-w-0",children:[e.jsx("span",{className:C("truncate text-sm font-medium",m&&"text-primary"),children:t.name}),e.jsx("span",{className:"shrink-0 text-[10px] font-mono text-muted-foreground/60",children:t.slug})]}),e.jsxs("div",{className:"flex items-center gap-2 mt-0.5 text-[11px] text-muted-foreground",children:[e.jsxs("span",{children:[t.itemCount," item",t.itemCount===1?"":"s"]}),t.nameI18n&&Object.keys(t.nameI18n).length>0&&e.jsxs("span",{children:["· ",Object.keys(t.nameI18n).length," locale",Object.keys(t.nameI18n).length===1?"":"s"]}),!t.isPublic&&e.jsx("span",{className:"text-amber-600",children:"· Hidden"})]})]})]})}function He({item:t,onMove:m,onDelete:b,canMove:u}){const{attributes:p,listeners:i,setNodeRef:l,transform:h,transition:n,isDragging:d}
1=pe({id:t.id}),w={transform:he.Transform.toString(h),transition:n,opacity:d?.5:1,zIndex:d?10:void 0};return e.jsxs("li",{ref:l,style:w,className:"group flex items-center gap-3 px-3 py-2 hover:bg-muted/30",children:[e.jsx("button",{type:"button",...p,...i,className:"cursor-grab active:cursor-grabbing text-muted-foreground/40 hover:text-muted-foreground touch-none p-0.5",title:"Drag to reorder",children:e.jsx(fe,{className:"size-4"})}),e.jsx("img",{src:ye(t.imageKey),alt:"",className:"size-12 shrink-0 rounded-md object-cover ring-1 ring-border"}),e.jsxs("div",{className:"min-w-0 flex-1",children:[e.jsx("div",{className:"truncate text-sm font-medium",children:t.title}),e.jsx("div",{className:"truncate text-[11px] text-muted-foreground",children:t.prompt})]}),e.jsxs("span",{className:"shrink-0 text-[11px] text-muted-foreground tabular-nums",children:["#",t.sortOrder]}),e.jsx("span",{className:C("shrink-0 rounded-full px-2 py-0.5 text-[10px] font-medium",t.isPublic?"bg-emerald-500/10 text-emerald-600":"bg-muted text-muted-foreground"),children:t.isPublic?"Public":"Hidden"}),e.jsxs("div",{className:"flex shrink-0 items-center gap-1 opacity-0 group-hover:opacity-100 transition-opacity",children:[e.jsxs("button",{type:"button",onClick:m,disabled:!u,className:"inline-flex items-center gap-1 rounded-md border border-border bg-background px-2 py-1 text-[11px] font-medium hover:bg-accent disabled:opacity-30 disabled:cursor-not-allowed",title:u?"Move to another category":"No other category to move to",children:[e.jsx(je,{className:"size-3"})," Move"]}),e.jsxs("button",{type:"button",onClick:b,className:"inline-flex items-center gap-1 rounded-md border border-destructive/40 bg-destructive/5 px-2 py-1 text-[11px] font-semibold text-destructive hover:bg-destructive/10",title:"Remove from gallery (deletes the showcase entry)",children:[e.jsx(X,{className:"size-3"})," Delete"]})]})]})}function ts(){return e.jsx(Ie,{title:"Gallery åç±»",description:"管ç gallery åç±»ï¼åç§°ãå½é
åãæ¾ç¤ºé¡ºåºãå¯è§æ§ã",children:e.jsx(Ke,{})})}export{ts as component};
Line numbers count LF bytes from the start of the resource, as the search results do. Vendor segments are library code the classifier recognised; they are stored but not indexed. Bytes are shown as Latin1 characters, one per byte.