js 代码如何实现根据输入的内容自动给其块加上属性或自定义属性

例如:

但我输入的文字符合自己设定的正则表达式的规则,则自动给当前块加上相关属性

例如当我笔记中存在成都时,自动给当前块加上“地点”:“成都”的属性

  • 思源笔记

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

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

    22246 引用 • 88921 回帖
  • Q&A

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

    8070 引用 • 36873 回帖 • 161 关注

相关帖子

被采纳的回答
  • wilsons 1 1 赞同

    监听编辑器输入事件,仅供参考

    (()=>{
        // 编辑器输入事件
        onEditorInput((editor) => {
            // 获取光标所在元素
            const currEl = getCursorElement();
            console.log('当前元素', currEl);
            // 获取当前块
            const currBlock = currEl.closest('[data-type]');
            console.log('当前块', currBlock);
        });
      
        // 编辑器输入事件
        function onEditorInput(callback) {
            whenElementExist(isMobile()?'body':'.layout__center').then(async element => {
                // 等待笔记列表加载完毕
                await sleep(40);
                // 监听编辑器加载事件
                observeDomChange(element, async (mutation) => {
                    if (mutation.target.classList?.contains("protyle-wysiwyg")) {
                        console.log(mutation.target);
                       const editor = mutation.target;
                        if(editor && editor.closest){
                            // 等待编辑器加载完毕
                            const protyle = editor.closest(".protyle");
                            if(protyle.dataset.loading !== 'finished'){
                                await whenElementExist(()=>editor?.closest(".protyle") === 'finished');
                            }
                            if(!editor.getAttribute('custom-listened')){
                                editor.setAttribute('custom-listened', true);
                                //console.log('listen editor');
                                editor.addEventListener('input', ()=>{
                                    //console.log('editor inputed');
                                    callback(editor);
                                })
                            }
                        }
                    }
                });
            });
        }
        // 获取光标所在元素
        function getCursorElement() {
            const selection = window.getSelection();
            if (selection.rangeCount > 0) {
                const range = selection.getRangeAt(0);
                // 获取选择范围的起始位置所在的节点
                const startContainer = range.startContainer;
                // 如果起始位置是文本节点,返回其父元素节点
                const cursorElement = startContainer.nodeType === Node.TEXT_NODE
                    ? startContainer.parentElement
                    : startContainer;
      
                return cursorElement;
            }
            return null;
        }
        // 观察元素被添加
        function observeDomChange(selector, callback) {
            // 定义一个回调函数,当DOM发生变化时调用
            const onChange = function(mutationsList, observer) {
                for (const mutation of mutationsList) {
                    if (mutation.type === 'childList') {
                        callback(mutation);
                    }
                }
            };
            // 创建一个观察器实例,并传入回调函数
            const observer = new MutationObserver(onChange);
            // 配置观察选项:指定需要观察哪些变动
            const config = { attributes: false, childList: true, subtree: true };
            // 获取目标节点
            const targetNode = typeof selector === 'string' ? document.querySelector(selector) : selector;
            // 如果目标节点存在,则开始观察
            if (targetNode) {
                observer.observe(targetNode, config);
            }
            // 返回一个函数,用于停止观察
            return () => {
                observer.disconnect();
            };
        }
        // 是否手机端
        function isMobile() {
            return !!document.getElementById("sidebar");
        }
        // 延迟执行
        function sleep(ms) {
            return new Promise(resolve => setTimeout(resolve, ms));
        }
        // 等待元素渲染完成后执行
        function whenElementExist(selector) {
            return new Promise(resolve => {
                const checkForElement = () => {
                    let element = null;
                    if (typeof selector === 'function') {
                        element = selector();
                    } else {
                        element = document.querySelector(selector);
                    }
                    if (element) {
                        resolve(element);
                    } else {
                        requestAnimationFrame(checkForElement);
                    }
                };
                checkForElement();
            });
        }
    })();
    

欢迎来到这里!

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

注册 关于
请输入回帖内容 ...
  • stevehfut
    作者

    可以提供监听思源编辑事件的代码吗

    1 回复
  • 其他回帖
  • 监听编辑事件,符合正则时调用 api 写块属性

    1 回复
  • wilsons 1 1 赞同 1 评论

    监听编辑器输入事件,仅供参考

    (()=>{
        // 编辑器输入事件
        onEditorInput((editor) => {
            // 获取光标所在元素
            const currEl = getCursorElement();
            console.log('当前元素', currEl);
            // 获取当前块
            const currBlock = currEl.closest('[data-type]');
            console.log('当前块', currBlock);
        });
      
        // 编辑器输入事件
        function onEditorInput(callback) {
            whenElementExist(isMobile()?'body':'.layout__center').then(async element => {
                // 等待笔记列表加载完毕
                await sleep(40);
                // 监听编辑器加载事件
                observeDomChange(element, async (mutation) => {
                    if (mutation.target.classList?.contains("protyle-wysiwyg")) {
                        console.log(mutation.target);
                       const editor = mutation.target;
                        if(editor && editor.closest){
                            // 等待编辑器加载完毕
                            const protyle = editor.closest(".protyle");
                            if(protyle.dataset.loading !== 'finished'){
                                await whenElementExist(()=>editor?.closest(".protyle") === 'finished');
                            }
                            if(!editor.getAttribute('custom-listened')){
                                editor.setAttribute('custom-listened', true);
                                //console.log('listen editor');
                                editor.addEventListener('input', ()=>{
                                    //console.log('editor inputed');
                                    callback(editor);
                                })
                            }
                        }
                    }
                });
            });
        }
        // 获取光标所在元素
        function getCursorElement() {
            const selection = window.getSelection();
            if (selection.rangeCount > 0) {
                const range = selection.getRangeAt(0);
                // 获取选择范围的起始位置所在的节点
                const startContainer = range.startContainer;
                // 如果起始位置是文本节点,返回其父元素节点
                const cursorElement = startContainer.nodeType === Node.TEXT_NODE
                    ? startContainer.parentElement
                    : startContainer;
      
                return cursorElement;
            }
            return null;
        }
        // 观察元素被添加
        function observeDomChange(selector, callback) {
            // 定义一个回调函数,当DOM发生变化时调用
            const onChange = function(mutationsList, observer) {
                for (const mutation of mutationsList) {
                    if (mutation.type === 'childList') {
                        callback(mutation);
                    }
                }
            };
            // 创建一个观察器实例,并传入回调函数
            const observer = new MutationObserver(onChange);
            // 配置观察选项:指定需要观察哪些变动
            const config = { attributes: false, childList: true, subtree: true };
            // 获取目标节点
            const targetNode = typeof selector === 'string' ? document.querySelector(selector) : selector;
            // 如果目标节点存在,则开始观察
            if (targetNode) {
                observer.observe(targetNode, config);
            }
            // 返回一个函数,用于停止观察
            return () => {
                observer.disconnect();
            };
        }
        // 是否手机端
        function isMobile() {
            return !!document.getElementById("sidebar");
        }
        // 延迟执行
        function sleep(ms) {
            return new Promise(resolve => setTimeout(resolve, ms));
        }
        // 等待元素渲染完成后执行
        function whenElementExist(selector) {
            return new Promise(resolve => {
                const checkForElement = () => {
                    let element = null;
                    if (typeof selector === 'function') {
                        element = selector();
                    } else {
                        element = document.querySelector(selector);
                    }
                    if (element) {
                        resolve(element);
                    } else {
                        requestAnimationFrame(checkForElement);
                    }
                };
                checkForElement();
            });
        }
    })();
    
    万分感谢!!
    stevehfut

推荐标签 标签

  • 百度

    百度(Nasdaq:BIDU)是全球最大的中文搜索引擎、最大的中文网站。2000 年 1 月由李彦宏创立于北京中关村,致力于向人们提供“简单,可依赖”的信息获取方式。“百度”二字源于中国宋朝词人辛弃疾的《青玉案·元夕》词句“众里寻他千百度”,象征着百度对中文信息检索技术的执著追求。

    63 引用 • 785 回帖 • 177 关注
  • Docker

    Docker 是一个开源的应用容器引擎,让开发者可以打包他们的应用以及依赖包到一个可移植的容器中,然后发布到任何流行的操作系统上。容器完全使用沙箱机制,几乎没有性能开销,可以很容易地在机器和数据中心中运行。

    491 引用 • 916 回帖 • 1 关注
  • Scala

    Scala 是一门多范式的编程语言,集成面向对象编程和函数式编程的各种特性。

    13 引用 • 11 回帖 • 128 关注
  • Solidity

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

    3 引用 • 18 回帖 • 390 关注
  • 分享

    有什么新发现就分享给大家吧!

    248 引用 • 1792 回帖 • 1 关注
  • AngularJS

    AngularJS 诞生于 2009 年,由 Misko Hevery 等人创建,后为 Google 所收购。是一款优秀的前端 JS 框架,已经被用于 Google 的多款产品当中。AngularJS 有着诸多特性,最为核心的是:MVC、模块化、自动化双向数据绑定、语义化标签、依赖注入等。2.0 版本后已经改名为 Angular。

    12 引用 • 50 回帖 • 476 关注
  • uTools

    uTools 是一个极简、插件化、跨平台的现代桌面软件。通过自由选配丰富的插件,打造你得心应手的工具集合。

    6 引用 • 14 回帖
  • 思源笔记

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

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

    22246 引用 • 88919 回帖
  • Kafka

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

    36 引用 • 35 回帖 • 4 关注
  • NGINX

    NGINX 是一个高性能的 HTTP 和反向代理服务器,也是一个 IMAP/POP3/SMTP 代理服务器。 NGINX 是由 Igor Sysoev 为俄罗斯访问量第二的 Rambler.ru 站点开发的,第一个公开版本 0.1.0 发布于 2004 年 10 月 4 日。

    311 引用 • 546 回帖
  • InfluxDB

    InfluxDB 是一个开源的没有外部依赖的时间序列数据库。适用于记录度量,事件及实时分析。

    2 引用 • 68 关注
  • JetBrains

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

    18 引用 • 54 回帖 • 4 关注
  • Netty

    Netty 是一个基于 NIO 的客户端-服务器编程框架,使用 Netty 可以让你快速、简单地开发出一个可维护、高性能的网络应用,例如实现了某种协议的客户、服务端应用。

    49 引用 • 33 回帖 • 21 关注
  • Sublime

    Sublime Text 是一款可以用来写代码、写文章的文本编辑器。支持代码高亮、自动完成,还支持通过插件进行扩展。

    10 引用 • 5 回帖 • 1 关注
  • TensorFlow

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

    20 引用 • 19 回帖
  • 服务器

    服务器,也称伺服器,是提供计算服务的设备。由于服务器需要响应服务请求,并进行处理,因此一般来说服务器应具备承担服务并且保障服务的能力。

    125 引用 • 588 回帖
  • API

    应用程序编程接口(Application Programming Interface)是一些预先定义的函数,目的是提供应用程序与开发人员基于某软件或硬件得以访问一组例程的能力,而又无需访问源码,或理解内部工作机制的细节。

    77 引用 • 430 回帖 • 2 关注
  • Spark

    Spark 是 UC Berkeley AMP lab 所开源的类 Hadoop MapReduce 的通用并行框架。Spark 拥有 Hadoop MapReduce 所具有的优点;但不同于 MapReduce 的是 Job 中间输出结果可以保存在内存中,从而不再需要读写 HDFS,因此 Spark 能更好地适用于数据挖掘与机器学习等需要迭代的 MapReduce 的算法。

    74 引用 • 46 回帖 • 556 关注
  • DNSPod

    DNSPod 建立于 2006 年 3 月份,是一款免费智能 DNS 产品。 DNSPod 可以为同时有电信、网通、教育网服务器的网站提供智能的解析,让电信用户访问电信的服务器,网通的用户访问网通的服务器,教育网的用户访问教育网的服务器,达到互联互通的效果。

    6 引用 • 26 回帖 • 511 关注
  • abitmean

    有点意思就行了

    31 关注
  • 持续集成

    持续集成(Continuous Integration)是一种软件开发实践,即团队开发成员经常集成他们的工作,通过每个成员每天至少集成一次,也就意味着每天可能会发生多次集成。每次集成都通过自动化的构建(包括编译,发布,自动化测试)来验证,从而尽早地发现集成错误。

    15 引用 • 7 回帖
  • wolai

    我来 wolai:不仅仅是未来的云端笔记!

    2 引用 • 14 回帖
  • CSS

    CSS(Cascading Style Sheet)“层叠样式表”是用于控制网页样式并允许将样式信息与网页内容分离的一种标记性语言。

    197 引用 • 549 回帖
  • MyBatis

    MyBatis 本是 Apache 软件基金会 的一个开源项目 iBatis,2010 年这个项目由 Apache 软件基金会迁移到了 google code,并且改名为 MyBatis ,2013 年 11 月再次迁移到了 GitHub。

    170 引用 • 414 回帖 • 387 关注
  • flomo

    flomo 是新一代 「卡片笔记」 ,专注在碎片化时代,促进你的记录,帮你积累更多知识资产。

    5 引用 • 107 回帖
  • Flutter

    Flutter 是谷歌的移动 UI 框架,可以快速在 iOS 和 Android 上构建高质量的原生用户界面。 Flutter 可以与现有的代码一起工作,它正在被越来越多的开发者和组织使用,并且 Flutter 是完全免费、开源的。

    39 引用 • 92 回帖 • 4 关注
  • 外包

    有空闲时间是接外包好呢还是学习好呢?

    26 引用 • 232 回帖 • 1 关注