<script>
    import { onMount, onDestroy } from "svelte";
    import { basicSetup, EditorView } from "codemirror";
    import { EditorState, Compartment } from "@codemirror/state";
    import { keymap } from "@codemirror/view";
    import { indentWithTab } from "@codemirror/commands";
    import { json, jsonParseLinter } from "@codemirror/lang-json";
    import { linter, lintGutter } from "@codemirror/lint";
    let parentElement;
    let codeMirrorView;
    export let value;
    export let editable = true;

    onMount(() => {
        let language = new Compartment();
        let tabSize = new Compartment();

        let state = EditorState.create({
            doc: JSON.stringify(value, null, 4),
            extensions: [
                basicSetup,
                keymap.of([indentWithTab]),
                language.of(json()),
                json(),
                tabSize.of(EditorState.tabSize.of(4)),
                lintGutter(),
                basicSetup,
                EditorView.editable.of(editable),
                EditorView.updateListener.of(function (e) {
                    if (e.docChanged) {
                        value = e.state.doc.toString();
                    }
                }),
                linter(jsonParseLinter()),
            ],
        });

        

        codeMirrorView = new EditorView({
            state,

            parent: parentElement,
        });
    });

    onDestroy(() => {
        if (codeMirrorView) {
            codeMirrorView.destroy();
        }
    });
</script>

<div class="is-editable-{editable}" bind:this={parentElement} />
