preferences.ts 2.6 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114
  1. import { useStorage } from '@vueuse/core'
  2. import { acceptHMRUpdate, defineStore } from 'pinia'
  3. import { ref, watch } from 'vue'
  4. import { mergeWithArrayReplace } from '@/utils/lodash-helpers'
  5. import type { WatermarkProps } from 'naive-ui'
  6. export type LayoutSlideDirection = 'left' | 'right' | null
  7. export interface PreferencesOptions {
  8. menu: Partial<{
  9. collapsed: boolean
  10. width: number
  11. maxWidth: number
  12. }>
  13. shouldRefreshTab: boolean
  14. showFooter: boolean
  15. showLogo: boolean
  16. showTabs: boolean
  17. showTabClose: boolean
  18. showNavigation: boolean
  19. showBreadcrumb: boolean
  20. showWatermark: boolean
  21. showNoise: boolean
  22. showTopLoadingBar: boolean
  23. enableNavigationTransition: boolean
  24. enableTextSelect: boolean
  25. watermarkOptions: Partial<WatermarkProps>
  26. noiseOpacity: number
  27. }
  28. export const DEFAULT_PREFERENCES_OPTIONS: PreferencesOptions = {
  29. menu: {
  30. collapsed: false,
  31. width: 64,
  32. maxWidth: 272,
  33. },
  34. shouldRefreshTab: false,
  35. showFooter: true,
  36. showTabs: true,
  37. showTabClose: true,
  38. showLogo: true,
  39. showNoise: true,
  40. showWatermark: false,
  41. showNavigation: true,
  42. showBreadcrumb: true,
  43. showTopLoadingBar: true,
  44. enableNavigationTransition: true,
  45. enableTextSelect: true,
  46. watermarkOptions: {
  47. content: 'Watermark',
  48. fontColor: '#D81E1E96',
  49. fontSize: 16,
  50. width: 384,
  51. height: 384,
  52. xGap: 0,
  53. yGap: 0,
  54. xOffset: 12,
  55. yOffset: 60,
  56. globalRotate: 0,
  57. rotate: -20,
  58. textAlign: 'center',
  59. cross: true,
  60. fontStyle: 'normal',
  61. fontWeight: 400,
  62. lineHeight: 16,
  63. image: undefined,
  64. imageHeight: 64,
  65. imageWidth: 64,
  66. imageOpacity: 0.5,
  67. },
  68. noiseOpacity: 0.02,
  69. }
  70. export const usePreferencesStore = defineStore('preferencesStore', () => {
  71. const preferences = useStorage<PreferencesOptions>('preferences', DEFAULT_PREFERENCES_OPTIONS)
  72. const layoutSlideDirection = ref<LayoutSlideDirection>(null)
  73. const modify = (options: Partial<PreferencesOptions>) => {
  74. preferences.value = mergeWithArrayReplace(preferences.value, options)
  75. }
  76. const setLayoutSlideDirection = (direction: LayoutSlideDirection) => {
  77. layoutSlideDirection.value = direction
  78. }
  79. const reset = () => {
  80. preferences.value = structuredClone(DEFAULT_PREFERENCES_OPTIONS)
  81. }
  82. watch(
  83. () => preferences.value.enableTextSelect,
  84. (newValue) => {
  85. document.documentElement.style.userSelect = newValue ? 'auto' : 'none'
  86. },
  87. {
  88. immediate: true,
  89. },
  90. )
  91. return {
  92. preferences,
  93. layoutSlideDirection,
  94. setLayoutSlideDirection,
  95. reset,
  96. modify,
  97. }
  98. })
  99. if (import.meta.hot) {
  100. import.meta.hot.accept(acceptHMRUpdate(usePreferencesStore, import.meta.hot))
  101. }