slideshare/scripts/generate-themes-manifest.js
Michael Mainguy 6e6c09b5ba Add comprehensive theme routing and browsing system
- Add React Router with theme browser, theme detail, and layout detail pages
- Implement manifest-based theme discovery for better performance
- Add Welcome component as home page with feature overview
- Fix layout and styling issues with proper CSS centering
- Implement introspective theme browsing (dynamically discover colors/variables)
- Add layout preview system with iframe scaling
- Create comprehensive theme detail page with color palette display
- Fix TypeScript errors and build issues
- Remove hardcoded theme assumptions in favor of dynamic discovery

🤖 Generated with [Claude Code](https://claude.ai/code)

Co-Authored-By: Claude <noreply@anthropic.com>
2025-08-20 10:17:55 -05:00

74 lines
2.3 KiB
JavaScript

import fs from 'fs';
import path from 'path';
import { fileURLToPath } from 'url';
const __filename = fileURLToPath(import.meta.url);
const __dirname = path.dirname(__filename);
const PUBLIC_THEMES_DIR = path.join(__dirname, '..', 'public', 'themes');
const MANIFEST_OUTPUT = path.join(__dirname, '..', 'public', 'themes-manifest.json');
/**
* Generates a manifest of all available themes and their layouts
*/
async function generateThemesManifest() {
const manifest = {
themes: {},
generated: new Date().toISOString()
};
try {
// Check if themes directory exists
if (!fs.existsSync(PUBLIC_THEMES_DIR)) {
console.warn('Themes directory not found:', PUBLIC_THEMES_DIR);
return;
}
// Read all theme directories
const themeDirectories = fs.readdirSync(PUBLIC_THEMES_DIR, { withFileTypes: true })
.filter(dirent => dirent.isDirectory())
.map(dirent => dirent.name);
for (const themeId of themeDirectories) {
const themePath = path.join(PUBLIC_THEMES_DIR, themeId);
const layoutsPath = path.join(themePath, 'layouts');
// Check for required files
const styleFile = path.join(themePath, 'style.css');
if (!fs.existsSync(styleFile)) {
console.warn(`Theme ${themeId} missing style.css, skipping`);
continue;
}
const themeInfo = {
id: themeId,
cssFile: 'style.css',
layouts: [],
hasMasterSlide: fs.existsSync(path.join(themePath, 'master-slide.html'))
};
// Discover layouts
if (fs.existsSync(layoutsPath)) {
const layoutFiles = fs.readdirSync(layoutsPath)
.filter(file => file.endsWith('.html'))
.map(file => path.basename(file, '.html'));
themeInfo.layouts = layoutFiles;
}
manifest.themes[themeId] = themeInfo;
console.log(`✓ Found theme: ${themeId} with ${themeInfo.layouts.length} layouts`);
}
// Write manifest file
fs.writeFileSync(MANIFEST_OUTPUT, JSON.stringify(manifest, null, 2));
console.log(`✓ Generated themes manifest: ${MANIFEST_OUTPUT}`);
console.log(`✓ Found ${Object.keys(manifest.themes).length} themes total`);
} catch (error) {
console.error('Error generating themes manifest:', error);
process.exit(1);
}
}
generateThemesManifest();