"use strict";
Object.defineProperty(exports, "__esModule", { value: true });
exports.create = create;
const language_core_1 = require("@vue/language-core");
const shared_1 = require("@vue/shared");
const path_browserify_1 = require("path-browserify");
const getUserPreferences_1 = require("volar-service-typescript/lib/configs/getUserPreferences");
const vscode_uri_1 = require("vscode-uri");
const nameCasing_1 = require("../nameCasing");
const vue_extract_file_1 = require("../plugins/vue-extract-file");
const utils_1 = require("../utils");
function create(ts, { getImportPathForFile }) {
    return {
        name: 'vue-document-drop',
        capabilities: {
            documentDropEditsProvider: true,
        },
        create(context) {
            return {
                async provideDocumentDropEdits(document, _position, dataTransfer) {
                    if (document.languageId !== 'html') {
                        return;
                    }
                    const info = (0, utils_1.resolveEmbeddedCode)(context, document.uri);
                    if (info?.code.id !== 'template') {
                        return;
                    }
                    let importUri;
                    for (const [mimeType, item] of dataTransfer) {
                        if (mimeType === 'text/uri-list') {
                            importUri = item.value;
                        }
                    }
                    if (!importUri || !info.root.vueCompilerOptions.extensions.some(ext => importUri.endsWith(ext))) {
                        return;
                    }
                    const { sfc } = info.root;
                    const script = sfc.scriptSetup ?? sfc.script;
                    if (!script) {
                        return;
                    }
                    const tagNameCasing = await (0, nameCasing_1.getTagNameCasing)(context, info.script.id);
                    const baseName = path_browserify_1.posix.basename(importUri);
                    const newName = (0, shared_1.capitalize)((0, shared_1.camelize)(baseName.slice(0, baseName.lastIndexOf('.'))));
                    const additionalEdit = {};
                    const code = [...(0, language_core_1.forEachEmbeddedCode)(info.root)].find(code => code.id === (sfc.scriptSetup ? 'scriptsetup_raw' : 'script_raw'));
                    const lastImportNode = (0, vue_extract_file_1.getLastImportNode)(ts, script.ast);
                    const incomingFileName = vscode_uri_1.URI.parse(importUri).fsPath.replace(/\\/g, '/');
                    let importPath;
                    const serviceScript = info.script.generated.languagePlugin.typescript?.getServiceScript(info.root);
                    if (serviceScript) {
                        const tsDocumentUri = context.encodeEmbeddedDocumentUri(info.script.id, serviceScript.code.id);
                        const tsDocument = context.documents.get(tsDocumentUri, serviceScript.code.languageId, serviceScript.code.snapshot);
                        const preferences = await (0, getUserPreferences_1.getUserPreferences)(context, tsDocument);
                        importPath = await getImportPathForFile(info.root.fileName, incomingFileName, preferences);
                    }
                    if (!importPath) {
                        importPath = path_browserify_1.posix.relative(path_browserify_1.posix.dirname(info.root.fileName), incomingFileName)
                            || importUri.slice(importUri.lastIndexOf('/') + 1);
                        if (!importPath.startsWith('./') && !importPath.startsWith('../')) {
                            importPath = './' + importPath;
                        }
                    }
                    const embeddedDocumentUriStr = context.encodeEmbeddedDocumentUri(info.script.id, code.id).toString();
                    additionalEdit.changes ??= {};
                    additionalEdit.changes[embeddedDocumentUriStr] = [];
                    additionalEdit.changes[embeddedDocumentUriStr].push({
                        range: lastImportNode
                            ? {
                                start: script.ast.getLineAndCharacterOfPosition(lastImportNode.end),
                                end: script.ast.getLineAndCharacterOfPosition(lastImportNode.end),
                            }
                            : {
                                start: script.ast.getLineAndCharacterOfPosition(0),
                                end: script.ast.getLineAndCharacterOfPosition(0),
                            },
                        newText: `\nimport ${newName} from '${importPath}'`
                            + (lastImportNode ? '' : '\n'),
                    });
                    if (sfc.script) {
                        const edit = (0, vue_extract_file_1.createAddComponentToOptionEdit)(ts, sfc, sfc.script.ast, newName);
                        if (edit) {
                            additionalEdit.changes[embeddedDocumentUriStr].push({
                                range: {
                                    start: document.positionAt(edit.range.start),
                                    end: document.positionAt(edit.range.end),
                                },
                                newText: edit.newText,
                            });
                        }
                    }
                    return {
                        insertText: `<${tagNameCasing === 0 /* TagNameCasing.Kebab */ ? (0, shared_1.hyphenate)(newName) : newName}$0 />`,
                        insertTextFormat: 2,
                        additionalEdit,
                    };
                },
            };
        },
    };
}
//# sourceMappingURL=vue-document-drop.js.map