Vanessa219 / vditor

♏ 一款浏览器端的 Markdown 编辑器,支持所见即所得(富文本)、即时渲染(类似 Typora)和分屏预览模式。An In-browser Markdown editor, support WYSIWYG (Rich Text), Instant Rendering (Typora-like) and Split View modes.
https://b3log.org/vditor
MIT License
8.35k stars 857 forks source link

升级到新版本之后,使用Vditor.preview(),Vditor.outlineRender()API生成大纲点击无法跳转 #1605

Closed crushjjl closed 6 months ago

crushjjl commented 6 months ago

编辑模式

描述问题

采用官网的demo示例:
  const initOutline = () => {
    const headingElements = []
    Array.from(document.getElementById('preview').children).forEach((item) => {
      if (item.tagName.length === 2 && item.tagName !== 'HR' && item.tagName.indexOf('H') === 0) {
        headingElements.push(item)
      }
    })

    let toc = []
    window.addEventListener('scroll', () => {
      const scrollTop = window.scrollY
      toc = []
      headingElements.forEach((item) => {
        toc.push({
          id: item.id,
          offsetTop: item.offsetTop,
        })
      })

      const currentElement = document.querySelector('.vditor-outline__item--current')
      for (let i = 0, iMax = toc.length; i < iMax; i++) {
        if (scrollTop < toc[i].offsetTop - 30) {
          if (currentElement) {
            currentElement.classList.remove('vditor-outline__item--current')
          }
          let index = i > 0 ? i - 1 : 0
          document.querySelector('span[data-target-id="' + toc[index].id + '"]').classList.add('vditor-outline__item--current')
          break
        }
      }
    })
  }
  fetch('markdown/zh_CN.md').
  then(response => response.text()).
  then(markdown => {
    Vditor.preview(document.getElementById('preview'),
      markdown, {
        speech: {
          enable: true,
        },
        anchor: 1,
        after () {
          if (window.innerWidth <= 768) {
            return
          }
          const outlineElement = document.getElementById('outline')
          Vditor.outlineRender(document.getElementById('preview'), outlineElement)
          if (outlineElement.innerText.trim() !== '') {
            outlineElement.style.display = 'block'
            initOutline()
          }
        },
      })
  })

期待的结果

生成的大纲点击能够正常跳转响应。

截屏或录像

image

版本信息

### vue 3.3.4 + vite 4.4.9,本地demo代码如下: const getProObjContentInfo = async (id) => { loading.value = true; try { const res = await getProObjContentData(id); // console.log(11111111, res); if (res?.data?.code === 200) { const _data = res?.data?.data; // content.value = _data?.content; Vditor?.preview(htmlBodyRef?.value, _data?.content, { speech: { enable: true, }, anchor: 1, after() { if (window.innerWidth <= 768) { return; } Vditor.outlineRender(htmlBodyRef?.value, htmlNavRef?.value); if (htmlNavRef.value.innerText.trim() !== '') { htmlNavRef.value.style.display = 'block'; initOutline(); } }, }); } } catch (error) { console.error(error); } finally { loading.value = false; } };

watch( () => route?.params?.objectId, () => { getProObjContentInfo(route?.params?.objectId); }, { immediate: true, } );

const initOutline = () => { const headingElements = []; Array.from(htmlBodyRef?.value?.children).forEach((item) => { if (item.tagName.length === 2 && item.tagName !== 'HR' && item.tagName.indexOf('H') === 0) { headingElements.push(item); } });

let toc = [];
window.addEventListener('scroll', () => {
  const scrollTop = window.scrollY;
  toc = [];
  headingElements.forEach((item) => {
    toc.push({
      id: item.id,
      offsetTop: item.offsetTop,
    });
  });

  const currentElement = document.querySelector('.vditor-outline__item--current');
  for (let i = 0, iMax = toc.length; i < iMax; i++) {
    if (scrollTop < toc[i].offsetTop - 30) {
      if (currentElement) {
        currentElement.classList.remove('vditor-outline__item--current');
      }
      let index = i > 0 ? i - 1 : 0;
      document.querySelector('span[data-target-id="' + toc[index].id + '"]').classList.add('vditor-outline__item--current');
      break;
    }
  }
});

};

Vanessa219 commented 6 months ago

Demo 上的最新代码是可以的

https://github.com/Vanessa219/vditor/assets/970828/a7f8e1ec-2f26-41dc-bf83-1cc3ff394eb0

crushjjl commented 6 months ago

Demo 上的最新代码是可以的

QQ20240409-175225-HD.mp4

能贴一下这个demo的源码吗?

crushjjl commented 6 months ago

Demo 上的最新代码是可以的 QQ20240409-175225-HD.mp4

能贴一下这个demo的源码吗?

html代码 我复制下来 没有效果。。。

Vanessa219 commented 6 months ago

代码参见 https://github.com/Vanessa219/vditor/tree/master/demo