diff --git a/src/deck/Deck.vue b/src/deck/Deck.vue index e0a9866..a836d17 100644 --- a/src/deck/Deck.vue +++ b/src/deck/Deck.vue @@ -12,6 +12,7 @@ import EntitiesSlide from './slides/EntitiesSlide.vue' import ArchipelagoSlide from './slides/ArchipelagoSlide.vue' import SolunarSlide from './slides/SolunarSlide.vue' import ChateauSlide from './slides/ChateauSlide.vue' +import GallerySlide from './slides/GallerySlide.vue' import EcosystemSlide from './slides/EcosystemSlide.vue' import RevenueSlide from './slides/RevenueSlide.vue' import InvestmentOverviewSlide from './slides/InvestmentOverviewSlide.vue' @@ -30,6 +31,7 @@ const slides = [ { id: 'archipelago', label: 'Archipelago', component: ArchipelagoSlide }, { id: 'solunar', label: 'Solunar Society', component: SolunarSlide }, { id: 'chateau', label: 'Chateau du Faune', component: ChateauSlide }, + { id: 'gallery', label: 'Gallery', component: GallerySlide }, { id: 'ecosystem', label: 'One membership', component: EcosystemSlide }, { id: 'revenue', label: 'Revenue', component: RevenueSlide }, { id: 'invest-overview', label: 'The raise', component: InvestmentOverviewSlide }, diff --git a/src/deck/components/Icon.vue b/src/deck/components/Icon.vue index 1ecde30..e46ad45 100644 --- a/src/deck/components/Icon.vue +++ b/src/deck/components/Icon.vue @@ -30,6 +30,8 @@ import { Moon, MapPin, ChevronRight, + Images, + Expand, type LucideProps, } from '@lucide/vue' import type { FunctionalComponent } from 'vue' @@ -64,6 +66,8 @@ const registry: Record> = { Moon, MapPin, ChevronRight, + Images, + Expand, } const props = defineProps<{ name: string }>() diff --git a/src/deck/components/Lightbox.vue b/src/deck/components/Lightbox.vue new file mode 100644 index 0000000..ce78a9e --- /dev/null +++ b/src/deck/components/Lightbox.vue @@ -0,0 +1,125 @@ + + + + + diff --git a/src/deck/gallery.ts b/src/deck/gallery.ts new file mode 100644 index 0000000..de2fff2 --- /dev/null +++ b/src/deck/gallery.ts @@ -0,0 +1,82 @@ +/** + * Gallery auto-population. + * + * Drop image files into these folders and they appear in the deck gallery + * automatically — no code changes, no manifest to edit: + * + * src/deck/gallery/city/ → City (Archipelago) + * src/deck/gallery/farm/ → Farm (Chateau du Faune) + * src/deck/gallery/festival/ → Festival (Solunar Society) + * + * Supported: jpg jpeg png webp avif gif svg. Images show sorted by filename, + * so prefix with 01-, 02-, … to control order. The seeded *-placeholder.svg + * files are just demo art — delete them once you add real photos. + * + * Under the hood this uses Vite's import.meta.glob, which must take a literal + * pattern (no variables) — hence one call per folder. + */ +import { entityById, type Accent } from './data' + +type GlobMap = Record + +// NB: import.meta.glob is statically analysed by Vite — its options must be an +// inline object literal (not a shared const), so the object is repeated below. +const city = import.meta.glob('./gallery/city/*.{jpg,jpeg,png,webp,avif,gif,svg}', { + eager: true, + query: '?url', + import: 'default', +}) as GlobMap +const farm = import.meta.glob('./gallery/farm/*.{jpg,jpeg,png,webp,avif,gif,svg}', { + eager: true, + query: '?url', + import: 'default', +}) as GlobMap +const festival = import.meta.glob('./gallery/festival/*.{jpg,jpeg,png,webp,avif,gif,svg}', { + eager: true, + query: '?url', + import: 'default', +}) as GlobMap + +export type GalleryImage = { src: string; name: string } + +function toImages(map: GlobMap): GalleryImage[] { + return Object.entries(map) + .sort(([a], [b]) => a.localeCompare(b)) + .map(([path, src]) => ({ src, name: path.split('/').pop()!.replace(/\.[^.]+$/, '') })) +} + +export type GallerySection = { + id: 'city' | 'farm' | 'festival' + label: string + entityName: string + accent: Accent + folder: string + images: GalleryImage[] +} + +export const gallerySections: GallerySection[] = [ + { + id: 'city', + label: 'City', + entityName: entityById('archipelago').name, + accent: 'pine', + folder: 'src/deck/gallery/city/', + images: toImages(city), + }, + { + id: 'farm', + label: 'Farm', + entityName: entityById('chateau').name, + accent: 'clay', + folder: 'src/deck/gallery/farm/', + images: toImages(farm), + }, + { + id: 'festival', + label: 'Festival', + entityName: entityById('solunar').name, + accent: 'indigo', + folder: 'src/deck/gallery/festival/', + images: toImages(festival), + }, +] diff --git a/src/deck/gallery/README.md b/src/deck/gallery/README.md new file mode 100644 index 0000000..4706557 --- /dev/null +++ b/src/deck/gallery/README.md @@ -0,0 +1,18 @@ +# Deck gallery — just drop images in + +Each subfolder feeds one section of the Gallery slide. **Drop image files in and +they appear automatically** — no code to touch. + +| Folder | Section | Entity | +| ----------- | -------- | ----------------- | +| `city/` | City | Archipelago | +| `farm/` | Farm | Chateau du Faune | +| `festival/` | Festival | Solunar Society | + +- Supported formats: `jpg` `jpeg` `png` `webp` `avif` `gif` `svg`. +- Images display **sorted by filename** — prefix `01-`, `02-`, … to order them. +- The `*-placeholder.svg` files are demo art. **Delete them** once you add real photos. +- Wiring lives in `src/deck/gallery.ts` (Vite `import.meta.glob`). If you add a + brand-new format, extend the glob patterns there. + +Recommended: web-optimized `.webp` under ~500 KB each for fast loading. diff --git a/src/deck/gallery/city/01-placeholder.svg b/src/deck/gallery/city/01-placeholder.svg new file mode 100644 index 0000000..08db74e --- /dev/null +++ b/src/deck/gallery/city/01-placeholder.svg @@ -0,0 +1,15 @@ + + + + + + + + + + + + City + Photo 01 + PLACEHOLDER · 800×1040 + diff --git a/src/deck/gallery/city/02-placeholder.svg b/src/deck/gallery/city/02-placeholder.svg new file mode 100644 index 0000000..9b3bb39 --- /dev/null +++ b/src/deck/gallery/city/02-placeholder.svg @@ -0,0 +1,15 @@ + + + + + + + + + + + + City + Photo 02 + PLACEHOLDER · 800×620 + diff --git a/src/deck/gallery/city/03-placeholder.svg b/src/deck/gallery/city/03-placeholder.svg new file mode 100644 index 0000000..fe463cb --- /dev/null +++ b/src/deck/gallery/city/03-placeholder.svg @@ -0,0 +1,15 @@ + + + + + + + + + + + + City + Photo 03 + PLACEHOLDER · 800×800 + diff --git a/src/deck/gallery/city/04-placeholder.svg b/src/deck/gallery/city/04-placeholder.svg new file mode 100644 index 0000000..7af5625 --- /dev/null +++ b/src/deck/gallery/city/04-placeholder.svg @@ -0,0 +1,15 @@ + + + + + + + + + + + + City + Photo 04 + PLACEHOLDER · 800×560 + diff --git a/src/deck/gallery/city/05-placeholder.svg b/src/deck/gallery/city/05-placeholder.svg new file mode 100644 index 0000000..b2000a4 --- /dev/null +++ b/src/deck/gallery/city/05-placeholder.svg @@ -0,0 +1,15 @@ + + + + + + + + + + + + City + Photo 05 + PLACEHOLDER · 800×900 + diff --git a/src/deck/gallery/farm/01-placeholder.svg b/src/deck/gallery/farm/01-placeholder.svg new file mode 100644 index 0000000..6becd7a --- /dev/null +++ b/src/deck/gallery/farm/01-placeholder.svg @@ -0,0 +1,15 @@ + + + + + + + + + + + + Farm + Photo 01 + PLACEHOLDER · 800×620 + diff --git a/src/deck/gallery/farm/02-placeholder.svg b/src/deck/gallery/farm/02-placeholder.svg new file mode 100644 index 0000000..bd737ad --- /dev/null +++ b/src/deck/gallery/farm/02-placeholder.svg @@ -0,0 +1,15 @@ + + + + + + + + + + + + Farm + Photo 02 + PLACEHOLDER · 800×900 + diff --git a/src/deck/gallery/farm/03-placeholder.svg b/src/deck/gallery/farm/03-placeholder.svg new file mode 100644 index 0000000..04911bb --- /dev/null +++ b/src/deck/gallery/farm/03-placeholder.svg @@ -0,0 +1,15 @@ + + + + + + + + + + + + Farm + Photo 03 + PLACEHOLDER · 800×560 + diff --git a/src/deck/gallery/farm/04-placeholder.svg b/src/deck/gallery/farm/04-placeholder.svg new file mode 100644 index 0000000..2f3a624 --- /dev/null +++ b/src/deck/gallery/farm/04-placeholder.svg @@ -0,0 +1,15 @@ + + + + + + + + + + + + Farm + Photo 04 + PLACEHOLDER · 800×800 + diff --git a/src/deck/gallery/festival/01-placeholder.svg b/src/deck/gallery/festival/01-placeholder.svg new file mode 100644 index 0000000..73a7b1f --- /dev/null +++ b/src/deck/gallery/festival/01-placeholder.svg @@ -0,0 +1,15 @@ + + + + + + + + + + + + Festival + Photo 01 + PLACEHOLDER · 800×800 + diff --git a/src/deck/gallery/festival/02-placeholder.svg b/src/deck/gallery/festival/02-placeholder.svg new file mode 100644 index 0000000..b6c7456 --- /dev/null +++ b/src/deck/gallery/festival/02-placeholder.svg @@ -0,0 +1,15 @@ + + + + + + + + + + + + Festival + Photo 02 + PLACEHOLDER · 800×560 + diff --git a/src/deck/gallery/festival/03-placeholder.svg b/src/deck/gallery/festival/03-placeholder.svg new file mode 100644 index 0000000..3951739 --- /dev/null +++ b/src/deck/gallery/festival/03-placeholder.svg @@ -0,0 +1,15 @@ + + + + + + + + + + + + Festival + Photo 03 + PLACEHOLDER · 800×1040 + diff --git a/src/deck/gallery/festival/04-placeholder.svg b/src/deck/gallery/festival/04-placeholder.svg new file mode 100644 index 0000000..46ef5c8 --- /dev/null +++ b/src/deck/gallery/festival/04-placeholder.svg @@ -0,0 +1,15 @@ + + + + + + + + + + + + Festival + Photo 04 + PLACEHOLDER · 800×700 + diff --git a/src/deck/gallery/festival/05-placeholder.svg b/src/deck/gallery/festival/05-placeholder.svg new file mode 100644 index 0000000..e9ce0cc --- /dev/null +++ b/src/deck/gallery/festival/05-placeholder.svg @@ -0,0 +1,15 @@ + + + + + + + + + + + + Festival + Photo 05 + PLACEHOLDER · 800×600 + diff --git a/src/deck/slides/GallerySlide.vue b/src/deck/slides/GallerySlide.vue new file mode 100644 index 0000000..b059a62 --- /dev/null +++ b/src/deck/slides/GallerySlide.vue @@ -0,0 +1,92 @@ + + +