diff --git a/apps/web/vibes/soul/docs/account-layout.mdx b/apps/web/vibes/soul/docs/account-layout.mdx deleted file mode 100644 index f88470c58..000000000 --- a/apps/web/vibes/soul/docs/account-layout.mdx +++ /dev/null @@ -1,5 +0,0 @@ ---- -title: Account Layout -preview: account-layout-example -previewSize: lg ---- diff --git a/apps/web/vibes/soul/docs/sticky-sidebar-layout.mdx b/apps/web/vibes/soul/docs/sticky-sidebar-layout.mdx new file mode 100644 index 000000000..e126e8555 --- /dev/null +++ b/apps/web/vibes/soul/docs/sticky-sidebar-layout.mdx @@ -0,0 +1,5 @@ +--- +title: Sticky Sidebar Layout +preview: sticky-sidebar-layout-example +previewSize: lg +--- diff --git a/apps/web/vibes/soul/examples.ts b/apps/web/vibes/soul/examples.ts index 7a33ba3de..8f251c096 100644 --- a/apps/web/vibes/soul/examples.ts +++ b/apps/web/vibes/soul/examples.ts @@ -13,11 +13,11 @@ export const examples = [ component: lazy(() => import('./examples/primitives/accordions')), }, { - name: 'account-layout-example', + name: 'sticky-sidebar-layout-example', dependencies: [], registryDependencies: [], - files: ['examples/sections/account-layout/index.tsx'], - component: lazy(() => import('./examples/sections/account-layout')), + files: ['examples/sections/sticky-sidebar-layout/index.tsx'], + component: lazy(() => import('./examples/sections/sticky-sidebar-layout')), }, { name: 'account-settings-section-example', diff --git a/apps/web/vibes/soul/examples/sections/account-layout/index.tsx b/apps/web/vibes/soul/examples/sections/account-layout/index.tsx deleted file mode 100644 index faac01347..000000000 --- a/apps/web/vibes/soul/examples/sections/account-layout/index.tsx +++ /dev/null @@ -1,11 +0,0 @@ -import { AccountLayout } from '@/vibes/soul/sections/account-layout'; - -const links = [ - { href: '/preview/soul/account-layout-example/Electric#a', label: 'Orders' }, - { href: '/preview/soul/account-layout-example/Electric#b', label: 'Addresses' }, - { href: '/preview/soul/account-layout-example/Electric#c', label: 'Account' }, -]; - -export default function Preview() { - return Put some stuff here!; -} diff --git a/apps/web/vibes/soul/examples/sections/account-settings-section/index.tsx b/apps/web/vibes/soul/examples/sections/account-settings-section/index.tsx index 43770f8b1..ffeaf465f 100644 --- a/apps/web/vibes/soul/examples/sections/account-settings-section/index.tsx +++ b/apps/web/vibes/soul/examples/sections/account-settings-section/index.tsx @@ -1,5 +1,6 @@ -import { AccountLayout } from '@/vibes/soul/sections/account-layout'; import { AccountSettingsSection } from '@/vibes/soul/sections/account-settings-section'; +import { SidebarMenu } from '@/vibes/soul/sections/sidebar-menu'; +import { StickySidebarLayout } from '@/vibes/soul/sections/sticky-sidebar-layout'; import { changePasswordAction, updateAccountAction } from './actions'; @@ -11,12 +12,12 @@ const links = [ export default function Preview() { return ( - + } sidebarSize="small"> - + ); } diff --git a/apps/web/vibes/soul/examples/sections/address-list-section/index.tsx b/apps/web/vibes/soul/examples/sections/address-list-section/index.tsx index d911474f5..a52804a40 100644 --- a/apps/web/vibes/soul/examples/sections/address-list-section/index.tsx +++ b/apps/web/vibes/soul/examples/sections/address-list-section/index.tsx @@ -1,6 +1,7 @@ import { Field, FieldGroup } from '@/vibes/soul/primitives/dynamic-form/schema'; -import { AccountLayout } from '@/vibes/soul/sections/account-layout'; import { Address, AddressListSection } from '@/vibes/soul/sections/address-list-section'; +import { SidebarMenu } from '@/vibes/soul/sections/sidebar-menu'; +import { StickySidebarLayout } from '@/vibes/soul/sections/sticky-sidebar-layout'; import { addressAction } from './actions'; @@ -109,13 +110,13 @@ const fields: Array> = [ export default function Preview() { return ( - + } sidebarSize="small"> - + ); } diff --git a/apps/web/vibes/soul/examples/sections/order-details-section/electric.tsx b/apps/web/vibes/soul/examples/sections/order-details-section/electric.tsx index 478503656..9182b1b4c 100644 --- a/apps/web/vibes/soul/examples/sections/order-details-section/electric.tsx +++ b/apps/web/vibes/soul/examples/sections/order-details-section/electric.tsx @@ -1,6 +1,7 @@ import { getProducts } from '@/vibes/soul/data'; -import { AccountLayout } from '@/vibes/soul/sections/account-layout'; import { OrderDetailsSection } from '@/vibes/soul/sections/order-details-section'; +import { SidebarMenu } from '@/vibes/soul/sections/sidebar-menu'; +import { StickySidebarLayout } from '@/vibes/soul/sections/sticky-sidebar-layout'; const products = await getProducts('Electric'); @@ -95,15 +96,15 @@ const order = { }; const links = [ - { href: '#', label: 'Orders' }, - { href: '#', label: 'Addresses' }, - { href: '#', label: 'Account' }, + { href: '#a', label: 'Orders' }, + { href: '#b', label: 'Addresses' }, + { href: '#c', label: 'Account' }, ]; export default function Preview() { return ( - + } sidebarSize="small"> - + ); } diff --git a/apps/web/vibes/soul/examples/sections/order-details-section/luxury.tsx b/apps/web/vibes/soul/examples/sections/order-details-section/luxury.tsx index f94334db5..d93e983c6 100644 --- a/apps/web/vibes/soul/examples/sections/order-details-section/luxury.tsx +++ b/apps/web/vibes/soul/examples/sections/order-details-section/luxury.tsx @@ -1,6 +1,7 @@ import { getProducts } from '@/vibes/soul/data'; -import { AccountLayout } from '@/vibes/soul/sections/account-layout'; import { OrderDetailsSection } from '@/vibes/soul/sections/order-details-section'; +import { SidebarMenu } from '@/vibes/soul/sections/sidebar-menu'; +import { StickySidebarLayout } from '@/vibes/soul/sections/sticky-sidebar-layout'; const products = await getProducts('Luxury'); @@ -95,15 +96,15 @@ const order = { }; const links = [ - { href: '#', label: 'Orders' }, - { href: '#', label: 'Addresses' }, - { href: '#', label: 'Account' }, + { href: '#a', label: 'Orders' }, + { href: '#b', label: 'Addresses' }, + { href: '#c', label: 'Account' }, ]; export default function Preview() { return ( - + } sidebarSize="small"> - + ); } diff --git a/apps/web/vibes/soul/examples/sections/order-details-section/warm.tsx b/apps/web/vibes/soul/examples/sections/order-details-section/warm.tsx index e8eb3e0de..ae16866d8 100644 --- a/apps/web/vibes/soul/examples/sections/order-details-section/warm.tsx +++ b/apps/web/vibes/soul/examples/sections/order-details-section/warm.tsx @@ -1,6 +1,7 @@ import { getProducts } from '@/vibes/soul/data'; -import { AccountLayout } from '@/vibes/soul/sections/account-layout'; import { OrderDetailsSection } from '@/vibes/soul/sections/order-details-section'; +import { SidebarMenu } from '@/vibes/soul/sections/sidebar-menu'; +import { StickySidebarLayout } from '@/vibes/soul/sections/sticky-sidebar-layout'; const products = await getProducts('Warm'); @@ -95,15 +96,15 @@ const order = { }; const links = [ - { href: '#', label: 'Orders' }, - { href: '#', label: 'Addresses' }, - { href: '#', label: 'Account' }, + { href: '#a', label: 'Orders' }, + { href: '#b', label: 'Addresses' }, + { href: '#c', label: 'Account' }, ]; export default function Preview() { return ( - + } sidebarSize="small"> - + ); } diff --git a/apps/web/vibes/soul/examples/sections/order-list-section/electric.tsx b/apps/web/vibes/soul/examples/sections/order-list-section/electric.tsx index 982bebe1a..a99a1a7ba 100644 --- a/apps/web/vibes/soul/examples/sections/order-list-section/electric.tsx +++ b/apps/web/vibes/soul/examples/sections/order-list-section/electric.tsx @@ -1,6 +1,7 @@ import { getProducts } from '@/vibes/soul/data'; -import { AccountLayout } from '@/vibes/soul/sections/account-layout'; import { OrderListSection } from '@/vibes/soul/sections/order-list-section'; +import { SidebarMenu } from '@/vibes/soul/sections/sidebar-menu'; +import { StickySidebarLayout } from '@/vibes/soul/sections/sticky-sidebar-layout'; const products = await getProducts('Electric'); @@ -56,15 +57,15 @@ const orders = [ ]; const links = [ - { href: '/preview/soul/order-list-section-electric-example', label: 'Orders' }, - { href: '/preview/soul/address-list-section-example', label: 'Addresses' }, - { href: '/preview/soul/account-settings-section-example', label: 'Account' }, + { href: '#a', label: 'Orders' }, + { href: '#b', label: 'Addresses' }, + { href: '#c', label: 'Account' }, ]; export default function Preview() { return ( - + } sidebarSize="small"> - + ); } diff --git a/apps/web/vibes/soul/examples/sections/order-list-section/luxury.tsx b/apps/web/vibes/soul/examples/sections/order-list-section/luxury.tsx index 99c1f1b61..075f2f0b0 100644 --- a/apps/web/vibes/soul/examples/sections/order-list-section/luxury.tsx +++ b/apps/web/vibes/soul/examples/sections/order-list-section/luxury.tsx @@ -1,6 +1,7 @@ import { getProducts } from '@/vibes/soul/data'; -import { AccountLayout } from '@/vibes/soul/sections/account-layout'; import { OrderListSection } from '@/vibes/soul/sections/order-list-section'; +import { SidebarMenu } from '@/vibes/soul/sections/sidebar-menu'; +import { StickySidebarLayout } from '@/vibes/soul/sections/sticky-sidebar-layout'; const products = await getProducts('Luxury'); @@ -56,15 +57,15 @@ const orders = [ ]; const links = [ - { href: '#', label: 'Orders' }, - { href: '#', label: 'Addresses' }, - { href: '#', label: 'Account' }, + { href: '#a', label: 'Orders' }, + { href: '#b', label: 'Addresses' }, + { href: '#c', label: 'Account' }, ]; export default function Preview() { return ( - + } sidebarSize="small"> - + ); } diff --git a/apps/web/vibes/soul/examples/sections/order-list-section/warm.tsx b/apps/web/vibes/soul/examples/sections/order-list-section/warm.tsx index efda34401..fe8fb00d9 100644 --- a/apps/web/vibes/soul/examples/sections/order-list-section/warm.tsx +++ b/apps/web/vibes/soul/examples/sections/order-list-section/warm.tsx @@ -1,6 +1,7 @@ import { getProducts } from '@/vibes/soul/data'; -import { AccountLayout } from '@/vibes/soul/sections/account-layout'; import { OrderListSection } from '@/vibes/soul/sections/order-list-section'; +import { SidebarMenu } from '@/vibes/soul/sections/sidebar-menu'; +import { StickySidebarLayout } from '@/vibes/soul/sections/sticky-sidebar-layout'; const products = await getProducts('Warm'); @@ -56,15 +57,15 @@ const orders = [ ]; const links = [ - { href: '#', label: 'Orders' }, - { href: '#', label: 'Addresses' }, - { href: '#', label: 'Account' }, + { href: '#a', label: 'Orders' }, + { href: '#b', label: 'Addresses' }, + { href: '#c', label: 'Account' }, ]; export default function Preview() { return ( - + } sidebarSize="small"> - + ); } diff --git a/apps/web/vibes/soul/examples/sections/sticky-sidebar-layout/index.tsx b/apps/web/vibes/soul/examples/sections/sticky-sidebar-layout/index.tsx new file mode 100644 index 000000000..c4db30b18 --- /dev/null +++ b/apps/web/vibes/soul/examples/sections/sticky-sidebar-layout/index.tsx @@ -0,0 +1,16 @@ +import { SidebarMenu } from '@/vibes/soul/sections/sidebar-menu'; +import { StickySidebarLayout } from '@/vibes/soul/sections/sticky-sidebar-layout'; + +const links = [ + { href: '/preview/soul/sticky-sidebar-layout-example/Electric#a', label: 'Orders' }, + { href: '/preview/soul/sticky-sidebar-layout-example/Electric#b', label: 'Addresses' }, + { href: '/preview/soul/sticky-sidebar-layout-example/Electric#c', label: 'Account' }, +]; + +export default function Preview() { + return ( + } sidebarSize="small"> + Put some stuff here! + + ); +} diff --git a/apps/web/vibes/soul/navigation.ts b/apps/web/vibes/soul/navigation.ts index daec0256f..c960f19d6 100644 --- a/apps/web/vibes/soul/navigation.ts +++ b/apps/web/vibes/soul/navigation.ts @@ -155,12 +155,6 @@ export const navigation = [ { title: 'Sections', pages: [ - { - title: 'Account Layout', - slug: 'account-layout', - file: 'docs/account-layout.mdx', - component: 'account-layout', - }, { title: 'Account Settings Section', slug: 'account-settings-section', @@ -281,6 +275,12 @@ export const navigation = [ file: 'docs/slideshow.mdx', component: 'slideshow', }, + { + title: 'Sticky Sidebar Layout', + slug: 'sticky-sidebar-layout', + file: 'docs/sticky-sidebar-layout.mdx', + component: 'sticky-sidebar-layout', + }, { title: 'Subscribe', slug: 'subscribe', diff --git a/apps/web/vibes/soul/sections.ts b/apps/web/vibes/soul/sections.ts index 6f389d086..9ebea76ba 100644 --- a/apps/web/vibes/soul/sections.ts +++ b/apps/web/vibes/soul/sections.ts @@ -2,10 +2,10 @@ import { Components } from '@/vibes/schema'; export const sections = [ { - name: 'account-layout', + name: 'sticky-sidebar-layout', dependencies: ['clsx'], registryDependencies: [], - files: ['sections/account-layout/index.tsx'], + files: ['sections/sticky-sidebar-layout/index.tsx'], }, { name: 'account-settings-section', diff --git a/apps/web/vibes/soul/sections/account-layout/index.tsx b/apps/web/vibes/soul/sections/account-layout/index.tsx deleted file mode 100644 index 01f02ba7b..000000000 --- a/apps/web/vibes/soul/sections/account-layout/index.tsx +++ /dev/null @@ -1,38 +0,0 @@ -import { ReactNode } from 'react'; - -import { StickySidebarLayout } from '@/vibes/soul/sections/sticky-sidebar-layout'; - -import { AccountLayoutLink } from './account-layout-link'; -import { AccountLayoutLinkSelect } from './account-layout-link-select'; - -interface Props { - links: Array<{ - href: string; - label: string; - }>; - children: ReactNode; -} - -export function AccountLayout({ links, children }: Props) { - return ( - - -
- -
- - } - sidebarSize="small" - > - {children} -
- ); -} diff --git a/apps/web/vibes/soul/sections/sidebar-menu/index.tsx b/apps/web/vibes/soul/sections/sidebar-menu/index.tsx new file mode 100644 index 000000000..be162303e --- /dev/null +++ b/apps/web/vibes/soul/sections/sidebar-menu/index.tsx @@ -0,0 +1,63 @@ +import { Stream, Streamable } from '@/vibes/soul/lib/streamable'; + +import { SidebarMenuLink } from './sidebar-menu-link'; +import { SidebarMenuSelect } from './sidebar-menu-select'; + +interface MenuLink { + href: string; + label: string; +} + +interface Props { + links: Streamable; + placeholderCount?: number; +} + +export function SidebarMenu({ links: streamableLinks, placeholderCount = 5 }: Props) { + return ( + } + value={streamableLinks} + > + {(links) => { + if (!links.length) { + return null; + } + + return ( + + ); + }} + + ); +} + +function SidebarMenuSkeleton({ placeholderCount }: { placeholderCount: number }) { + return ( + <> +
+
+ {Array.from({ length: placeholderCount }).map((_, index) => ( +
+
+
+ ))} +
+
+
+
+
+ + ); +} diff --git a/apps/web/vibes/soul/sections/account-layout/account-layout-link.tsx b/apps/web/vibes/soul/sections/sidebar-menu/sidebar-menu-link.tsx similarity index 94% rename from apps/web/vibes/soul/sections/account-layout/account-layout-link.tsx rename to apps/web/vibes/soul/sections/sidebar-menu/sidebar-menu-link.tsx index dc1f254e6..de356b5f7 100644 --- a/apps/web/vibes/soul/sections/account-layout/account-layout-link.tsx +++ b/apps/web/vibes/soul/sections/sidebar-menu/sidebar-menu-link.tsx @@ -5,7 +5,7 @@ import Link from 'next/link'; import { usePathname } from 'next/navigation'; import React from 'react'; -export function AccountLayoutLink({ +export function SidebarMenuLink({ className, href, ...rest diff --git a/apps/web/vibes/soul/sections/account-layout/account-layout-link-select.tsx b/apps/web/vibes/soul/sections/sidebar-menu/sidebar-menu-select.tsx similarity index 72% rename from apps/web/vibes/soul/sections/account-layout/account-layout-link-select.tsx rename to apps/web/vibes/soul/sections/sidebar-menu/sidebar-menu-select.tsx index 9d1ab9de0..2625273ef 100644 --- a/apps/web/vibes/soul/sections/account-layout/account-layout-link-select.tsx +++ b/apps/web/vibes/soul/sections/sidebar-menu/sidebar-menu-select.tsx @@ -4,17 +4,13 @@ import { usePathname, useRouter } from 'next/navigation'; import { Select } from '@/vibes/soul/form/select'; -export function AccountLayoutLinkSelect({ - links, -}: { - links: Array<{ href: string; label: string }>; -}) { +export function SidebarMenuSelect({ links }: { links: Array<{ href: string; label: string }> }) { const pathname = usePathname(); const router = useRouter(); return (