为了账号安全,请及时绑定邮箱和手机立即绑定

语法荧光笔无法更新文本

语法荧光笔无法更新文本

临摹微笑 2023-08-24 10:26:59
我正在尝试使用 HTML 制作一个代码编辑器:<!DOCTYPE html><html><head>    <meta charset='UTF-8'>    <meta http-equiv='X-UA-Compatible' content='IE=Edge'>    <meta name='viewport' content='width=device-width, initial-scale=1'>    <link rel='stylesheet' href='style.css'></head><body>    <pre id='editor'><code contenteditable='true'></code></pre>        <script type='module'>        import { highlight } from './highlighter.js';        import { Caret } from './caret.js';        (() =>        {            const editor = document.querySelector('#editor code');            const caret = new Caret(editor);            highlight(editor);            editor.addEventListener('input', e =>            {                highlight(editor);                e.preventDefault();            });            editor.addEventListener('keydown', e =>            {                const TAB   = 9;                const ENTER = 13;                switch (e.keyCode)                {                    // ...                }            });        })();    </script></body></html>荧光笔.js:import { Caret } from './caret.js';export function highlight(editor){    // ...    const NORM = '#E6E6FA';    // ...    const Highlighter = {        source: editor.innerText,        start: 0,        curr: 0,        // ...        fin()        {            return this.curr >= this.source.length;        },        advance()        {            return this.source[this.curr++];        },        // ...        scan()        {            let result = '';            this.start = this.curr;            if (this.fin())            {                return null;            }基本上,它获取用户代码的文本内容,扫描它以生成带有颜色数据的词素,将这些词素拆分为字符,并将其放入带有颜色的 <span> 标签中,然后将这些 <span> 附加到字符串中编辑器的innerHTML更新为,最后用户的光标放回到正确的位置;这是根据输入完成的。但有一个问题:如果用户输入速度太快,他们输入的文本可能会加倍。我尝试使用其他类型的事件侦听器来解决此问题,并尝试简单地使用 setInterval,但效果并不好。
查看完整描述

1 回答

?
守着一只汪

TA贡献1872条经验 获得超3个赞

从你所描述的情况来看


如果用户输入太快


并看到在元素highlight()的每次更改时都会调用计算量大的函数input


editor.addEventListener('input', e => {

  highlight(editor); // <--

  e.preventDefault();

});

我建议取消该调用以突出显示。


尝试这样的事情:

// Vanilla debounce: https://gist.github.com/peduarte/7ee475dd0fae1940f857582ecbb9dc5f


function debounce(func, wait = 100) {

  let timeout;

  return function(...args) {

    clearTimeout(timeout);

    timeout = setTimeout(() => {

      func.apply(this, args);

    }, wait);

  };

}


// ...


// adjust delay to find a balance between responsiveness and performance

const delay = 500; 


const runHighlight = () => highlight(editor);

const debouncedHighlight = debounce(runHighlight, delay);


editor.addEventListener('input', e => {

  e.preventDefault();

  debouncedHighlight();

});


查看完整回答
反对 回复 2023-08-24
  • 1 回答
  • 0 关注
  • 123 浏览
慕课专栏
更多

添加回答

举报

0/150
提交
取消
意见反馈 帮助中心 APP下载
官方微信