Browse Source

refactor/refactored-editor-and-integrated-to-json-cell

pull/2946/head
Muhammed Mustafa 2 years ago
parent
commit
8b08f8ac87
  1. 41
      packages/nc-gui-v2/components/cell/Json.vue
  2. 72
      packages/nc-gui-v2/components/monaco/Editor.vue

41
packages/nc-gui-v2/components/cell/Json.vue

@ -7,11 +7,11 @@ import { inject, onMounted } from '#imports'
import { EditModeInj } from '~/context' import { EditModeInj } from '~/context'
interface Props { interface Props {
modelValue: any modelValue: string
} }
interface Emits { interface Emits {
(event: 'update:modelValue', model: any): void (event: 'update:modelValue', model: string): void
} }
const props = defineProps<Props>() const props = defineProps<Props>()
@ -22,40 +22,44 @@ let editEnabled = $(inject(EditModeInj))
let vModel = $(useVModel(props, 'modelValue', emits)) let vModel = $(useVModel(props, 'modelValue', emits))
let localValue = $ref({}) let localValue = $ref<string>('{}')
let error = $ref<string | undefined>(undefined) let error = $ref<string | undefined>(undefined)
let isExpanded = $ref(false) let isExpanded = $ref(false)
const onError = (e: any) => {
error = e
}
const clear = () => { const clear = () => {
error = undefined error = undefined
isExpanded = false isExpanded = false
editEnabled = false editEnabled = false
localValue = JSON.parse(vModel) localValue = vModel
} }
const onSave = () => { const onSave = () => {
vModel = JSON.stringify(localValue) vModel = localValue
isExpanded = false isExpanded = false
} }
const resetError = () => {
error = undefined
}
onMounted(() => { onMounted(() => {
localValue = JSON.parse(vModel) localValue = vModel
}) })
watch(
() => localValue,
(val) => {
try {
JSON.parse(val)
error = undefined
} catch (e: any) {
error = e
}
},
)
watch( watch(
() => editEnabled, () => editEnabled,
() => { () => {
isExpanded = false isExpanded = false
localValue = JSON.parse(vModel) localValue = vModel
}, },
) )
</script> </script>
@ -70,7 +74,9 @@ watch(
</a-button> </a-button>
<div class="flex flex-row"> <div class="flex flex-row">
<a-button type="text" size="small" :onclick="clear"><div class="text-xs">Cancel</div></a-button> <a-button type="text" size="small" :onclick="clear"><div class="text-xs">Cancel</div></a-button>
<a-button type="primary" size="small" :disabled="!!error"><div class="text-xs" :onclick="onSave">Save</div></a-button> <a-button type="primary" size="small" :disabled="!!error || localValue === vModel"
><div class="text-xs" :onclick="onSave">Save</div></a-button
>
</div> </div>
</div> </div>
<Editor <Editor
@ -78,9 +84,8 @@ watch(
class="min-w-full w-80" class="min-w-full w-80"
:class="{ 'expanded-editor': isExpanded, 'editor': !isExpanded }" :class="{ 'expanded-editor': isExpanded, 'editor': !isExpanded }"
:hide-minimap="true" :hide-minimap="true"
@validation-error="onError" :disable-deep-compare="true"
@update:model-value="localValue = $event" @update:model-value="localValue = $event"
@text-changed="resetError"
/> />
<span v-if="error" class="text-xs w-full py-1 text-red-500"> <span v-if="error" class="text-xs w-full py-1 text-red-500">
{{ error.toString() }} {{ error.toString() }}

72
packages/nc-gui-v2/components/monaco/Editor.vue

@ -7,22 +7,37 @@ import { onMounted } from '#imports'
import { deepCompare } from '~/utils' import { deepCompare } from '~/utils'
interface Props { interface Props {
modelValue: any modelValue: string | Record<string, any>
hideMinimap?: boolean hideMinimap?: boolean
lang?: string
validate?: boolean
disableDeepCompare?: boolean
} }
interface Emits { const { hideMinimap, lang = 'json', validate = true, disableDeepCompare = false, modelValue } = defineProps<Props>()
(event: 'update:modelValue', model: any): void
(event: 'validationError', error: any): void
(event: 'textChanged'): void
}
const props = defineProps<Props>()
const emits = defineEmits<Emits>()
const { hideMinimap } = props const emits = defineEmits(['update:modelValue'])
let vModel = $(useVModel(props, 'modelValue', emits)) let vModel = $computed<string>({
get: () => {
if (typeof modelValue === 'object') {
return JSON.stringify(modelValue, null, 2)
} else {
return modelValue
}
},
set: (newVal: string | Record<string, any>) => {
if (typeof modelValue === 'object') {
try {
emits('update:modelValue', typeof newVal === 'object' ? newVal : JSON.parse(newVal))
} catch (e) {
console.error(e)
}
} else {
emits('update:modelValue', newVal)
}
},
})
const isValid = ref(true) const isValid = ref(true)
@ -56,13 +71,15 @@ defineExpose({
}) })
onMounted(() => { onMounted(() => {
if (root.value) { if (root.value && lang) {
const model = monaco.editor.createModel(JSON.stringify(vModel, null, 2), 'json') const model = monaco.editor.createModel(vModel, lang)
if (lang === 'json') {
// configure the JSON language support with schemas and schema associations // configure the JSON language support with schemas and schema associations
monaco.languages.json.jsonDefaults.setDiagnosticsOptions({ monaco.languages.json.jsonDefaults.setDiagnosticsOptions({
validate: true, validate: validate as boolean,
}) })
}
editor = monaco.editor.create(root.value, { editor = monaco.editor.create(root.value, {
model, model,
@ -80,15 +97,18 @@ onMounted(() => {
}, },
}) })
editor.onDidChangeModelContent(async (e) => { editor.onDidChangeModelContent(async () => {
try { try {
isValid.value = true isValid.value = true
if (disableDeepCompare) {
vModel = editor.getValue()
} else {
const obj = JSON.parse(editor.getValue()) const obj = JSON.parse(editor.getValue())
emits('textChanged') if (!obj || !deepCompare(vModel, obj)) vModel = obj
if (!deepCompare(vModel, obj)) vModel = obj }
} catch (e) { } catch (e) {
isValid.value = false isValid.value = false
emits('validationError', e)
console.log(e) console.log(e)
} }
}) })
@ -98,17 +118,15 @@ onMounted(() => {
watch( watch(
() => vModel, () => vModel,
(v) => { (v) => {
if (!editor || !v) { if (!editor || !v) return
return
}
try { const editorValue = editor?.getValue()
if (!deepCompare(v, JSON.parse(editor?.getValue() as string))) { if (!disableDeepCompare) {
editor.setValue(JSON.stringify(v, null, 2)) if (!editorValue || !deepCompare(JSON.parse(v), JSON.parse(editorValue))) {
editor.setValue(v)
} }
} catch (e) { } else {
console.log(e) if (editorValue !== v) editor.setValue(v)
editor.setValue(JSON.stringify(v, null, 2))
} }
}, },
) )

Loading…
Cancel
Save