[js] 添加一个顶栏按钮,实现点击即打开代码片段界面

本贴最后更新于 237 天前,其中的信息可能已经时移世异

最终实现的 JS 代码片段:

/** * 在顶栏添加按钮,快捷打开代码片段界面 JS片段 * 参考 https://ld246.com/article/1674026309504 修改,同时感谢 [Undii](https://ld246.com/member/Undii) 提供 帮助 * 为顶栏增加代码片段按钮,点击后创建快捷键按下事件 * 挂件模式支持点击日记列出笔记本。 https://ld246.com/article/1674026309504 */ // 设置是否添加对应按钮 let g_addSnippets = true;// 设置 // 插入按钮 // 插入日历笔记本选择挂件 // 参考: https://ld246.com/article/1662969146166 原作者: BryceAndJuly // 参考: https://github.com/svchord/Rem-Craft 原作者: Seven Chor function addSnippets() { let barMode = document.getElementById("barMode"); barMode.insertAdjacentHTML( "afterend", '<div id="barSnippets_simulate" class="toolbar__item ariaLabel" aria-label="代码片段/Snippets"></div>' ); let settingBtn = document.getElementById("barSnippets_simulate"); settingBtn.innerHTML = `<svg><use xlink:href="#iconCode"></use></svg>`; settingBtn.addEventListener( "click", function (e) { dispatchKeyEvent("config"); setTimeout(function() { // 找到包含 data-name="appearance" 的 <li> 元素 var element = document.querySelector('li[data-name="appearance"]'); // 创建一个点击事件 var event = new MouseEvent('click', { bubbles: true, cancelable: true, view: window }); // 触发点击事件 element.dispatchEvent(event); }, 100); // 1000毫秒 = 1秒 setTimeout(function() { // 获取按钮元素 var button = document.getElementById('codeSnippet'); // 创建一个新的点击事件 var clickEvent = new MouseEvent('click', { view: window, bubbles: true, cancelable: true }); // 触发按钮的点击事件 button.dispatchEvent(clickEvent); }, 200); // 1000毫秒 = 1秒 } ); } /** * */ function dispatchKeyEvent(functionName) { let keyInit = parseHotKeyStr(window.top.siyuan.config.keymap.general[functionName].custom); keyInit["bubbles"] = true; let keydownEvent = new KeyboardEvent('keydown', keyInit); document.getElementsByTagName("body")[0].dispatchEvent(keydownEvent); let keyUpEvent = new KeyboardEvent('keyup', keyInit); document.getElementsByTagName("body")[0].dispatchEvent(keyUpEvent); } /** * * @param {*} hotkeyStr 思源hotkey格式 Refer: https://github.com/siyuan-note/siyuan/blob/d0f011b1a5b12e5546421f8bd442606bf0b5ad86/app/src/protyle/util/hotKey.ts#L4 * @returns KeyboardEventInit Refer: https://developer.mozilla.org/zh-CN/docs/Web/API/KeyboardEvent/KeyboardEvent */ function parseHotKeyStr(hotkeyStr) { let result = { ctrlKey: false, altKey: false, metaKey: false, shiftKey: false, key: 'A', keyCode: 0 } if (hotkeyStr == "" || hotkeyStr == undefined || hotkeyStr == null) { console.error("解析快捷键设置失败", hotkeyStr); throw new Error("解析快捷键设置失败"); } let onlyKey = hotkeyStr; if (hotkeyStr.indexOf("⌘") != -1) { result.ctrlKey = true; onlyKey = onlyKey.replace("⌘", ""); } if (hotkeyStr.indexOf("⌥") != -1) { result.altKey = true; onlyKey = onlyKey.replace("⌥", ""); } if (hotkeyStr.indexOf("⇧") != -1) { result.shiftKey = true; onlyKey = onlyKey.replace("⇧", ""); } // 未处理 windows btn (MetaKey) result.key = onlyKey; // 在https://github.com/siyuan-note/siyuan/commit/70acd57c4b4701b973a8ca93fadf6c003b24c789#diff-558f9f531a326d2fd53151e3fc250ac4bd545452ba782b0c7c18765a37a4e2cc // 更改中,思源改为使用keyCode判断快捷键按下事件,这里进行了对应的转换 // 另请参考该提交中涉及的文件 result.keyCode = keyCodeList[result.key]; console.assert(result.keyCode != undefined, `keyCode转换错误,key为${result.key}`); switch (result.key) { case "→": { result.key = "ArrowRight"; break; } case "←": { result.key = "ArrowLeft"; break; } case "↑": { result.key = "ArrowUp"; break; } case "↓": { result.key = "ArrowDown"; break; } case "⌦": { result.key = "Delete"; break; } case "⌫": { result.key = "Backspace"; break; } case "↩": { result.key = "Enter"; break; } } return result; } if (g_addSnippets) addSnippets(); const keyCodeList = { "⌫": 8, "⇥": 9, "↩": 13, "⇧": 16, "⌘": 91, "⌥": 18, "Pause": 19, "CapsLock": 20, "Escape": 27, " ": 32, "PageUp": 33, "PageDown": 34, "End": 35, "Home": 36, "←": 37, "↑": 38, "→": 39, "↓": 40, "PrintScreen": 44, "Insert": 45, "⌦": 46, "0": 48, "1": 49, "2": 50, "3": 51, "4": 52, "5": 53, "6": 54, "7": 55, "8": 56, "9": 57, "A": 65, "B": 66, "C": 67, "D": 68, "E": 69, "F": 70, "G": 71, "H": 72, "I": 73, "J": 74, "K": 75, "L": 76, "M": 77, "N": 78, "O": 79, "P": 80, "Q": 81, "R": 82, "S": 83, "T": 84, "U": 85, "V": 86, "W": 87, "X": 88, "Y": 89, "Z": 90, "ContextMenu": 93, "MyComputer": 182, "MyCalculator": 183, ";": 186, "=": 187, ",": 188, "-": 189, ".": 190, "/": 191, "`": 192, "[": 219, "\\": 220, "]": 221, "'": 222, "*": 106, "+": 107, "-": 109, ".": 110, "/": 111, "F1": 112, "F2": 113, "F3": 114, "F4": 115, "F5": 116, "F6": 117, "F7": 118, "F8": 119, "F9": 120, "F10": 121, "F11": 122, "F12": 123, "NumLock": 144, "ScrollLock": 145 };

原贴:

看到个 帖子 ,添加按钮应该是这样:

function addSnippets() { let barMode = document.getElementById("barMode"); barMode.insertAdjacentHTML( "afterend", '<div id="barSnippets_simulate" class="toolbar__item ariaLabel" aria-label="代码片段/Snippets" ></div>' ); let settingBtn = document.getElementById("barSnippets_simulate"); settingBtn.innerHTML = `<svg><use xlink:href="#iconCode"></use></svg>`; settingBtn.addEventListener("click", function() { openSnippets(); }, false); } function openSnippets() { } addSnippets();

但是我不知道怎么打开代码片段界面

  • 思源笔记

    思源笔记是一款隐私优先的个人知识管理系统,支持完全离线使用,同时也支持端到端加密同步。

    融合块、大纲和双向链接,重构你的思维。

    25723 引用 • 106432 回帖
  • 代码片段

    代码片段分为 CSS 与 JS 两种代码,添加在 [设置 - 外观 - 代码片段] 中,这些代码会在思源笔记加载时自动执行,用于改善笔记的样式或功能。

    用户在该标签下分享代码片段时需在帖子标题前添加 [css] [js] 用于区分代码片段类型。

    173 引用 • 1203 回帖
  • Q&A

    提问之前请先看《提问的智慧》,好的问题比好的答案更有价值。

    9857 引用 • 44803 回帖 • 76 关注
1 操作
JeffreyChen 在 2024-10-04 17:26:37 更新了该帖

相关帖子

被采纳的回答
  • Undii 1 via Android

    主要是 模拟点击应该在 点击顶栏按钮、并且打开设置页之后进行
    你这里的 setTimeout 并没有和点击顶栏按钮关联起来,也就是,“延迟模拟点击打开代码片段”,这个事情之会在代码生效时执行一次。在 4 秒内打开了设置,这里代码就会正确执行一次。

    settingBtn.addEventListener( "click", function (e) { dispatchKeyEvent("config"); // setTimeout写在这里 } );

    上面的代码,是将 click 点击顶栏按钮的事件和 function 关联了起来,具体的,这里执行了 dispatchKeyEvent 来模拟快捷键打开设置页面,

    所以 setTimeout 应该写在这里;

    我也在原帖中更新了相应的代码。

欢迎来到这里!

我们正在构建一个小众社区,大家在这里相互信任,以平等 • 自由 • 奔放的价值观进行分享交流。最终,希望大家能够找到与自己志同道合的伙伴,共同成长。

注册 关于
请输入回帖内容 ...
  • Undii 1 1 评论 via Android

    主要是 模拟点击应该在 点击顶栏按钮、并且打开设置页之后进行
    你这里的 setTimeout 并没有和点击顶栏按钮关联起来,也就是,“延迟模拟点击打开代码片段”,这个事情之会在代码生效时执行一次。在 4 秒内打开了设置,这里代码就会正确执行一次。

    settingBtn.addEventListener( "click", function (e) { dispatchKeyEvent("config"); // setTimeout写在这里 } );

    上面的代码,是将 click 点击顶栏按钮的事件和 function 关联了起来,具体的,这里执行了 dispatchKeyEvent 来模拟快捷键打开设置页面,

    所以 setTimeout 应该写在这里;

    我也在原帖中更新了相应的代码。

    1 回复
    用 api 的话 返回的是代码片段的内容 需要自己写一个 dialog 显示 这个最好用插件做。
    Undii
  • 其他回帖
  • kikkawa via macOS

    很实用,谢谢

  • 我首先理解了基础代码,然后再修改到可以正常打开设置界面,之后模拟点击我不会,就用开发者工具找到那个元素,然后:

    我:怎么用 JS 模拟点击按钮:<button class="b3-button b3-button--outline fn__flex-center fn__size200" id="codeSnippet"><svg><use xlink:href="#iconSettings"></use></svg>设置 </button>

    GPT:要使用 JavaScript 模拟点击按钮,可以通过以下步骤实现:

    1. 首先,获取对应的按钮元素。在这种情况下,您可以使用按钮的 id 属性来获取该元素。
    var button = document.getElementById('codeSnippet');
    1. 然后,您可以使用 click() 方法来模拟点击按钮。
    button.click();

    整体代码如下:

    var button = document.getElementById('codeSnippet'); button.click();

    这样,当您运行这段 JavaScript 代码时,它将模拟点击具有 id 为 codeSnippet 的按钮。

    我:让这个模拟点击在这段程序的最后阶段执行:

    function addSnippets() { let barMode = document.getElementById("barMode"); barMode.insertAdjacentHTML( "afterend", '<div id="barSnippets_simulate" class="toolbar__item ariaLabel" aria-label="代码片段/Snippets" ></div>' ); let settingBtn = document.getElementById("barSnippets_simulate"); settingBtn.innerHTML = `<svg><use xlink:href="#iconCode"></use></svg>`; settingBtn.addEventListener( "click", function (e) { dispatchKeyEvent("config"); }, false ); }

    GPT:要在这段程序的最后阶段执行模拟点击按钮的操作,您可以在 addSnippets() 函数的最后调用前面提到的模拟点击按钮的代码。这样可以确保在设置按钮被添加到页面并且事件监听器被设置后再触发点击事件。

    下面是修改后的代码:

    function addSnippets() { let barMode = document.getElementById("barMode"); barMode.insertAdjacentHTML( "afterend", '<div id="barSnippets_simulate" class="toolbar__item ariaLabel" aria-label="代码片段/Snippets" ></div>' ); let settingBtn = document.getElementById("barSnippets_simulate"); settingBtn.innerHTML = `<svg><use xlink:href="#iconCode"></use></svg>`; settingBtn.addEventListener( "click", function (e) { dispatchKeyEvent("config"); }, false ); // 模拟点击按钮 var button = document.getElementById('codeSnippet'); button.click(); }

    在这个修改后的代码中,addSnippets() 函数会先执行添加设置按钮的操作,然后再执行模拟点击按钮的操作。这样可以确保在设置按钮被添加到页面并且事件监听器被设置后再触发点击事件。

    然后发现界面加载要一点时间,于是就:

    我:我想在前面增加 1s 的延时

    GPT:要在调用按钮点击事件处理程序之前增加 1 秒的延时,您可以使用 setTimeout() 函数来实现。setTimeout() 函数可以在指定的时间间隔后执行指定的函数。

    下面是一个示例代码,演示如何在调用按钮点击事件处理程序之前增加 1 秒的延时:

    // 获取按钮元素 var button = document.getElementById('codeSnippet'); // 创建一个新的点击事件 var clickEvent = new MouseEvent('click', { view: window, bubbles: true, cancelable: true }); // 增加1秒延时后触发按钮的点击事件 setTimeout(function() { button.dispatchEvent(clickEvent); }, 1000); // 1000毫秒 = 1秒

    在这段代码中,setTimeout() 函数会在 1 秒后触发指定的函数,该函数会触发按钮的点击事件处理程序。这样就实现了在调用按钮点击事件处理程序之前增加 1 秒的延时。

    我就自己把代码加上去了。

  • 两个 setTimeout 的位置错了,应该放在 dispatchKeyEvent("config"); 之后;

    我没想过 GPT 还能做这个;这是怎么给 GPT 说的呢?

    setTimeout 延迟两秒似乎也不需要,能更快,设置几百应该就行;

    2 回复
  • 查看全部回帖
JeffreyChen
思源是支持 Markdown 语法输入的块编辑器,不是 Markdown 文件编辑器; 思源笔记同步教程:https://ld246.com/article/1692089679062 爱发电:https://afdian.com/a/JeffreyChen

推荐标签 标签

  • GitBook

    GitBook 使您的团队可以轻松编写和维护高质量的文档。 分享知识,提高团队的工作效率,让用户满意。

    3 引用 • 8 回帖 • 1 关注
  • 书籍

    宋真宗赵恒曾经说过:“书中自有黄金屋,书中自有颜如玉。”

    79 引用 • 396 回帖
  • 心情

    心是产生任何想法的源泉,心本体会陷入到对自己本体不能理解的状态中,因为心能产生任何想法,不能分出对错,不能分出自己。

    59 引用 • 369 回帖
  • Node.js

    Node.js 是一个基于 Chrome JavaScript 运行时建立的平台, 用于方便地搭建响应速度快、易于扩展的网络应用。Node.js 使用事件驱动, 非阻塞 I/O 模型而得以轻量和高效。

    139 引用 • 269 回帖 • 1 关注
  • Kafka

    Kafka 是一种高吞吐量的分布式发布订阅消息系统,它可以处理消费者规模的网站中的所有动作流数据。 这种动作(网页浏览,搜索和其他用户的行动)是现代系统中许多功能的基础。 这些数据通常是由于吞吐量的要求而通过处理日志和日志聚合来解决。

    36 引用 • 35 回帖 • 7 关注
  • OpenShift

    红帽提供的 PaaS 云,支持多种编程语言,为开发人员提供了更为灵活的框架、存储选择。

    14 引用 • 20 回帖 • 662 关注
  • Solidity

    Solidity 是一种智能合约高级语言,运行在 [以太坊] 虚拟机(EVM)之上。它的语法接近于 JavaScript,是一种面向对象的语言。

    3 引用 • 18 回帖 • 432 关注
  • Eclipse

    Eclipse 是一个开放源代码的、基于 Java 的可扩展开发平台。就其本身而言,它只是一个框架和一组服务,用于通过插件组件构建开发环境。

    76 引用 • 258 回帖 • 625 关注
  • 创造

    你创造的作品可能会帮助到很多人,如果是开源项目的话就更赞了!

    186 引用 • 1020 回帖
  • Spring

    Spring 是一个开源框架,是于 2003 年兴起的一个轻量级的 Java 开发框架,由 Rod Johnson 在其著作《Expert One-On-One J2EE Development and Design》中阐述的部分理念和原型衍生而来。它是为了解决企业应用开发的复杂性而创建的。框架的主要优势之一就是其分层架构,分层架构允许使用者选择使用哪一个组件,同时为 JavaEE 应用程序开发提供集成的框架。

    947 引用 • 1460 回帖
  • Sandbox

    如果帖子标签含有 Sandbox ,则该帖子会被视为“测试帖”,主要用于测试社区功能,排查 bug 等,该标签下内容不定期进行清理。

    438 引用 • 1250 回帖 • 595 关注
  • RabbitMQ

    RabbitMQ 是一个开源的 AMQP 实现,服务器端用 Erlang 语言编写,支持多种语言客户端,如:Python、Ruby、.NET、Java、C、PHP、ActionScript 等。用于在分布式系统中存储转发消息,在易用性、扩展性、高可用性等方面表现不俗。

    49 引用 • 60 回帖 • 349 关注
  • CloudFoundry

    Cloud Foundry 是 VMware 推出的业界第一个开源 PaaS 云平台,它支持多种框架、语言、运行时环境、云平台及应用服务,使开发人员能够在几秒钟内进行应用程序的部署和扩展,无需担心任何基础架构的问题。

    5 引用 • 18 回帖 • 185 关注
  • Excel
    31 引用 • 28 回帖
  • Angular

    AngularAngularJS 的新版本。

    26 引用 • 66 回帖 • 555 关注
  • JetBrains

    JetBrains 是一家捷克的软件开发公司,该公司位于捷克的布拉格,并在俄国的圣彼得堡及美国麻州波士顿都设有办公室,该公司最为人所熟知的产品是 Java 编程语言开发撰写时所用的集成开发环境:IntelliJ IDEA

    18 引用 • 54 回帖 • 1 关注
  • 笔记

    好记性不如烂笔头。

    310 引用 • 794 回帖
  • Sphinx

    Sphinx 是一个基于 SQL 的全文检索引擎,可以结合 MySQL、PostgreSQL 做全文搜索,它可以提供比数据库本身更专业的搜索功能,使得应用程序更容易实现专业化的全文检索。

    1 引用 • 223 关注
  • 一些有用的避坑指南。

    69 引用 • 93 回帖
  • Solo

    Solo 是一款小而美的开源博客系统,专为程序员设计。Solo 有着非常活跃的社区,可将文章作为帖子推送到社区,来自社区的回帖将作为博客评论进行联动(具体细节请浏览 B3log 构思 - 分布式社区网络)。

    这是一种全新的网络社区体验,让热爱记录和分享的你不再感到孤单!

    1441 引用 • 10069 回帖 • 494 关注
  • frp

    frp 是一个可用于内网穿透的高性能的反向代理应用,支持 TCP、UDP、 HTTP 和 HTTPS 协议。

    17 引用 • 7 回帖 • 3 关注
  • 京东

    京东是中国最大的自营式电商企业,2015 年第一季度在中国自营式 B2C 电商市场的占有率为 56.3%。2014 年 5 月,京东在美国纳斯达克证券交易所正式挂牌上市(股票代码:JD),是中国第一个成功赴美上市的大型综合型电商平台,与腾讯、百度等中国互联网巨头共同跻身全球前十大互联网公司排行榜。

    14 引用 • 102 回帖 • 314 关注
  • GitHub

    GitHub 于 2008 年上线,目前,除了 Git 代码仓库托管及基本的 Web 管理界面以外,还提供了订阅、讨论组、文本渲染、在线文件编辑器、协作图谱(报表)、代码片段分享(Gist)等功能。正因为这些功能所提供的便利,又经过长期的积累,GitHub 的用户活跃度很高,在开源世界里享有深远的声望,并形成了社交化编程文化(Social Coding)。

    209 引用 • 2040 回帖
  • TensorFlow

    TensorFlow 是一个采用数据流图(data flow graphs),用于数值计算的开源软件库。节点(Nodes)在图中表示数学操作,图中的线(edges)则表示在节点间相互联系的多维数据数组,即张量(tensor)。

    20 引用 • 19 回帖 • 4 关注
  • V2EX

    V2EX 是创意工作者们的社区。这里目前汇聚了超过 400,000 名主要来自互联网行业、游戏行业和媒体行业的创意工作者。V2EX 希望能够成为创意工作者们的生活和事业的一部分。

    16 引用 • 236 回帖 • 255 关注
  • jsoup

    jsoup 是一款 Java 的 HTML 解析器,可直接解析某个 URL 地址、HTML 文本内容。它提供了一套非常省力的 API,可通过 DOM,CSS 以及类似于 jQuery 的操作方法来取出和操作数据。

    6 引用 • 1 回帖 • 485 关注
  • Hadoop

    Hadoop 是由 Apache 基金会所开发的一个分布式系统基础架构。用户可以在不了解分布式底层细节的情况下,开发分布式程序。充分利用集群的威力进行高速运算和存储。

    90 引用 • 122 回帖 • 624 关注