alt+d 导出 markdown 文档 (docId 为空导出当前文档)

see https://ld246.com/article/1743689632996

// alt+d 导出markdown文档(docId为空导出当前文档)
// see https://ld246.com/article/1743689632996
{
    // 导出文档的id(docId为空导出当前文档)
    const docId = '';
  
    // alt+d事件
    document.addEventListener('keydown', async function(event) {
        // 检查是否按下了 Alt 键和 D 键,并确保没有按下其他修饰键
        if (
            event.altKey &&                  // Alt 键被按下
            event.code === 'KeyD' &&         // D 键被按下
            !event.shiftKey &&               // Shift 键未被按下
            !event.ctrlKey &&                // Ctrl 键未被按下
            !event.metaKey                   // Cmd 键(Meta 键)未被按下
        ) {
            event.preventDefault(); // 阻止默认行为(可选)
            const result = await fetchSyncPost('/api/export/exportMd', {id:docId||getCurrentDocId()});
            window.open(result.data.zip);
        }
    }, true);

    // 获取当前文档id
    function getCurrentDocId() {
        return (document.querySelector('[data-type="wnd"].layout__wnd--active .protyle:not(.fn__none)')||document.querySelector('[data-type="wnd"] .protyle:not(.fn__none)'))?.querySelector('.protyle-title')?.dataset?.nodeId;
    }

    // api请求
    async function fetchSyncPost(url, data, method = 'POST') {
        return await (await fetch(url, {method: method, body: JSON.stringify(data||{})})).json();
    }
}

直接导出markdown文件,而不是zip文件

缺点:只能导出单个文件,且不会导出图片资源

实现方式:直接读取文档 Markdown 源码,然后把内容直接写入到文件

// alt+d 导出markdown文档(docId为空导出当前文档)
// see https://ld246.com/article/1743689632996
{
    // 导出文档的id(docId为空导出当前文档)
    const docId = '';

    // 写入markdown文件路径
    // 需填写绝对路径
    // windows路径需要用\转义,比如 c:\\
    const toPath = '/your/path/Downloads/';
  
    // alt+d事件
    document.addEventListener('keydown', async function(event) {
        // 检查是否按下了 Alt 键和 D 键,并确保没有按下其他修饰键
        if (
            event.altKey &&                  // Alt 键被按下
            event.code === 'KeyD' &&         // D 键被按下
            !event.shiftKey &&               // Shift 键未被按下
            !event.ctrlKey &&                // Ctrl 键未被按下
            !event.metaKey                   // Cmd 键(Meta 键)未被按下
        ) {
            event.preventDefault(); // 阻止默认行为(可选)
            if(!isElectron()) {
                showMessage('仅在Electron客户端有效', true);
                return;
            }
            // 获取Markdown文本
            const doc = await fetchSyncPost("/api/lute/copyStdMarkdown", {id: docId || getCurrentDocId()});
            if(!doc || doc.code !== 0) {
                showMessage(doc.msg || '获取文档失败', true);
                return;
            }
            const markdown = doc.data || '';
            // 写入文本到文件
            const fs = require('fs');
            if (!fs.existsSync(toPath)) {
                showMessage('保存路径不存在', true);
                return;
            }
            let title = '未命名文档';
            if(docId) {
                const docInfo = fetchSyncPost('/api/block/getDocInfo',{id:docId});
                if(docInfo && docInfo.data && docInfo.data.name){
                    title = docInfo.data.name;
                }
            } else {
                title = getCurrentDocTitle() || title;
            }
            const path = require('path');
            fs.appendFileSync(path.join(toPath, title + '.md'), markdown, 'utf8');
            showMessage('已导出成功', false, 3000);
        }
    }, true);

    // 获取当前文档id
    function getCurrentDocId() {
        return (document.querySelector('[data-type="wnd"].layout__wnd--active .protyle:not(.fn__none)')||document.querySelector('[data-type="wnd"] .protyle:not(.fn__none)'))?.querySelector('.protyle-title')?.dataset?.nodeId;
    }

    function getCurrentDocTitle() {
        return (document.querySelector('[data-type="wnd"].layout__wnd--active .protyle:not(.fn__none)')||document.querySelector('[data-type="wnd"] .protyle:not(.fn__none)'))?.querySelector('.protyle-title__input')?.textContent;
    }

    // api请求
    async function fetchSyncPost(url, data, method = 'POST') {
        return await (await fetch(url, {method: method, body: JSON.stringify(data||{})})).json();
    }

    function isElectron() {
        return navigator.userAgent.includes('Electron');
    }

    // 发送消息
    function showMessage(message, isError = false, delay = 7000) {
        return fetch('/api/notification/' + (isError ? 'pushErrMsg' : 'pushMsg'), {
            "method": "POST",
            "body": JSON.stringify({"msg": message, "timeout": delay})
        });
    }
}

image.png

留下你的脚步
推荐阅读