Now.js Framework Documentation
ThemeManager
ThemeManager
ภาพรวม
ThemeManager คือระบบจัดการ theme ใน Now.js Framework รองรับ:
- Light/Dark mode switching
- Auto-enhanced toggle buttons (
data-component="theme") - Backend API integration (โหลด CSS Variables จาก server)
- Smooth transitions (Anti-FOUC)
- System preference detection
การใช้งานพื้นฐาน
Initialization
await Now.init({
theme: {
enabled: true,
defaultTheme: 'light',
storageKey: 'app_theme',
systemPreference: true
}
});Toggle Theme
ThemeManager.toggle(); // สลับ light ↔ dark
await ThemeManager.setTheme('dark'); // ตั้งค่าเฉพาะเจาะจง
const theme = ThemeManager.getCurrentTheme();Toggle Button
HTML
<!-- Auto-enhanced - ไม่ต้องเขียน JS -->
<button data-component="theme">🌓</button>ThemeManager จะ enhance ปุ่มอัตโนมัติ:
- ✅ เพิ่ม click handler
- ✅ Sync
data-theme-stateattribute - ✅ ทุกปุ่มจะ sync เมื่อ theme เปลี่ยน
CSS สำหรับ Toggle Button
/* Icon font setup */
[data-component="theme"]:before {
font-family: 'icomoon' !important;
}
/* แสดง icon ตาม theme */
[data-component="theme"][data-theme-state="light"]:before {
content: "\e929"; /* icon-night */
}
[data-component="theme"][data-theme-state="dark"]:before {
content: "\e9d4"; /* icon-day */
}หรือใช้ CSS classes:
[data-theme-state="light"] .icon-light { display: none; }
[data-theme-state="dark"] .icon-dark { display: none; }การตั้งค่าเต็มรูปแบบ
await Now.init({
theme: {
enabled: true,
defaultTheme: 'light',
storageKey: 'app_theme',
systemPreference: true,
// Smooth Transitions
transition: {
enabled: true,
duration: 300,
hideOnSwitch: true,
readyClass: 'theme-ready',
transitionClass: 'theme-transitioning'
},
// Backend API
api: {
enabled: false,
configUrl: '/api/theme/config',
timeout: 5000,
cacheResponse: true
}
}
});Backend API Integration
โหลด Config จาก API
await ThemeManager.loadFromAPI('/api/theme/config');API Response Format
{
"variables": {
"--color-primary": "#6366f1",
"--color-background": "#0f172a",
"--hero-bg": "images/hero.jpg"
}
}หมายเหตุ: API ไม่ควบคุม light/dark mode - ผู้ใช้ควบคุมเอง
CSS Variables
Apply Variables
ThemeManager.applyVariables({
'--color-primary': '#6366f1',
'--color-background': '#0f172a',
'--hero-bg': '/images/hero.jpg' // Auto-wrap เป็น url()
});Security
- อนุญาตเฉพาะ CSS Custom Properties (
--*) - ลบ patterns อันตราย (
javascript:,expression(),<script>) - URLs: รองรับ local paths หรือ absolute URLs จากโดเมนเดียวกัน
- โดเมนภายนอกถูกบล็อกโดย default
- Extensions ต้องเป็นรูปภาพ (ไม่มี SVG)
Smooth Transitions
CSS ที่ต้องใช้
body {
opacity: 0;
transition: opacity 0.3s ease;
}
body.theme-ready {
opacity: 1;
}
body.theme-transitioning {
opacity: 0;
}วิธีทำงาน
bodyเริ่มต้นที่opacity: 0- ThemeManager โหลด theme
- เพิ่ม class
theme-ready→ fade in - เมื่อ switch → fade out → apply → fade in
API Reference
| Method | คำอธิบาย |
|---|---|
toggle() |
สลับ theme |
setTheme(theme) |
ตั้งค่า theme |
getCurrentTheme() |
รับ theme ปัจจุบัน |
applyVariables(vars) |
Apply CSS Variables |
clearVariables() |
ล้าง CSS Variables |
getAppliedVariables() |
ดึง variables ที่ใช้ |
loadFromAPI(url?) |
โหลดจาก API |
refreshFromAPI() |
โหลดใหม่ (ล้าง cache) |
destroy() |
Cleanup ทั้งหมด |
reset() |
Reset state |
Events
| Event | เมื่อเกิด |
|---|---|
theme:initialized |
Init เสร็จ |
theme:changed |
Theme เปลี่ยน |
theme:ready |
พร้อมแสดงผล |
theme:variables-applied |
Apply variables เสร็จ |
theme:variables-cleared |
ล้าง variables เสร็จ |
theme:api-loaded |
โหลดจาก API สำเร็จ |
theme:api-error |
API error |
theme:destroyed |
Cleanup เสร็จ |
theme:reset |
Reset เสร็จ |
EventManager.on('theme:changed', ({ theme }) => {
console.log('เปลี่ยนเป็น:', theme);
});Cleanup
// Cleanup สมบูรณ์ (unmount app)
ThemeManager.destroy();
// Reset เบาๆ (re-init)
ThemeManager.reset();
await ThemeManager.init({ ... });ข้อควรระวัง
⚠️ 1. Enable ก่อนใช้
// ❌ ยังไม่ enable
ThemeManager.toggle();
// ✅ Enable ก่อน
await Now.init({ theme: { enabled: true } });
ThemeManager.toggle();⚠️ 2. ใช้ CSS Variables
/* ❌ ใช้ค่าคงที่ */
body { background: white; }
/* ✅ ใช้ variables */
body { background: var(--color-background); }⚠️ 3. เปิดผ่าน HTTP
// ❌ file:// protocol ใช้ API ไม่ได้
// ✅ http://localhost/...