Unverified Commit 0eee0519 authored by NGPixel's avatar NGPixel

feat: insert asset in editor

parent 708e6f77
...@@ -43,7 +43,8 @@ module.exports = { ...@@ -43,7 +43,8 @@ module.exports = {
__QUASAR_SSR_CLIENT__: 'readonly', __QUASAR_SSR_CLIENT__: 'readonly',
__QUASAR_SSR_PWA__: 'readonly', __QUASAR_SSR_PWA__: 'readonly',
process: 'readonly', process: 'readonly',
APOLLO_CLIENT: 'readonly' APOLLO_CLIENT: 'readonly',
EVENT_BUS: 'readonly'
}, },
// add your custom rules here // add your custom rules here
......
...@@ -72,6 +72,7 @@ ...@@ -72,6 +72,7 @@
"markdown-it-sub": "1.0.0", "markdown-it-sub": "1.0.0",
"markdown-it-sup": "1.0.0", "markdown-it-sup": "1.0.0",
"markdown-it-task-lists": "2.1.1", "markdown-it-task-lists": "2.1.1",
"mitt": "3.0.0",
"pako": "2.1.0", "pako": "2.1.0",
"pinia": "2.0.33", "pinia": "2.0.33",
"prosemirror-commands": "1.5.1", "prosemirror-commands": "1.5.1",
......
...@@ -38,6 +38,7 @@ module.exports = configure(function (/* ctx */) { ...@@ -38,6 +38,7 @@ module.exports = configure(function (/* ctx */) {
boot: [ boot: [
'apollo', 'apollo',
'components', 'components',
'eventbus',
'i18n' 'i18n'
], ],
......
import { boot } from 'quasar/wrappers'
import mitt from 'mitt'
export default boot(({ app }) => {
const emitter = mitt()
if (import.meta.env.SSR) {
global.EVENT_BUS = emitter
} else {
window.EVENT_BUS = emitter
}
})
...@@ -233,7 +233,7 @@ ...@@ -233,7 +233,7 @@
</template> </template>
<script setup> <script setup>
import { reactive, ref, shallowRef, nextTick, onBeforeMount, onMounted, watch } from 'vue' import { reactive, ref, shallowRef, nextTick, onMounted, watch, onBeforeUnmount } from 'vue'
import { useMeta, useQuasar, setCssVar } from 'quasar' import { useMeta, useQuasar, setCssVar } from 'quasar'
import { useI18n } from 'vue-i18n' import { useI18n } from 'vue-i18n'
import { get, flatten, last, times, startsWith, debounce } from 'lodash-es' import { get, flatten, last, times, startsWith, debounce } from 'lodash-es'
...@@ -297,9 +297,26 @@ const CtrlKey = /Mac/.test(navigator.platform) ? 'Cmd' : 'Ctrl' ...@@ -297,9 +297,26 @@ const CtrlKey = /Mac/.test(navigator.platform) ? 'Cmd' : 'Ctrl'
// METHODS // METHODS
function insertAssets () { function insertAssets () {
siteStore.$patch({ siteStore.openFileManager({ insertMode: true })
overlay: 'FileManager' }
})
function insertAssetClb (opts) {
const assetPath = opts.folderPath ? `${opts.folderPath}/${opts.fileName}` : opts.fileName
let content = ''
switch (opts.type) {
case 'asset': {
content = `![${opts.title}](${assetPath})`
break
}
case 'page': {
content = `[${opts.title}](${assetPath})`
break
}
}
insertAtCursor({ content })
setTimeout(() => {
cm.value.focus()
}, 500)
} }
function insertTable () { function insertTable () {
...@@ -505,6 +522,8 @@ onMounted(async () => { ...@@ -505,6 +522,8 @@ onMounted(async () => {
cm.value.focus() cm.value.focus()
}) })
EVENT_BUS.on('insertAsset', insertAssetClb)
// this.$root.$on('editorInsert', opts => { // this.$root.$on('editorInsert', opts => {
// switch (opts.kind) { // switch (opts.kind) {
// case 'IMAGE': // case 'IMAGE':
...@@ -538,7 +557,8 @@ onMounted(async () => { ...@@ -538,7 +557,8 @@ onMounted(async () => {
// }) // })
}) })
onBeforeMount(() => { onBeforeUnmount(() => {
EVENT_BUS.off('insertAsset', insertAssetClb)
// if (editor.value) { // if (editor.value) {
// editor.value.destroy() // editor.value.destroy()
// } // }
......
...@@ -499,9 +499,7 @@ const menuBar = [ ...@@ -499,9 +499,7 @@ const menuBar = [
icon: 'mdi-image-plus', icon: 'mdi-image-plus',
title: 'Image', title: 'Image',
action: () => { action: () => {
siteStore.$patch({ siteStore.openFileManager({ insertMode: true })
overlay: 'FileManager'
})
} }
}, },
{ {
......
...@@ -79,6 +79,16 @@ q-layout.fileman(view='hHh lpR lFr', container) ...@@ -79,6 +79,16 @@ q-layout.fileman(view='hHh lpR lFr', container)
) )
label {{item.label}} label {{item.label}}
span {{item.value}} span {{item.value}}
template(v-if='insertMode')
q-separator.q-my-md
q-btn.full-width(
@click='insertItem()'
:label='t(`common.actions.insert`)'
color='primary'
icon='las la-plus-circle'
push
padding='sm'
)
q-page-container q-page-container
q-page.fileman-center.column q-page.fileman-center.column
//- TOOLBAR ----------------------------------------------------- //- TOOLBAR -----------------------------------------------------
...@@ -223,7 +233,7 @@ q-layout.fileman(view='hHh lpR lFr', container) ...@@ -223,7 +233,7 @@ q-layout.fileman(view='hHh lpR lFr', container)
active-class='active' active-class='active'
:active='item.id === state.currentFileId' :active='item.id === state.currentFileId'
@click.native='selectItem(item)' @click.native='selectItem(item)'
@dblclick.native='openItem(item)' @dblclick.native='doubleClickItem(item)'
) )
q-item-section.fileman-filelist-icon(avatar) q-item-section.fileman-filelist-icon(avatar)
q-icon(:name='item.icon', :size='state.isCompact ? `md` : `xl`') q-icon(:name='item.icon', :size='state.isCompact ? `md` : `xl`')
...@@ -242,14 +252,18 @@ q-layout.fileman(view='hHh lpR lFr', container) ...@@ -242,14 +252,18 @@ q-layout.fileman(view='hHh lpR lFr', container)
) )
q-card.q-pa-sm q-card.q-pa-sm
q-list(dense, style='min-width: 150px;') q-list(dense, style='min-width: 150px;')
q-item(clickable, v-if='item.type !== `folder`', @click='insertItem(item)')
q-item-section(side)
q-icon(name='las la-plus-circle', color='primary')
q-item-section {{ t(`common.actions.insert`) }}
q-item(clickable, v-if='item.type === `page`') q-item(clickable, v-if='item.type === `page`')
q-item-section(side) q-item-section(side)
q-icon(name='las la-edit', color='orange') q-icon(name='las la-edit', color='orange')
q-item-section Edit q-item-section {{ t(`common.actions.edit`) }}
q-item(clickable, v-if='item.type !== `folder`', @click='openItem(item)') q-item(clickable, v-if='item.type !== `folder`', @click='openItem(item)')
q-item-section(side) q-item-section(side)
q-icon(name='las la-eye', color='primary') q-icon(name='las la-eye', color='primary')
q-item-section View q-item-section {{ t(`common.actions.view`) }}
template(v-if='item.type === `asset` && item.imageEdit') template(v-if='item.type === `asset` && item.imageEdit')
q-item(clickable) q-item(clickable)
q-item-section(side) q-item-section(side)
...@@ -262,11 +276,11 @@ q-layout.fileman(view='hHh lpR lFr', container) ...@@ -262,11 +276,11 @@ q-layout.fileman(view='hHh lpR lFr', container)
q-item(clickable, v-if='item.type !== `folder`', @click='copyItemURL(item)') q-item(clickable, v-if='item.type !== `folder`', @click='copyItemURL(item)')
q-item-section(side) q-item-section(side)
q-icon(name='las la-clipboard', color='primary') q-icon(name='las la-clipboard', color='primary')
q-item-section Copy URL q-item-section {{ t(`common.actions.copyURL`) }}
q-item(clickable, v-if='item.type !== `folder`', @click='') q-item(clickable, v-if='item.type !== `folder`', @click='')
q-item-section(side) q-item-section(side)
q-icon(name='las la-download', color='primary') q-icon(name='las la-download', color='primary')
q-item-section Download q-item-section {{ t(`common.actions.download`) }}
q-item(clickable) q-item(clickable)
q-item-section(side) q-item-section(side)
q-icon(name='las la-copy', color='teal') q-icon(name='las la-copy', color='teal')
...@@ -282,7 +296,7 @@ q-layout.fileman(view='hHh lpR lFr', container) ...@@ -282,7 +296,7 @@ q-layout.fileman(view='hHh lpR lFr', container)
q-item(clickable, @click='delItem(item)') q-item(clickable, @click='delItem(item)')
q-item-section(side) q-item-section(side)
q-icon(name='las la-trash-alt', color='negative') q-icon(name='las la-trash-alt', color='negative')
q-item-section.text-negative Delete q-item-section.text-negative {{ t(`common.actions.delete`) }}
q-footer q-footer
q-bar.fileman-path q-bar.fileman-path
small.text-caption.text-grey-7 {{folderPath}} small.text-caption.text-grey-7 {{folderPath}}
...@@ -298,7 +312,7 @@ q-layout.fileman(view='hHh lpR lFr', container) ...@@ -298,7 +312,7 @@ q-layout.fileman(view='hHh lpR lFr', container)
<script setup> <script setup>
import { useI18n } from 'vue-i18n' import { useI18n } from 'vue-i18n'
import { computed, defineAsyncComponent, nextTick, onMounted, reactive, ref, watch } from 'vue' import { computed, defineAsyncComponent, nextTick, onMounted, reactive, ref, toRaw, watch } from 'vue'
import { filesize } from 'filesize' import { filesize } from 'filesize'
import { useQuasar } from 'quasar' import { useQuasar } from 'quasar'
import { DateTime } from 'luxon' import { DateTime } from 'luxon'
...@@ -377,6 +391,8 @@ const treeComp = ref(null) ...@@ -377,6 +391,8 @@ const treeComp = ref(null)
// COMPUTED // COMPUTED
const insertMode = computed(() => siteStore.overlayOpts?.insertMode ?? false)
const folderPath = computed(() => { const folderPath = computed(() => {
if (!state.currentFolderId) { if (!state.currentFolderId) {
return '/' return '/'
...@@ -506,6 +522,14 @@ function close () { ...@@ -506,6 +522,14 @@ function close () {
siteStore.overlay = null siteStore.overlay = null
} }
function insertItem (item) {
if (!item) {
item = find(state.fileList, ['id', state.currentFileId])
}
EVENT_BUS.emit('insertAsset', toRaw(item))
close()
}
async function treeLazyLoad (nodeId, isCurrent, { done, fail }) { async function treeLazyLoad (nodeId, isCurrent, { done, fail }) {
await loadTree({ parentId: nodeId, types: isCurrent ? null : ['folder'] }) await loadTree({ parentId: nodeId, types: isCurrent ? null : ['folder'] })
done() done()
...@@ -849,6 +873,14 @@ function selectItem (item) { ...@@ -849,6 +873,14 @@ function selectItem (item) {
} }
} }
function doubleClickItem (item) {
if (insertMode.value) {
insertItem(item)
} else {
openItem(item)
}
}
function openItem (item) { function openItem (item) {
switch (item.type) { switch (item.type) {
case 'folder': { case 'folder': {
......
...@@ -48,6 +48,11 @@ q-header.bg-header.text-white.site-header( ...@@ -48,6 +48,11 @@ q-header.bg-header.text-white.site-header(
v-if='state.search.length > 0' v-if='state.search.length > 0'
:color='$q.dark.isActive ? `blue` : `grey-4`' :color='$q.dark.isActive ? `blue` : `grey-4`'
) )
q-badge.q-ml-sm(
label='v3 Preview'
color='pink'
outline
)
q-btn.q-ml-md( q-btn.q-ml-md(
flat flat
round round
...@@ -131,7 +136,7 @@ const state = reactive({ ...@@ -131,7 +136,7 @@ const state = reactive({
// METHODS // METHODS
function openFileManager () { function openFileManager () {
siteStore.overlay = 'FileManager' siteStore.openFileManager()
} }
</script> </script>
......
...@@ -116,7 +116,7 @@ function create (editor) { ...@@ -116,7 +116,7 @@ function create (editor) {
} }
function openFileManager () { function openFileManager () {
siteStore.overlay = 'FileManager' siteStore.openFileManager()
} }
function newFolder () { function newFolder () {
......
...@@ -1164,6 +1164,7 @@ ...@@ -1164,6 +1164,7 @@
"common.actions.commit": "Commit", "common.actions.commit": "Commit",
"common.actions.confirm": "Confirm", "common.actions.confirm": "Confirm",
"common.actions.copy": "Copy", "common.actions.copy": "Copy",
"common.actions.copyURL": "Copy URL",
"common.actions.create": "Create", "common.actions.create": "Create",
"common.actions.deactivate": "Deactivate", "common.actions.deactivate": "Deactivate",
"common.actions.delete": "Delete", "common.actions.delete": "Delete",
...@@ -1198,6 +1199,7 @@ ...@@ -1198,6 +1199,7 @@
"common.actions.select": "Select", "common.actions.select": "Select",
"common.actions.update": "Update", "common.actions.update": "Update",
"common.actions.upload": "Upload", "common.actions.upload": "Upload",
"common.actions.view": "View",
"common.clipboard.failure": "Failed to copy to clipboard.", "common.clipboard.failure": "Failed to copy to clipboard.",
"common.clipboard.success": "Copied to clipboard successfully.", "common.clipboard.success": "Copied to clipboard successfully.",
"common.clipboard.uuid": "Copy UUID to clipboard.", "common.clipboard.uuid": "Copy UUID to clipboard.",
......
...@@ -149,7 +149,7 @@ const isSidebarShown = computed(() => { ...@@ -149,7 +149,7 @@ const isSidebarShown = computed(() => {
// METHODS // METHODS
function openFileManager () { function openFileManager () {
siteStore.overlay = 'FileManager' siteStore.openFileManager()
} }
</script> </script>
......
...@@ -25,6 +25,7 @@ export const useSiteStore = defineStore('site', { ...@@ -25,6 +25,7 @@ export const useSiteStore = defineStore('site', {
showSideNav: true, showSideNav: true,
showSidebar: true, showSidebar: true,
overlay: null, overlay: null,
overlayOpts: {},
features: { features: {
ratingsMode: 'off', ratingsMode: 'off',
reasonForChange: 'required', reasonForChange: 'required',
...@@ -70,6 +71,14 @@ export const useSiteStore = defineStore('site', { ...@@ -70,6 +71,14 @@ export const useSiteStore = defineStore('site', {
overlayIsShown: (state) => Boolean(state.overlay) overlayIsShown: (state) => Boolean(state.overlay)
}, },
actions: { actions: {
openFileManager (opts) {
this.$patch({
overlay: 'FileManager',
overlayOpts: {
insertMode: opts?.insertMode ?? false
}
})
},
async loadSite (hostname) { async loadSite (hostname) {
try { try {
const resp = await APOLLO_CLIENT.query({ const resp = await APOLLO_CLIENT.query({
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment