Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Refactor paste as JSON logic #460

Merged
merged 2 commits into from
Jul 11, 2024
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
6 changes: 0 additions & 6 deletions src/lib/components/controls/EditableDiv.svelte
Original file line number Diff line number Diff line change
Expand Up @@ -37,12 +37,6 @@
// eslint-disable-next-line @typescript-eslint/ban-ts-comment
// @ts-ignore
domValue.refresh = handleValueInput

// The cancel method can be used to cancel editing, without firing a change
// when the contents did change in the meantime. It is the same as pressing ESC
// eslint-disable-next-line @typescript-eslint/ban-ts-comment
// @ts-ignore
domValue.cancel = handleCancel
}
})

Expand Down
25 changes: 4 additions & 21 deletions src/lib/components/modes/tablemode/TableMode.svelte
Original file line number Diff line number Diff line change
Expand Up @@ -77,8 +77,7 @@
findParentWithNodeName,
getDataPathFromTarget,
getWindow,
isChildOf,
isEditableDivRef
isChildOf
} from '$lib/utils/domUtils.js'
import { createDebug } from '$lib/utils/debug.js'
import {
Expand Down Expand Up @@ -219,7 +218,7 @@
let text: string | undefined
let parseError: ParseError | undefined = undefined

let pastedJson: PastedJson
let pastedJson: PastedJson | undefined

let searchResultDetails: SearchResultDetails | undefined
let searchResults: SearchResults | undefined
Expand Down Expand Up @@ -1096,24 +1095,8 @@
return
}

const { path, contents } = pastedJson

// exit edit mode
const refEditableDiv = refContents?.querySelector('.jse-editable-div') ?? undefined
if (isEditableDivRef(refEditableDiv)) {
refEditableDiv.cancel()
}

// replace the value with the JSON object/array
const operations: JSONPatchDocument = [
{
op: 'replace',
path: compileJSONPointer(path),
value: contents
}
]

handlePatch(operations)
const { onPasteAsJson } = pastedJson
onPasteAsJson()

// TODO: get rid of the setTimeout here
setTimeout(focus)
Expand Down
28 changes: 4 additions & 24 deletions src/lib/components/modes/treemode/TreeMode.svelte
Original file line number Diff line number Diff line change
Expand Up @@ -79,8 +79,7 @@
findParentWithNodeName,
getWindow,
isChildOf,
isChildOfNodeName,
isEditableDivRef
isChildOfNodeName
} from '$lib/utils/domUtils.js'
import {
convertValue,
Expand Down Expand Up @@ -264,7 +263,7 @@

$: debug('selection', selection)

let pastedJson: PastedJson
let pastedJson: PastedJson | undefined

let searchResultDetails: SearchResultDetails | undefined
let searchResults: SearchResults | undefined
Expand Down Expand Up @@ -1770,29 +1769,10 @@
return
}

const { path, contents } = pastedJson
const { onPasteAsJson } = pastedJson
pastedJson = undefined

// exit edit mode
const refEditableDiv = refContents?.querySelector('.jse-editable-div') ?? undefined
if (isEditableDivRef(refEditableDiv)) {
refEditableDiv.cancel()
}

// replace the value with the JSON object/array
const operations: JSONPatchDocument = [
{
op: 'replace',
path: compileJSONPointer(path),
value: contents
}
]

handlePatch(operations, (patchedJson, patchedState) => {
return {
state: expandSmart(patchedJson, patchedState, path)
}
})
onPasteAsJson()

// TODO: get rid of the setTimeout here
setTimeout(focus)
Expand Down
22 changes: 20 additions & 2 deletions src/lib/plugins/value/components/EditableValue.svelte
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
<svelte:options immutable={true} />

<script lang="ts">
import type { JSONPath } from 'immutable-json-patch'
import type { JSONPatchDocument, JSONPath } from 'immutable-json-patch'
import { compileJSONPointer } from 'immutable-json-patch'
import { isObjectOrArray, stringConvert } from '$lib/utils/typeUtils.js'
import { createValueSelection, getFocusPath } from '$lib/logic/selection.js'
Expand All @@ -18,6 +18,7 @@
} from '$lib/types.js'
import { UpdateSelectionAfterChange } from '$lib/types.js'
import { isEqual } from 'lodash-es'
import { expandSmart } from '$lib/logic/documentState'

export let path: JSONPath
export let value: unknown
Expand Down Expand Up @@ -78,7 +79,24 @@
if (isObjectOrArray(pastedJson)) {
onPasteJson({
path,
contents: pastedJson
contents: pastedJson,
onPasteAsJson: () => {
// exit edit mode
handleCancelChange()

// replace the value with the JSON object/array
const operations: JSONPatchDocument = [
{
op: 'replace',
path: compileJSONPointer(path),
value: pastedJson
}
]

onPatch(operations, (patchedJson, patchedState) => ({
state: expandSmart(patchedJson, patchedState, path)
}))
}
})
}
} catch (err) {
Expand Down
8 changes: 6 additions & 2 deletions src/lib/types.ts
Original file line number Diff line number Diff line change
Expand Up @@ -383,7 +383,7 @@ export type OnSort = (params: {
}) => void
export type OnFind = (findAndReplace: boolean) => void
export type OnPaste = (pastedText: string) => void
export type OnPasteJson = (pastedJson: { path: JSONPath; contents: unknown }) => void
export type OnPasteJson = (pastedJson: PastedJson) => void
export type OnExpand = (relativePath: JSONPath) => boolean
export type OnRenderValue = (props: RenderValueProps) => RenderValueComponentDescription[]
export type OnClassName = (path: JSONPath, value: unknown) => string | undefined
Expand Down Expand Up @@ -449,7 +449,11 @@ export interface ValueNormalization {
unescapeValue: UnescapeValue
}

export type PastedJson = { contents: unknown; path: JSONPath } | undefined
export type PastedJson = {
path: JSONPath
contents: unknown
onPasteAsJson: () => void
}

export interface DragInsideProps {
json: unknown
Expand Down
14 changes: 0 additions & 14 deletions src/lib/utils/domUtils.ts
Original file line number Diff line number Diff line change
Expand Up @@ -405,17 +405,3 @@ export function findNearestElement<T extends Element>({

return undefined
}

export interface EditableDivElement extends HTMLDivElement {
refresh: () => void
cancel: () => void
}

export function isEditableDivRef(element: Element | undefined): element is EditableDivElement {
return (
!!element &&
element.nodeName === 'DIV' &&
typeof (element as unknown as Record<string, unknown>).refresh === 'function' &&
typeof (element as unknown as Record<string, unknown>).cancel === 'function'
)
}