滾動事件偵聽器加入元素,但只有當scrollTop不等於0時才能正確移動
P粉427877676
P粉427877676 2024-04-01 11:03:26
0
1
615

所以我編寫了這個小腳本,其中有兩個列表 - 已完成/活動任務,您可以透過點擊按鈕切換任務列表,也可以透過點擊「更多資訊」閱讀更多關於任務的資訊。當點擊更多資訊時,創建了一個新的 div 元素,我想跟隨它的主機元素 Y 位置,並且它可以工作一半。 這就是它的樣子:在此輸入圖像描述

這是一個錯誤,當可滾動元素scrollTop 不為0 時,我很確定會發生這個錯誤(它是以正確的方式創建的,每當我開始滾動時,它都會立即向上跳並覆蓋任務本身):輸入圖像描述在這裡。

這是我的程式碼的一部分,負責識別滾動的px 量、滾動方向和移動「更多資訊」div 元素,以及負責創建它的部分,我不知道在哪裡這是問題所在,因為我對整體編碼還很陌生,而且我對css/html 也不太熟悉。

createTooltip() {
    const tooltipElement = document.createElement('div');
    tooltipElement.className = 'card';
    const toolTipTemplate = document.getElementById('tooltip');
    const tooltipBody = document.importNode(toolTipTemplate.content, true);
    tooltipBody.querySelector('p').textContent = this.text;
    tooltipElement.append(tooltipBody);

    const hostElPosLeft = this.hostElement.offsetLeft;
    const hostElPostop = this.hostElement.offsetTop;
    const hostElHeight = this.hostElement.clientHeight;
    const parentElementScrolling = this.hostElement.parentElement.scrollTop;

    const x = hostElPosLeft + 20;
    const y = hostElPostop + hostElHeight - parentElementScrolling - 10;
    tooltipElement.style.position = 'absolute';
    tooltipElement.style.left = x + 'px';
    tooltipElement.style.top = y + 'px';

    const scrollHandler = () => {
      ulElement.addEventListener('scroll', yLogger);
    };
    tooltipElement.addEventListener('click', this.closeToolTip);
    tooltipElement.addEventListener('click', scrollHandler);
    this.element = tooltipElement;
    const ulElement = this.hostElement.parentElement;
    console.log(ulElement);

    let pxPosition = [0];
    let currentY = y;

    const yLogger = () => {
      let scrollDirection;
      let pxScrolled = 0;
      if (pxPosition.length <= 1) {
        pxPosition.push(ulElement.scrollTop);
      } else {
        pxPosition.push(ulElement.scrollTop);
        pxPosition.shift(ulElement);
      }
      console.log(pxPosition);
      if (pxPosition[1] < pxPosition[0]) {
        scrollDirection = 'up';
        pxScrolled = pxPosition[0] - pxPosition[1];
      } else if (pxPosition[0] < pxPosition[1]) {
        scrollDirection = 'down';
        pxScrolled = pxPosition[1] - pxPosition[0];
      }
      console.log(pxScrolled);
      console.log(scrollDirection);

      if (scrollDirection === 'down') {
        currentY = currentY - pxScrolled;
        console.log(currentY);
        tooltipElement.style.top = currentY + 'px';
      } else {
        scrollDirection === 'up';
        currentY = currentY + pxScrolled;
        console.log(currentY);
        tooltipElement.style.top = currentY + 'px';
      }
    };

    this.hostElement.closest('ul').addEventListener('scroll', yLogger);
  }
}

我正在添加 HTML 和 CSS 片段,儘管我認為它們不是必需的,因為它是由我參加的課程講師編寫的。

這是 HTML 片段:

<!DOCTYPE html>
<html lang="en">
  <head>
    <meta charset="UTF-8" />
    <meta name="viewport" content="width=device-width, initial-scale=1.0" />
    <meta http-equiv="X-UA-Compatible" content="ie=edge" />
    <title>Project Board</title>
    <link rel="stylesheet" href="assets/styles/app.css" />
    <script src="assets/scripts/app.js" defer></script>
  </head>
  <body>
    <template id="tooltip">
      <h2>More Info</h2>
      <p></p>
    </template>
    <header id="main-header">
      <h1>Project Planner</h1>
    </header>
    <section id="active-projects">
      <header>
        <h2>Active Projects</h2>
      </header>
      <ul>
        <li
          id="p1"
          data-extra-info="Got lifetime access, but would be nice to finish it soon!"
          class="card"
          draggable="true"
        >
          <h2>Finish the Course</h2>
          <p>Finish the course within the next two weeks.</p>
          <button class="alt">More Info</button>
          <button>Finish</button>
        </li>
        <li
          id="p2"
          data-extra-info="Not really a business topic but still important."
          class="card"
          draggable="true"
        >
          <h2>Buy Groceries</h2>
          <p>Don't forget to pick up groceries today.</p>
          <button class="alt">More Info</button>
          <button>Finish</button>
        </li>
      </ul>
    </section>
    <section id="finished-projects">
      <header>
        <h2>Finished Projects</h2>
      </header>
      <ul>
        <li
          id="p3"
          data-extra-info="Super important conference! Fictional but still!"
          class="card"
          draggable="true"
        >
          <h2>Book Hotel</h2>
          <p>
            Academind conference takes place in December, don't forget to book a
            hotel.
          </p>
          <button class="alt">More Info</button>
          <button>Activate</button>
        </li>
      </ul>
    </section>
    <footer>
      <button id="im-done-btn">I'm Done!</button>
    </footer>
  </body>
</html>

這是相關的 CSS 片段:

* {
  box-sizing: border-box;
}

html {
  font-family: sans-serif;
}

body {
  margin: 0;
}

#main-header {
  width: 100%;
  height: 6rem;
  display: flex;
  justify-content: center;
  align-items: center;
  background: #ff0062;
}

#main-header h1 {
  color: white;
  margin: 0;
}

footer {
  position: absolute;
  bottom: 0;
  left: 0;
  width: 100%;
  text-align: center;
}

ul {
  list-style: none;
  margin: 0;
  padding: 0;
}

li {
  margin: 1rem 0;
}

section {
  margin: 1rem auto;
  width: 40rem;
  max-width: 90%;
}

section ul {
  padding: 1rem;
  max-height: 20rem;
  overflow: scroll;
}

section > h2 {
  color: white;
  margin: 0;
}

button {
  font: inherit;
  background: #ff0062;
  color: white;
  border: 1px solid #ff0062;
  padding: 0.5rem 1.5rem;
  cursor: pointer;
}

button.alt {
  background: white;
  color: #ff0062;
}

button:focus {
  outline: none;
}

button:hover,
button:active {
  background: #ff2579;
  border-color: #ff2579;
  color: white;
}

.card {
  border-radius: 10px;
  box-shadow: 0 2px 8px rgba(0, 0, 0, 0.26);
  padding: 1rem;
  background: white;
}

.droppable {
  background: #ffe0ec
}

#active-projects {
  border: 1px solid #870099;
}

#active-projects > header {
  background: #870099;
  padding: 1rem;
  display: flex;
  justify-content: space-between;
  align-items: center;
}

#active-projects header h2 {
  color: white;
  margin: 0;
}

#finished-projects {
  border: 1px solid #535353;
}

#finished-projects > header {
  background: #535353;
  padding: 1rem;
  display: flex;
  justify-content: space-between;
  align-items: center;
}

#finished-projects header h2 {
  color: white;
  margin: 0;
}

P粉427877676
P粉427877676

全部回覆(1)
P粉885035114

該問題可以透過 CSS 解決,您可以從 Javascript 程式碼中刪除以下內容:

tooltipElement.style.position = 'absolute';
tooltipElement.style.left = x + 'px';
tooltipElement.style.top = y + 'px';

取而代之的是,透過添加以下內容來更改 CSS:

li.card {
    position: relative;
}
div.card {
    position: absolute;
    top: 0; /* or some other value, experiment until you find the one which works for you */
    left: 0; /* same as above */
    z-index: 1;
}

為此,您在 Javascript 程式碼中建立的 div.card 元素必須是對應 li.card 元素的子元素。我還(可能是錯誤的)假設您的原始程式碼類似於我之前找到的程式碼,並在您的問題的評論中發布,因為我無法運行您的原始程式碼。

您的 position:absolute 最初不起作用,因為 li.card 父級的位置未明確設置,預設為 static

編輯忘記提及 z-index 位元。這是必需的,因為您的資訊框不會完全可見(它將位於下一個 li.card 元素下)。

熱門教學
更多>
最新下載
更多>
網站特效
網站源碼
網站素材
前端模板