diff --git a/servers/fastapi/api/v1/ppt/endpoints/slide_to_html.py b/servers/fastapi/api/v1/ppt/endpoints/slide_to_html.py index 221b3aa4..93b71e16 100644 --- a/servers/fastapi/api/v1/ppt/endpoints/slide_to_html.py +++ b/servers/fastapi/api/v1/ppt/endpoints/slide_to_html.py @@ -73,6 +73,11 @@ class GetLayoutsResponse(BaseModel): message: Optional[str] = None +class DeleteLayoutResponse(BaseModel): + success: bool + message: Optional[str] = None + + class PresentationSummary(BaseModel): presentation_id: str layout_count: int @@ -917,4 +922,40 @@ async def get_presentations_summary( raise HTTPException( status_code=500, detail=f"Internal server error while retrieving presentations summary: {str(e)}" - ) \ No newline at end of file + ) + + + +# ENDPOINT : Delete a layout +@LAYOUT_MANAGEMENT_ROUTER.delete( + "/delete-layouts/{presentation_id}", + response_model=DeleteLayoutResponse, + responses={ + 200: {"model": DeleteLayoutResponse, "description": "Layout deleted successfully"}, + 404: {"model": ErrorResponse, "description": "Presentation Layouts not found"}, + 500: {"model": ErrorResponse, "description": "Internal server error"} + } +) +async def delete_layouts(presentation_id: str, session: AsyncSession = Depends(get_async_session)): + try: + # Validate presentation_id format (basic UUID check) + if not presentation_id or len(presentation_id.strip()) == 0: + raise HTTPException( + status_code=400, + detail="Presentation ID cannot be empty" + ) + # Delete Presentation with all layouts + await session.execute(delete(PresentationLayoutCodeModel).where(PresentationLayoutCodeModel.presentation_id == presentation_id)) + await session.commit() + return DeleteLayoutResponse( + success=True, + message=f"Successfully deleted layout(s) for presentation {presentation_id}" + ) + except HTTPException: + raise + except Exception as e: + print(f"Error deleting layouts for presentation {presentation_id}: {str(e)}") + raise HTTPException( + status_code=500, + detail=f"Internal server error while deleting layouts: {str(e)}" + ) \ No newline at end of file diff --git a/servers/fastapi/chroma/chroma.sqlite3 b/servers/fastapi/chroma/chroma.sqlite3 index c35454c7..4e033503 100644 Binary files a/servers/fastapi/chroma/chroma.sqlite3 and b/servers/fastapi/chroma/chroma.sqlite3 differ diff --git a/servers/nextjs/app/(presentation-generator)/components/ImageEditor.tsx b/servers/nextjs/app/(presentation-generator)/components/ImageEditor.tsx index 820cf60c..29e67cc6 100644 --- a/servers/nextjs/app/(presentation-generator)/components/ImageEditor.tsx +++ b/servers/nextjs/app/(presentation-generator)/components/ImageEditor.tsx @@ -275,7 +275,7 @@ const ImageEditor = ({ {/* Generate Tab */} - +

Current Prompt

@@ -333,7 +333,7 @@ const ImageEditor = ({

Previous Generated Images

-
+
{previousGeneratedImages.map((image) => (
handleImageChange(image.path)} diff --git a/servers/nextjs/app/(presentation-generator)/context/LayoutContext.tsx b/servers/nextjs/app/(presentation-generator)/context/LayoutContext.tsx index 6b8fe710..3609d8ef 100644 --- a/servers/nextjs/app/(presentation-generator)/context/LayoutContext.tsx +++ b/servers/nextjs/app/(presentation-generator)/context/LayoutContext.tsx @@ -85,7 +85,8 @@ const compileCustomLayout = (layoutCode: string, React: any, z: any) => { .replace(/import\s+.*\s+from\s+['"]zod['"];?/g, "") // remove every zod import (any style) .replace(/import\s+.*\s+from\s+['"]zod['"];?/g, "") - .replace(/const\s+[^=]*=\s*require\(['"]zod['"]\);?/g, ""); + .replace(/const\s+[^=]*=\s*require\(['"]zod['"]\);?/g, "") + .replace(/Looking at this HTML structure, I can see it's a slide layout with a header, title, description, and a 2x2 grid of images with captions, plus footer elements.?/g, "") const compiled = Babel.transform(cleanCode, { presets: [ ["react", { runtime: "classic" }], diff --git a/servers/nextjs/app/layout-preview/[slug]/page.tsx b/servers/nextjs/app/layout-preview/[slug]/page.tsx index 6dd7cd2c..22570da2 100644 --- a/servers/nextjs/app/layout-preview/[slug]/page.tsx +++ b/servers/nextjs/app/layout-preview/[slug]/page.tsx @@ -5,14 +5,14 @@ import { useParams, useRouter } from "next/navigation"; import LoadingStates from "../components/LoadingStates"; import { Card } from "@/components/ui/card"; import { Button } from "@/components/ui/button"; -import { ArrowLeft, Home } from "lucide-react"; +import { ArrowLeft, Home, Trash2 } from "lucide-react"; import { useLayout } from "@/app/(presentation-generator)/context/LayoutContext"; const GroupLayoutPreview = () => { const params = useParams(); const router = useRouter(); const slug = params.slug as string; - const { getFullDataByGroup, loading } = useLayout(); + const { getFullDataByGroup, loading,refetch } = useLayout(); const layoutGroup = getFullDataByGroup(slug); useEffect(() => { @@ -36,7 +36,17 @@ const GroupLayoutPreview = () => { if (!layoutGroup || layoutGroup.length === 0) { return ; } - + const deleteLayouts = async () => { + const presentationId = slug.replace('custom-',''); + refetch(); + router.back(); + const response = await fetch(`/api/v1/ppt/layout-management/delete-layouts/${presentationId}`, { + method: "DELETE", + }); + if (response.ok) { + router.push("/layout-preview"); + } + } return (
{/* Header */} @@ -62,6 +72,9 @@ const GroupLayoutPreview = () => { All Groups + {slug.includes('custom-') && }
@@ -73,6 +86,7 @@ const GroupLayoutPreview = () => { {layoutGroup[0].groupName}

+