theme.js 2.3 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101
  1. import { defineStore } from 'pinia'
  2. import { ref, watch } from 'vue'
  3. export const useThemeStore = defineStore('theme', () => {
  4. // State
  5. const theme = ref('dark') // 'dark' | 'light'
  6. // Load persisted theme on init
  7. function init() {
  8. try {
  9. const saved = uni.getStorageSync('theme')
  10. if (saved === 'light' || saved === 'dark') {
  11. theme.value = saved
  12. } else {
  13. // Follow system preference if available
  14. try {
  15. const sysInfo = uni.getSystemInfoSync()
  16. if (sysInfo.theme && sysInfo.theme === 'light') {
  17. theme.value = 'light'
  18. }
  19. } catch (e) {
  20. // Default to dark (brand identity)
  21. }
  22. }
  23. } catch (e) {
  24. theme.value = 'dark'
  25. }
  26. applyTheme(theme.value)
  27. }
  28. // Toggle theme
  29. function toggle() {
  30. theme.value = theme.value === 'dark' ? 'light' : 'dark'
  31. applyTheme(theme.value)
  32. persistTheme(theme.value)
  33. }
  34. // Set specific theme
  35. function setTheme(t) {
  36. if (t !== 'dark' && t !== 'light') return
  37. theme.value = t
  38. applyTheme(t)
  39. persistTheme(t)
  40. }
  41. // Apply to DOM
  42. function applyTheme(t) {
  43. // Update page data-theme (CSS fallback)
  44. try {
  45. const pages = getCurrentPages()
  46. const curPage = pages[pages.length - 1]
  47. if (curPage && curPage.$page && curPage.$page.$el) {
  48. curPage.$page.$el.setAttribute('data-theme', t)
  49. }
  50. } catch (e) {
  51. // Silent fallback
  52. }
  53. // Update the native bottom tab bar (outside Vue component tree)
  54. try {
  55. uni.setTabBarStyle({
  56. color: t === 'light' ? '#4A5568' : '#A0AEC0',
  57. selectedColor: '#C9A84C',
  58. backgroundColor: t === 'light' ? '#FFFFFF' : '#1E3A5F',
  59. borderStyle: t === 'light' ? 'black' : 'white',
  60. })
  61. } catch (e) {
  62. // Tab bar not configured — skip
  63. }
  64. }
  65. // Persist to storage
  66. function persistTheme(t) {
  67. try {
  68. uni.setStorageSync('theme', t)
  69. } catch (e) {
  70. // Silent
  71. }
  72. }
  73. // Listen for system theme changes
  74. function watchSystemTheme() {
  75. try {
  76. uni.onThemeChange((res) => {
  77. // Optional: auto-follow system
  78. // theme.value = res.theme
  79. // applyTheme(res.theme)
  80. })
  81. } catch (e) {
  82. // onThemeChange not supported on this platform
  83. }
  84. }
  85. return {
  86. theme,
  87. init,
  88. toggle,
  89. setTheme,
  90. watchSystemTheme
  91. }
  92. })