Skip to content
Merged
Show file tree
Hide file tree
Changes from 1 commit
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 1 addition & 1 deletion apps/web/components/admin/page-editor/index.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -829,7 +829,7 @@ export default function PageEditor({
leftPaneContent === "widgets"
? EDIT_PAGE_ADD_WIDGET_TITLE
: leftPaneContent === "editor"
? "Edit Widget"
? "Edit Block"
: leftPaneContent === "fonts"
? "Fonts"
: leftPaneContent === "theme"
Expand Down
148 changes: 74 additions & 74 deletions apps/web/graphql/pages/logic.ts
Original file line number Diff line number Diff line change
Expand Up @@ -265,91 +265,91 @@ export const getPages = async (
};

export const initMandatoryPages = async (domain: Domain, user: User) => {
await PageModel.insertMany<Page>([
await PageModel.bulkWrite([
{
domain: domain._id,
pageId: defaultPages[0],
type: site,
creatorId: user.userId,
name: pageNames.home,
entityId: domain.name,
layout: [
{
name: "header",
deleteable: false,
shared: true,
},
...homePageTemplate,
{
name: "footer",
deleteable: false,
shared: true,
updateOne: {
filter: { domain: domain._id, pageId: defaultPages[0] },
update: {
$setOnInsert: {
domain: domain._id,
pageId: defaultPages[0],
type: site,
creatorId: user.userId,
name: pageNames.home,
entityId: domain.name,
layout: [
{ name: "header", deleteable: false, shared: true },
...homePageTemplate,
{ name: "footer", deleteable: false, shared: true },
],
draftLayout: [],
},
},
],
draftLayout: [],
upsert: true,
},
},
{
domain: domain._id,
pageId: defaultPages[2],
type: site,
creatorId: user.userId,
name: pageNames.privacy,
entityId: domain.name,
layout: [
{
name: "header",
deleteable: false,
shared: true,
},
{
name: "footer",
deleteable: false,
shared: true,
updateOne: {
filter: { domain: domain._id, pageId: defaultPages[2] },
update: {
$setOnInsert: {
domain: domain._id,
pageId: defaultPages[2],
type: site,
creatorId: user.userId,
name: pageNames.privacy,
entityId: domain.name,
layout: [
{ name: "header", deleteable: false, shared: true },
{ name: "footer", deleteable: false, shared: true },
],
draftLayout: [],
},
},
],
draftLayout: [],
upsert: true,
},
},
{
domain: domain._id,
pageId: defaultPages[1],
type: site,
creatorId: user.userId,
name: pageNames.terms,
entityId: domain.name,
layout: [
{
name: "header",
deleteable: false,
shared: true,
},
{
name: "footer",
deleteable: false,
shared: true,
updateOne: {
filter: { domain: domain._id, pageId: defaultPages[1] },
update: {
$setOnInsert: {
domain: domain._id,
pageId: defaultPages[1],
type: site,
creatorId: user.userId,
name: pageNames.terms,
entityId: domain.name,
layout: [
{ name: "header", deleteable: false, shared: true },
{ name: "footer", deleteable: false, shared: true },
],
draftLayout: [],
},
},
],
draftLayout: [],
upsert: true,
},
},
{
domain: domain._id,
pageId: defaultPages[3],
type: blogPage,
creatorId: user.userId,
name: pageNames.blog,
entityId: domain.name,
layout: [
{
name: "header",
deleteable: false,
shared: true,
},
{
name: "footer",
deleteable: false,
shared: true,
updateOne: {
filter: { domain: domain._id, pageId: defaultPages[3] },
update: {
$setOnInsert: {
domain: domain._id,
pageId: defaultPages[3],
type: blogPage,
creatorId: user.userId,
name: pageNames.blog,
entityId: domain.name,
layout: [
{ name: "header", deleteable: false, shared: true },
{ name: "footer", deleteable: false, shared: true },
],
draftLayout: [],
},
},
],
draftLayout: [],
upsert: true,
},
},
]);
};
Expand Down
13 changes: 6 additions & 7 deletions apps/web/ui-config/widgets.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -12,12 +12,14 @@ import {
FAQ,
Pricing,
Media,
Marquee,
Embed,
} from "@courselit/page-blocks";

function loadWidgets(): Record<string, any> {
const widgets: Record<string, Widget> = {};

// Add common widgets to CourseLit
// Adding page blocks to CourseLit
widgets[RichText.metadata.name] = RichText;
widgets[Featured.metadata.name] = Featured;
widgets[Banner.metadata.name] = Banner;
Expand All @@ -27,14 +29,11 @@ function loadWidgets(): Record<string, any> {
widgets[FAQ.metadata.name] = FAQ;
widgets[Pricing.metadata.name] = Pricing;
widgets[Media.metadata.name] = Media;
widgets[Marquee.metadata.name] = Marquee;
widgets[Embed.metadata.name] = Embed;
widgets[EmailForm.metadata.name] = EmailForm;
widgets[Footer.metadata.name] = Object.assign({}, Footer, { shared: true });
widgets[Header.metadata.name] = Object.assign({}, Header, { shared: true });
widgets[EmailForm.metadata.name] = Object.assign({}, EmailForm, {
shared: true,
});

// Additional widgets are added here
// widgets[buttondown.metadata.name] = buttondown;

return widgets;
}
Expand Down
63 changes: 58 additions & 5 deletions packages/components-library/src/admin-widget-panel.tsx
Original file line number Diff line number Diff line change
@@ -1,21 +1,74 @@
import * as React from "react";
import Section from "./section";
import {
Accordion,
AccordionContent,
AccordionItem,
AccordionTrigger,
} from "./components/ui/accordion";

interface AdminWidgetPanelContainerProps {
children: React.ReactNode;
className?: string;
type?: "single" | "multiple";
defaultValue?: string | string[];
}

export function AdminWidgetPanelContainer({
children,
className = "",
type = "multiple",
defaultValue,
}: AdminWidgetPanelContainerProps) {
return (
<div className={`flex flex-col gap-4 mb-4 ${className}`}>
{type === "single" ? (
<Accordion
type="single"
collapsible
defaultValue={defaultValue as string}
>
{children}
</Accordion>
) : (
<Accordion
type="multiple"
defaultValue={defaultValue as string[]}
>
{children}
</Accordion>
)}
</div>
);
}

interface AdminWidgetPanelProps {
title?: string;
children: React.ReactNode;
className?: string;
value: string;
defaultExpanded?: boolean;
}

export default function AdminWidgetPanel({
export function AdminWidgetPanel({
title,
children,
className = "",
value,
}: AdminWidgetPanelProps) {
if (!title) {
// If no title, render as non-collapsible section
return <Section className={className}>{children}</Section>;
}

return (
<Section className={className}>
{title && <h2 className="text-lg font-semibold">{title}</h2>}
{children}
</Section>
<AccordionItem value={value} className={className}>
<AccordionTrigger className="text-base hover:no-underline">
{title}
</AccordionTrigger>
<AccordionContent className="flex flex-col gap-4">
{children}
</AccordionContent>
</AccordionItem>
);
}
62 changes: 62 additions & 0 deletions packages/components-library/src/components/ui/alert.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,62 @@
import * as React from "react";
import { cva, type VariantProps } from "class-variance-authority";

import { cn } from "@/lib/utils";

const alertVariants = cva(
"relative w-full rounded-lg border p-4 [&>svg~*]:pl-7 [&>svg+div]:translate-y-[-3px] [&>svg]:absolute [&>svg]:left-4 [&>svg]:top-4 [&>svg]:text-foreground",
{
variants: {
variant: {
default: "bg-background text-foreground",
destructive:
"border-destructive/50 text-destructive dark:border-destructive [&>svg]:text-destructive",
},
},
defaultVariants: {
variant: "default",
},
},
);

const Alert = React.forwardRef<
HTMLDivElement,
React.HTMLAttributes<HTMLDivElement> & VariantProps<typeof alertVariants>
>(({ className, variant, ...props }, ref) => (
<div
ref={ref}
role="alert"
className={cn(alertVariants({ variant }), className)}
{...props}
/>
));
Alert.displayName = "Alert";

const AlertTitle = React.forwardRef<
HTMLParagraphElement,
React.HTMLAttributes<HTMLHeadingElement>
>(({ className, ...props }, ref) => (
<h5
ref={ref}
className={cn(
"mb-1 font-medium leading-none tracking-tight",
className,
)}
{...props}
/>
));
AlertTitle.displayName = "AlertTitle";

const AlertDescription = React.forwardRef<
HTMLParagraphElement,
React.HTMLAttributes<HTMLParagraphElement>
>(({ className, ...props }, ref) => (
<div
ref={ref}
className={cn("text-sm [&_p]:leading-relaxed", className)}
{...props}
/>
));
AlertDescription.displayName = "AlertDescription";

export { Alert, AlertTitle, AlertDescription };
8 changes: 5 additions & 3 deletions packages/components-library/src/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -11,7 +11,6 @@ import TextEditor, { emptyDoc as TextEditorEmptyDoc } from "./text-editor";
import TextRenderer from "./text-renderer";
import LessonIcon from "./lesson-icon";
import ColorSelector from "./color-selector";
import AdminWidgetPanel from "./admin-widget-panel";
import Button from "./button";
import IconButton from "./icon-button";
import Form from "./form";
Expand Down Expand Up @@ -41,14 +40,17 @@ import Tooltip from "./tooltip";
import DragAndDrop from "./drag-and-drop";

export { Button as Button2 } from "./components/ui/button";
export * from "./menu";
export * from "./components/ui/avatar";
export * from "./components/ui/accordion";
export * from "./components/ui/slider";
export * from "./components/ui/card";
export * from "./components/ui/badge";
export * from "./components/ui/skeleton";
export * from "./components/ui/textarea";
export * from "./components/ui/alert";

export * from "./admin-widget-panel";
export * from "./menu";
export * from "./toast2";
export * from "./paginated-table";
import getSymbolFromCurrency from "currency-symbol-map";
Expand All @@ -58,6 +60,7 @@ export * from "./video-with-preview";
export * from "./image";
export * from "./vertical-padding-selector";
export * from "./max-width-selector";
export * from "./lib/utils";

export {
PriceTag,
Expand All @@ -72,7 +75,6 @@ export {
TextRenderer,
LessonIcon,
ColorSelector,
AdminWidgetPanel,
Button,
IconButton,
Form,
Expand Down
Loading
Loading