JS

Infinite Scroll

choi95 2021. 7. 1. 14:23

Question

1. μ΅œμ΄ˆμ—λŠ” 20개의 λͺ©λ‘μ„ λΆˆλŸ¬μ˜¨λ‹€.

2. μŠ€ν¬λ‘€μ„ μ΅œν•˜λ‹¨μœΌλ‘œ μ΄λ™μ‹œ 'loading' μƒνƒœ ν‘œμ‹œκ°€ λ‚˜νƒ€λ‚˜λ©°, μ΄ν›„μ˜ 20개 λͺ©λ‘μ„ 더 κ°€μ Έμ˜¨λ‹€.

3. λ‘œλ”© μ™„λ£Œμ‹œ 'loading'ν‘œμ‹œκ°€ 사라지며, κ°€μ Έμ˜¨ λͺ©λ‘μ΄ ν•˜λ‹¨μ— μΆ”κ°€λœλ‹€. (λ¬΄ν•œ 반볡)

 

Solution

const loadMore = async () => {
  const target = page ? fetchMoreTrigger : app;
  target.classList.add("loading");
  await renderList(page++);
  target.classList.remove("loading");
};

const onScroll = async e => {
  const {scrollTop, scrollHeight, clientHeight} = e.target.scrollingElement;
  if(scrollHeight - scrollTop === clientHeight) {
    const target = page ? fetchMoreTrigger : app;
    target.classList.add("loading");
    await renderList(page++);
    target.classList.remove("loading");
  }
};

 

Issue

1. 슀크둀 이벀트λ₯Ό ν•˜λ©΄ 이벀트 νƒ€κ²Ÿμ— scrollingElement ν”„λ‘œνΌν‹°κ°€ μžˆλŠ”λ° 이것을 톡해 ν˜„μž¬ 슀크둀 μƒνƒœμ™€ κ΄€λ ¨λœ    정보λ₯Ό 얻을 수 μžˆλ‹€.    ν•΄λ‹Ή scrollingElement 내에 λ‹€μŒκ³Ό 같은 3κ°€μ§€ ν”„λ‘œνΌν‹°λ“€μ„ λ””μŠ€νŠΈλŸ­μ³λ§ ν• λ‹Ήν•œλ‹€.

  • clientHeight: μ›Ή λΈŒλΌμš°μ € μ°½(λ‚΄μš©μ΄ λ³΄μ—¬μ§€λŠ” μ˜μ—­)의 높이
  • scrollTop: ν˜„μž¬ 슀크둀된 λΆ€λΆ„μ˜ 맨 μœ„μ˜ 높이(=ν˜„μž¬ 슀크둀의 μœ„μΉ˜)
  • scrollHeight: λ¬Έμ„œμ˜ 총 높이(=슀크둀 λŒ€μƒμ˜ 총 높이)

2. '(전체 슀크둀 μ˜μ—­) - (ν˜„μž¬ 슀크둀의 μœ„μΉ˜)'의 값이 (ν˜„μž¬ 슀크둀 된 μƒνƒœμ—μ„œμ˜ λ³΄μ—¬μ§€λŠ” μ˜μ—­)κ³Ό κ°™λ‹€λ©΄ 더 이상 μŠ€ν¬λ‘€μ„

    ν•  곡간이 μ—†λ‹€λŠ” 의미이며 이 식을 쑰건문 내에 μ‚¬μš©ν•œλ‹€.

 

3. 초기 μƒνƒœμ™€ 이후 μ—…λ°μ΄νŠΈ 될 λ•Œμ˜ νŽ˜μ΄μ§€λŠ” λ³„λ„λ‘œ ꡬ성해야 ν•˜κΈ° λ•Œλ¬Έμ— μ‚Όν•­μ—°μ‚°μžλ₯Ό 톡해 쑰건에 맞게 taget λ³€μˆ˜λ₯Ό 

    각기 λ‹€λ₯΄κ²Œ ν• λ‹Ήν•΄ μ€€λ‹€. (초기 page λ³€μˆ˜ 값은 0이기 λ•Œλ¬Έμ— false)

 

Refactoring

const loadMore = async () => {
  const target = page ? fetchMoreTrigger : app;
  target.classList.add("loading");
  await renderList(page++);
  target.classList.remove("loading");
};

const onScroll = e => {
  const {scrollTop, scrollHeight, clientHeight} = e.target.scrollingElement;
  if(scrollHeight - scrollTop === clientHeight) {
    loadMore();
  }
};