diff --git a/.env b/.env new file mode 100644 index 0000000000000000000000000000000000000000..344bfda14acfa04a04c251729369a2df541bcacd --- /dev/null +++ b/.env @@ -0,0 +1,3 @@ +VITE_SUPABASE_URL=https://wrwwvdgppriodcdoyohp.supabase.co +VITE_SUPABASE_ANON_KEY=eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJpc3MiOiJzdXBhYmFzZSIsInJlZiI6Indyd3d2ZGdwcHJpb2RjZG95b2hwIiwicm9sZSI6ImFub24iLCJpYXQiOjE3MjM3OTc1NzQsImV4cCI6MjAzOTM3MzU3NH0.ttfp3RHEgJIwF8fC-iUx2BmfxB_T-NqNeQCxycMqCDs +VITE_SUPABASE_ACCESS_TOKEN=sbp_cc9798115cb71d087e9b6774a35ba5c6ab866c9f \ No newline at end of file diff --git a/components.d.ts b/components.d.ts index 9e5ed52bddc46b1b18e125061c9b92634c771b60..c0b700716c6ce387b98b7d5d83db79150ecdc8e9 100644 --- a/components.d.ts +++ b/components.d.ts @@ -15,6 +15,7 @@ declare module 'vue' { Drawer: typeof import('primevue/drawer')['default'] ImageItem: typeof import('@/modules/entities/ImageItem.vue')['default'] ImageMoveMenu: typeof import('./src/components/editEntityMenu/ImageMoveMenu.vue')['default'] + ImageSizeMenu: typeof import('./src/components/editEntityMenu/ImageSizeMenu.vue')['default'] ImageStateMenu: typeof import('./src/components/editEntityMenu/ImageStateMenu.vue')['default'] LogoAndLabel: typeof import('./src/components/LogoAndLabel.vue')['default'] MoveImageMenu: typeof import('./src/components/editEntityMenu/image/MoveImageMenu.vue')['default'] @@ -31,6 +32,7 @@ declare module 'vue' { TextItem: typeof import('@/modules/entities/TextItem.vue')['default'] TextMoveMenu: typeof import('./src/components/editEntityMenu/TextMoveMenu.vue')['default'] TextStateMenu: typeof import('./src/components/editEntityMenu/TextStateMenu.vue')['default'] + Toast: typeof import('primevue/toast')['default'] Tree: typeof import('primevue/tree')['default'] UserInfoHeaderWithSettings: typeof import('./src/components/UserInfoHeaderWithSettings.vue')['default'] } diff --git a/package.json b/package.json index 2001c5d999707e6e25d9424e27aeca97b1d65271..131c67df188266078267b40d77bde9d730589760 100644 --- a/package.json +++ b/package.json @@ -14,6 +14,7 @@ }, "dependencies": { "@primevue/themes": "^4.0.4", + "@supabase/supabase-js": "^2.45.1", "@vueuse/core": "^10.11.0", "@vueuse/integrations": "^10.11.0", "cropperjs": "^1.6.2", diff --git a/src/app/App.vue b/src/app/App.vue index c863b2c212458cc0de23afef931de2ba3cd308a7..26bfa004a56c37378f5b75fd58ea71514ae507dc 100644 --- a/src/app/App.vue +++ b/src/app/App.vue @@ -7,7 +7,7 @@ const visible = ref(false); diff --git a/src/app/auto-imports.d.ts b/src/app/auto-imports.d.ts index b14a1099bc9d648fb7159fe55bce138199bb5388..07ab7b9a30efbaa1b1306ef5dbcca4153ce2d09b 100644 --- a/src/app/auto-imports.d.ts +++ b/src/app/auto-imports.d.ts @@ -5,74 +5,85 @@ // Generated by unplugin-auto-import export {} declare global { - const EffectScope: typeof import('vue')['EffectScope'] - const [alias]: typeof import('[package-name]')['[from]'] - const [import-names]: typeof import('[package-name]')['[import-names]'] - const axios: typeof import('axios')['default'] - const computed: typeof import('vue')['computed'] - const createApp: typeof import('vue')['createApp'] - const customRef: typeof import('vue')['customRef'] - const defineAsyncComponent: typeof import('vue')['defineAsyncComponent'] - const defineComponent: typeof import('vue')['defineComponent'] - const effectScope: typeof import('vue')['effectScope'] - const getCurrentInstance: typeof import('vue')['getCurrentInstance'] - const getCurrentScope: typeof import('vue')['getCurrentScope'] - const h: typeof import('vue')['h'] - const inject: typeof import('vue')['inject'] - const isProxy: typeof import('vue')['isProxy'] - const isReactive: typeof import('vue')['isReactive'] - const isReadonly: typeof import('vue')['isReadonly'] - const isRef: typeof import('vue')['isRef'] - const markRaw: typeof import('vue')['markRaw'] - const nextTick: typeof import('vue')['nextTick'] - const onActivated: typeof import('vue')['onActivated'] - const onBeforeMount: typeof import('vue')['onBeforeMount'] - const onBeforeRouteLeave: typeof import('vue-router')['onBeforeRouteLeave'] - const onBeforeRouteUpdate: typeof import('vue-router')['onBeforeRouteUpdate'] - const onBeforeUnmount: typeof import('vue')['onBeforeUnmount'] - const onBeforeUpdate: typeof import('vue')['onBeforeUpdate'] - const onDeactivated: typeof import('vue')['onDeactivated'] - const onErrorCaptured: typeof import('vue')['onErrorCaptured'] - const onMounted: typeof import('vue')['onMounted'] - const onRenderTracked: typeof import('vue')['onRenderTracked'] - const onRenderTriggered: typeof import('vue')['onRenderTriggered'] - const onScopeDispose: typeof import('vue')['onScopeDispose'] - const onServerPrefetch: typeof import('vue')['onServerPrefetch'] - const onUnmounted: typeof import('vue')['onUnmounted'] - const onUpdated: typeof import('vue')['onUpdated'] - const provide: typeof import('vue')['provide'] - const reactive: typeof import('vue')['reactive'] - const readonly: typeof import('vue')['readonly'] - const ref: typeof import('vue')['ref'] - const resolveComponent: typeof import('vue')['resolveComponent'] - const shallowReactive: typeof import('vue')['shallowReactive'] - const shallowReadonly: typeof import('vue')['shallowReadonly'] - const shallowRef: typeof import('vue')['shallowRef'] - const toRaw: typeof import('vue')['toRaw'] - const toRef: typeof import('vue')['toRef'] - const toRefs: typeof import('vue')['toRefs'] - const toValue: typeof import('vue')['toValue'] - const triggerRef: typeof import('vue')['triggerRef'] - const unref: typeof import('vue')['unref'] - const useAttrs: typeof import('vue')['useAttrs'] - const useCssModule: typeof import('vue')['useCssModule'] - const useCssVars: typeof import('vue')['useCssVars'] - const useLink: typeof import('vue-router')['useLink'] - const useMyFetch: typeof import('@vueuse/core')['useFetch'] - const useRoute: typeof import('vue-router')['useRoute'] - const useRouter: typeof import('vue-router')['useRouter'] - const useSlots: typeof import('vue')['useSlots'] - const watch: typeof import('vue')['watch'] - const watchEffect: typeof import('vue')['watchEffect'] - const watchPostEffect: typeof import('vue')['watchPostEffect'] - const watchSyncEffect: typeof import('vue')['watchSyncEffect'] + const EffectScope: (typeof import('vue'))['EffectScope']; + const [alias]: (typeof import('[package-name]'))['[from]']; + const axios: (typeof import('axios'))['default']; + const computed: (typeof import('vue'))['computed']; + const createApp: (typeof import('vue'))['createApp']; + const customRef: (typeof import('vue'))['customRef']; + const defineAsyncComponent: (typeof import('vue'))['defineAsyncComponent']; + const defineComponent: (typeof import('vue'))['defineComponent']; + const effectScope: (typeof import('vue'))['effectScope']; + const getCurrentInstance: (typeof import('vue'))['getCurrentInstance']; + const getCurrentScope: (typeof import('vue'))['getCurrentScope']; + const h: (typeof import('vue'))['h']; + const inject: (typeof import('vue'))['inject']; + const isProxy: (typeof import('vue'))['isProxy']; + const isReactive: (typeof import('vue'))['isReactive']; + const isReadonly: (typeof import('vue'))['isReadonly']; + const isRef: (typeof import('vue'))['isRef']; + const markRaw: (typeof import('vue'))['markRaw']; + const nextTick: (typeof import('vue'))['nextTick']; + const onActivated: (typeof import('vue'))['onActivated']; + const onBeforeMount: (typeof import('vue'))['onBeforeMount']; + const onBeforeRouteLeave: (typeof import('vue-router'))['onBeforeRouteLeave']; + const onBeforeRouteUpdate: (typeof import('vue-router'))['onBeforeRouteUpdate']; + const onBeforeUnmount: (typeof import('vue'))['onBeforeUnmount']; + const onBeforeUpdate: (typeof import('vue'))['onBeforeUpdate']; + const onDeactivated: (typeof import('vue'))['onDeactivated']; + const onErrorCaptured: (typeof import('vue'))['onErrorCaptured']; + const onMounted: (typeof import('vue'))['onMounted']; + const onRenderTracked: (typeof import('vue'))['onRenderTracked']; + const onRenderTriggered: (typeof import('vue'))['onRenderTriggered']; + const onScopeDispose: (typeof import('vue'))['onScopeDispose']; + const onServerPrefetch: (typeof import('vue'))['onServerPrefetch']; + const onUnmounted: (typeof import('vue'))['onUnmounted']; + const onUpdated: (typeof import('vue'))['onUpdated']; + const provide: (typeof import('vue'))['provide']; + const reactive: (typeof import('vue'))['reactive']; + const readonly: (typeof import('vue'))['readonly']; + const ref: (typeof import('vue'))['ref']; + const resolveComponent: (typeof import('vue'))['resolveComponent']; + const shallowReactive: (typeof import('vue'))['shallowReactive']; + const shallowReadonly: (typeof import('vue'))['shallowReadonly']; + const shallowRef: (typeof import('vue'))['shallowRef']; + const toRaw: (typeof import('vue'))['toRaw']; + const toRef: (typeof import('vue'))['toRef']; + const toRefs: (typeof import('vue'))['toRefs']; + const toValue: (typeof import('vue'))['toValue']; + const triggerRef: (typeof import('vue'))['triggerRef']; + const unref: (typeof import('vue'))['unref']; + const useAttrs: (typeof import('vue'))['useAttrs']; + const useCssModule: (typeof import('vue'))['useCssModule']; + const useCssVars: (typeof import('vue'))['useCssVars']; + const useLink: (typeof import('vue-router'))['useLink']; + const useMyFetch: (typeof import('@vueuse/core'))['useFetch']; + const useRoute: (typeof import('vue-router'))['useRoute']; + const useRouter: (typeof import('vue-router'))['useRouter']; + const useSlots: (typeof import('vue'))['useSlots']; + const watch: (typeof import('vue'))['watch']; + const watchEffect: (typeof import('vue'))['watchEffect']; + const watchPostEffect: (typeof import('vue'))['watchPostEffect']; + const watchSyncEffect: (typeof import('vue'))['watchSyncEffect']; } // for type re-export declare global { // @ts-ignore - export type { Component, ComponentPublicInstance, ComputedRef, ExtractDefaultPropTypes, ExtractPropTypes, ExtractPublicPropTypes, InjectionKey, PropType, Ref, VNode, WritableComputedRef } from 'vue' - import('vue') + export type { + Component, + ComponentPublicInstance, + ComputedRef, + ExtractDefaultPropTypes, + ExtractPropTypes, + ExtractPublicPropTypes, + InjectionKey, + PropType, + Ref, + VNode, + WritableComputedRef + } from 'vue'; + import('vue'); // @ts-ignore - export type { RouteLocationRaw } from 'vue-router' - import('vue-router') + export type { RouteLocationRaw } from 'vue-router'; + import('vue-router'); } diff --git a/src/app/interfaces/entities.ts b/src/app/interfaces/entities.ts index d82328a355af046582734b3740ad43d255e79216..984ca161914392b00fd7c28916f91cdc459afa5e 100644 --- a/src/app/interfaces/entities.ts +++ b/src/app/interfaces/entities.ts @@ -36,8 +36,12 @@ export interface IImage { entity_uuid: string; title?: string; text?: string; - image_data: string; + text_size?: 'small' | 'medium' | 'large'; + paragraph_size?: 'small' | 'medium' | 'large' | 'extraLarge'; + text_position?: 'left' | 'right'; + image_url: string; image_width: number; image_height: number; image_position: 'left' | 'center' | 'right'; + image_scale: string; } diff --git a/src/app/interfaces/index.ts b/src/app/interfaces/index.ts index 424456135f391e911ae5f730ca6edcd14aad0bea..fcaa1f8132010ef7b5c0ffad8643ea3ff0565535 100644 --- a/src/app/interfaces/index.ts +++ b/src/app/interfaces/index.ts @@ -1,5 +1,5 @@ export interface IImageMainInfo { - url: string; - width: number; - height: number; + image_url: string; + image_width: number; + image_height: number; } diff --git a/src/app/stores/interface.ts b/src/app/stores/interface.ts index d834a66ad88590150042def97b59a265740394e8..2485d0c63952d64880d04009b8e0da95d29cff47 100644 --- a/src/app/stores/interface.ts +++ b/src/app/stores/interface.ts @@ -1,4 +1,5 @@ import { defineStore } from 'pinia'; +import { useWebsocketStore } from '@/app/stores/websocket'; export const useInterfaceStore = defineStore('interfaceStore', () => { const homeBackgroundUrl = ref( @@ -13,7 +14,27 @@ export const useInterfaceStore = defineStore('interfaceStore', () => { }); function changeHomeBackgroundUrl(newUrl: string) { homeBackgroundUrl.value = newUrl; + const websocketStore = useWebsocketStore(); + const data = { + event: 'changeHomeBackgroundUrl', + body: { + setting_name: 'homeBackgroundUrl', + setting_value: newUrl + } + }; + websocketStore.sendData(data); + } + function setHomeBackgroundUrlFromDB(url: string | null) { + if (!url) { + return; + } + homeBackgroundUrl.value = url; } - return { homeBackgroundUrl, defaultHomeBackgroundUrl, changeHomeBackgroundUrl }; + return { + homeBackgroundUrl, + defaultHomeBackgroundUrl, + changeHomeBackgroundUrl, + setHomeBackgroundUrlFromDB + }; }); diff --git a/src/app/stores/websocket.ts b/src/app/stores/websocket.ts index 3cff49c6e4eafe67164ca5a04ad0f434e84be6b6..20ea30571b2ebf132a2ebfdf0f74bbec81511c17 100644 --- a/src/app/stores/websocket.ts +++ b/src/app/stores/websocket.ts @@ -1,20 +1,26 @@ import { defineStore } from 'pinia'; import { useDataStore } from '@/app/stores/data'; import type { IEntity } from '@/app/interfaces/environment'; +import { useInterfaceStore } from '@/app/stores/interface'; export const useWebsocketStore = defineStore('websocketStore', () => { const socket = ref(); const dataStore = useDataStore(); + const interfaceStore = useInterfaceStore(); const homeEntities = computed(() => dataStore.homeEntities); onMounted(() => { socket.value = new WebSocket('ws://localhost:5000'); socket.value.onopen = () => { console.log('Websocket opened'); - const data = { + const getHomeEntitiesData = { event: 'getHomeEntities' }; - socket.value.send(JSON.stringify(data)); + socket.value.send(JSON.stringify(getHomeEntitiesData)); + const getHomeBackgroundUrlData = { + event: 'getHomeBackgroundUrl' + }; + socket.value.send(JSON.stringify(getHomeBackgroundUrlData)); }; socket.value.onmessage = (event: any) => { const response = JSON.parse(event.data); @@ -23,6 +29,9 @@ export const useWebsocketStore = defineStore('websocketStore', () => { case 'getHomeEntities': dataStore.editHomeEntities(response.data); break; + case 'getHomeBackgroundUrl': + interfaceStore.setHomeBackgroundUrlFromDB(response.data?.setting_value); + break; case 'createHomeEntity': { const entities = [...homeEntities.value]; entities.push(response.data); diff --git a/src/components/CreateEntityMenu.vue b/src/components/CreateEntityMenu.vue index 6dbdd34e98816aa0fb8630bbfc802f578cd4c8ae..cb07a8741501c385f47728605a26b72720acc5d4 100644 --- a/src/components/CreateEntityMenu.vue +++ b/src/components/CreateEntityMenu.vue @@ -4,31 +4,31 @@ import { useFileDialog } from '@vueuse/core'; const emit = defineEmits(['addEntity']); -const { - files, - open: uploadFile, - reset, - onChange -} = useFileDialog({ +const { open: uploadFile, onChange } = useFileDialog({ accept: 'image/*', reset: true }); -const addImage = (files: FileList) => { +const addImage = async (files: FileList) => { let image = new Image(); + const imageUuid = uuidv4(); const file = files[0]; - console.log('file', file, 'type: ', typeof file); - const url = URL.createObjectURL(file); - image.src = url; - console.log('image width and height: ', image.width, image.height); - console.log('url length: ', url.length); - emit('addEntity', { - entity_type: 'image', - entity_uuid: uuidv4(), - image_data: url, - image_position: 'left', - image_height: 300 + const reader = new FileReader(); + reader.readAsDataURL(file); + reader.addEventListener('load', () => { + image.src = String(reader.result); }); + image.onload = () => { + emit('addEntity', { + entity_type: 'image', + entity_uuid: imageUuid, + image_url: image.src, + image_position: 'left', + image_width: image.width, + image_height: image.height, + image_scale: '1' + }); + }; }; onChange((files) => { if (files && files?.length > 0) { diff --git a/src/components/editEntityMenu/ImageMoveMenu.vue b/src/components/editEntityMenu/ImageMoveMenu.vue index a38b828547a1ba91545a2da8be8a94b3dcb2084f..6ba5846fea0c71420f2f72d281babba2106f9c41 100644 --- a/src/components/editEntityMenu/ImageMoveMenu.vue +++ b/src/components/editEntityMenu/ImageMoveMenu.vue @@ -1,20 +1,16 @@