React-window: ์ ์‹œ ์ธก์ • ์ฝ˜ํ…์ธ  ์ง€์›

์— ๋งŒ๋“  2018๋…„ 05์›” 30์ผ  ยท  132์ฝ”๋ฉ˜ํŠธ  ยท  ์ถœ์ฒ˜: bvaughn/react-window

๊ธฐ์กด ๋ชฉ๋ก ๋ฐ ๊ทธ๋ฆฌ๋“œ ๊ตฌ์„ฑ ์š”์†Œ์— ๋น„์šฉ์„ ์ถ”๊ฐ€ํ•˜์ง€ ์•Š์œผ๋ ค๋ฉด ์ƒˆ ๋ณ€ํ˜•์„ ๋งŒ๋“ญ๋‹ˆ๋‹ค (์˜ˆ : DynamicSizeList ๋ฐ DynamicSizeGrid ). ์ด ๋ณ€ํ˜•์€ ์ปค๋ฐ‹ ๋‹จ๊ณ„ ๋™์•ˆ ์ฝ˜ํ…์ธ ๋ฅผ ์ž๋™์œผ๋กœ ์ธก์ •ํ•ด์•ผํ•ฉ๋‹ˆ๋‹ค.

MVP

์ดˆ๊ธฐ ๊ตฌํ˜„์€ CellMeasurer ๊ฐ€ ๋ฐ˜์‘ ๊ฐ€์ƒํ™”์—์„œ ์ž‘๋™ํ•˜๋Š” ๋ฐฉ์‹๊ณผ ์œ ์‚ฌํ•˜๊ฒŒ ์ž‘๋™ ํ•  ์ˆ˜ ์žˆ์Šต๋‹ˆ๋‹ค.

  1. ์ฝ˜ํ…์ธ ๋Š” ํ˜„์žฌ ์ธก์ • ๊ฐ’์ด์—†๋Š” ๊ฒฝ์šฐ์—๋งŒ ์ธก์ •๋ฉ๋‹ˆ๋‹ค.
  2. ๋ฌด์–ธ๊ฐ€ ๋ณ€๊ฒฝ๋˜๋ฉด ์ธก์ • ๊ฐ’์„ ์™ธ๋ถ€์—์„œ (ํ•„์ˆ˜์ ์œผ๋กœ) ์žฌ์„ค์ •ํ•ด์•ผํ•ฉ๋‹ˆ๋‹ค.
  3. ์ง€์ •๋œ ์ธ๋ฑ์Šค์˜ ์…€์€ ํ•ด๋‹น ์ธ๋ฑ์Šค๊ฐ€ ์ธก์ •๋˜๊ธฐ ์ „์˜ ๋ชจ๋“  ์…€ ๋’ค์— ์œ„์น˜ ํ•  ์ˆ˜ ์žˆ์Šต๋‹ˆ๋‹ค.

๊ณจ

์œ„์˜ ์„ธ ๋ฒˆ์งธ ์ œ์•ฝ ์กฐ๊ฑด์„ ์ œ๊ฑฐํ•˜์—ฌ ์ด์ „ ํ•ญ๋ชฉ์„ ์ธก์ •ํ•˜์ง€ ์•Š๊ณ  ์ž„์˜ ์•ก์„ธ์Šค (ํ•ญ๋ชฉ ์ธ๋ฑ์Šค ๋˜๋Š” ์Šคํฌ๋กค ์˜คํ”„์…‹)๋ฅผ ํ—ˆ์šฉํ•˜๋ฉด์ด ๊ตฌ์„ฑ ์š”์†Œ๊ฐ€ ๋” ์ž˜ ์ˆ˜ํ–‰ ๋  ์ˆ˜ ์žˆ์Šต๋‹ˆ๋‹ค. ์ด๊ฒƒ์€ ์ฑ„ํŒ… ์‘์šฉ ํ”„๋กœ๊ทธ๋žจ๊ณผ ๊ฐ™์€ ์‚ฌ์šฉ ์‚ฌ๋ก€์—์„œ ๋ฐ˜์‘ ์ฐฝ์„ ํ›จ์”ฌ ๋” ์„ฑ๋Šฅ์žˆ๊ฒŒ ๋งŒ๋“ญ๋‹ˆ๋‹ค.

๋˜ํ•œ ResizeObserver ๋ฅผ ์‚ฌ์šฉํ•˜์—ฌ ( react-measure ๋ฅผ ํ†ตํ•ด) ํ•ญ๋ชฉ ํฌ๊ธฐ๋ฅผ ์ž๋™์œผ๋กœ ๊ฐ์ง€ํ•˜๊ณ  ์œ„์น˜ ๋ฐ ์ธก์ • ์บ์‹œ๋ฅผ ์™„์ „ํžˆ ์ œ๊ฑฐํ•˜๋Š” ๊ธฐ๋Šฅ์„ ์ž ๊ธˆ ํ•ด์ œํ•ฉ๋‹ˆ๋‹ค. ์ด๋ ‡๊ฒŒํ•˜๋ฉด ์บ์‹œ ๋œ ์ธก์ •์„ ๊ฐ•์ œ๋กœ ์žฌ์„ค์ • ํ•  ํ•„์š”๊ฐ€ ์—†์–ด์ง€๊ณ  API๊ฐ€ ํฌ๊ฒŒ ํ–ฅ์ƒ๋ฉ๋‹ˆ๋‹ค.

์œ„์˜ ์ž‘์—…์ด ๊ฐ€๋Šฅํ•˜๋ ค๋ฉด ๋™์  ๋ชฉ๋ก / ๊ทธ๋ฆฌ๋“œ ๊ตฌ์„ฑ ์š”์†Œ๊ฐ€ ์˜คํ”„์…‹์„ ์ธ๋ฑ์Šค์— ๋งคํ•‘ํ•˜๋Š” ๋ฐ ๊ทน์ ์œผ๋กœ ๋‹ค๋ฅธ ์ ‘๊ทผ ๋ฐฉ์‹์„ ์‚ฌ์šฉํ•ด์•ผํ•˜๋ฉฐ ๊ทธ ๋ฐ˜๋Œ€์˜ ๊ฒฝ์šฐ๋„ ๋งˆ์ฐฌ๊ฐ€์ง€์ž…๋‹ˆ๋‹ค. ( react-virtualized์˜ "scroll anchoring"์— ๋Œ€ํ•œ์ด ์ฃผ์„ ์—๋Š” ๋ฉ‹์ง„ ๋น„์ฃผ์–ผ์ด ์žˆ์Šต๋‹ˆ๋‹ค.) ๊ธฐ๋ณธ์ ์œผ๋กœ ๋‹ค์Œ๊ณผ ๊ฐ™์€ ์ž‘์—…์„ ์ˆ˜ํ–‰ํ•ด์•ผํ•ฉ๋‹ˆ๋‹ค.

  • estimatedItemSize ์†Œํ’ˆ์„ ๊ณฑํ•œ ํ•ญ๋ชฉ ์ˆ˜๋ฅผ ๊ธฐ์ค€์œผ๋กœ ์ด ํฌ๊ธฐ๋ฅผ ์ถ”์ •ํ•ฉ๋‹ˆ๋‹ค. (์•„๋ž˜์— ์„ค๋ช… ๋œ ๋งคํ•‘์ด ๋ชจํ˜ธํ•˜์ง€ ์•Š๊ธฐ ๋•Œ๋ฌธ์—์ด ์˜ˆ์ƒ ํฌ๊ธฐ๋Š” ์กฐ์ •ํ•  ํ•„์š”๊ฐ€ ์—†์Šต๋‹ˆ๋‹ค.)

  • ์Šคํฌ๋กค ์œ„์น˜๊ฐ€ ๋ณ€๊ฒฝ๋˜๋ฉด ์ƒˆ ์˜คํ”„์…‹์„ ์ด์ „ ์˜คํ”„์…‹๊ณผ ๋น„๊ตํ•ฉ๋‹ˆ๋‹ค. ๋ธํƒ€๊ฐ€ [๊ฒฐ์ • ์˜ˆ์ •] ์ž„๊ณ„ ๊ฐ’๋ณด๋‹ค ํฌ๋ฉด ์ƒˆ ์˜คํ”„์…‹์„ "์Šคํฌ๋กค ์•ต์ปค"๋กœ ์„ค์ •ํ•ฉ๋‹ˆ๋‹ค. ์˜คํ”„์…‹์„ ์˜ˆ์ƒ ์ธ๋ฑ์Šค์— ๋งคํ•‘ํ•ฉ๋‹ˆ๋‹ค (์˜ˆ : ์˜คํ”„์…‹์„ ์ด ์˜ˆ์ƒ ์Šคํฌ๋กค ๊ฐ€๋Šฅ ํฌ๊ธฐ๋กœ ๋‚˜๋ˆ„๊ณ  ์ปฌ๋ ‰์…˜์˜ ํ•ญ๋ชฉ ์ˆ˜๋กœ ๊ณฑํ•ฉ๋‹ˆ๋‹ค). ์ด ๋งคํ•‘ ๋œ ์ธ๋ฑ์Šค๋ฅผ "์•ต์ปค ์ธ๋ฑ์Šค"๋กœ ์ €์žฅํ•ฉ๋‹ˆ๋‹ค. ์˜ˆ๋ฅผ ๋“ค์–ด, ์•„๋ž˜ ์ด๋ฏธ์ง€์— ์„ค๋ช… ๋œ ๋ชฉ๋ก์— 250 ๊ฐœ์˜ ํ•ญ๋ชฉ์ด์žˆ๋Š” ๊ฒฝ์šฐ "์•ต์ปค ์ธ๋ฑ์Šค"๋Š” 132๊ฐ€๋ฉ๋‹ˆ๋‹ค.

screen shot 2018-06-10 at 11 58 38 am

  • ์Šคํฌ๋กค ์œ„์น˜๊ฐ€ ๋ณ€๊ฒฝ ๋  ๋•Œ ๋ธํƒ€๊ฐ€ ์ž„๊ณ„ ๊ฐ’ ๋ฏธ๋งŒ์ด๋ฉด ์•ต์ปค ์ธ๋ฑ์Šค์™€ ๊ด€๋ จํ•˜์—ฌ ๋ Œ๋”๋ง ํ•  ์ƒˆ ํ•ญ๋ชฉ์„ ์„ ํƒํ•ฉ๋‹ˆ๋‹ค. ์ด์ „์— ๋ฐฐ์น˜ ๋œ ํ•ญ๋ชฉ์„ ๊ธฐ์ค€์œผ๋กœ ์ด๋Ÿฌํ•œ ํ•ญ๋ชฉ์„ ๋ฐฐ์น˜ํ•ฉ๋‹ˆ๋‹ค. ์œ„์˜ ์˜ˆ๋ฅผ ๊ณ„์† ์ง„ํ–‰ํ•˜๋ฉด ๋ชฉ๋ก์ด ์•ฝ๊ฐ„ (200px) ์Šคํฌ๋กค ๋œ ๊ฒฝ์šฐ ์ด์ „์— ๋ฐฐ์น˜ ๋œ ํ•ญ๋ชฉ ์•„๋ž˜์— 200px์— ํ•ด๋‹นํ•˜๋Š” ์ถ”๊ฐ€ ํ–‰์„ ์ถ”๊ฐ€ํ•ด์•ผํ•ฉ๋‹ˆ๋‹ค.

screen shot 2018-06-10 at 12 01 01 pm

์œ„์˜ ์ ‘๊ทผ ๋ฐฉ์‹์—๋Š” ๋‹จ ํ•˜๋‚˜์˜ ์ฃผ์š” ๋‹จ์ ์ด ์žˆ์Šต๋‹ˆ๋‹ค. ๋ชฉ๋ก ๊ฒฝ๊ณ„์—์„œ ํ•ญ๋ชฉ์„ ์˜ฌ๋ฐ”๋ฅด๊ฒŒ ์ •๋ ฌํ•˜๋Š” ๊ฒƒ์ž…๋‹ˆ๋‹ค. ํ•ญ๋ชฉ ์ธ๋ฑ์Šค๊ฐ€ ์ถ”์ •๋˜๋Š” ๊ฒฝ์šฐ (์œ„์—์„œ ์„ค๋ช…ํ•œ๋Œ€๋กœ) ์Šคํฌ๋กค ๊ฐ€๋Šฅ ์˜์—ญ์˜ ์‹œ์ž‘ ๋˜๋Š” ๋๊ณผ ์ •ํ™•ํžˆ ์ผ์น˜ํ•˜์ง€ ์•Š์„ ๊ฐ€๋Šฅ์„ฑ์ด ๋†’์Šต๋‹ˆ๋‹ค.

  • ๋ ๋ถ€๋ถ„์€ ์‚ฌ์šฉ์ž๊ฐ€ ๋ ๋ถ€๋ถ„์— ๊ฐ€๊นŒ์›Œ ์งˆ ๋•Œ ์ด ์˜ˆ์ƒ ํฌ๊ธฐ๋ฅผ ์กฐ์ •ํ•˜์—ฌ ์„ค๋ช… ํ•  ์ˆ˜ ์žˆ์Šต๋‹ˆ๋‹ค (์ด๋กœ ์ธํ•ด ์Šคํฌ๋กค์ด ๋ฒ„๋ฒ… ๊ฑฐ๋ฆด ์ˆ˜ ์žˆ์Œ).
  • ์ฒซ ๋ฒˆ์งธ ํ•ญ๋ชฉ์€ ์˜คํ”„์…‹ 0๊ณผ ์ •๋ ฌํ•ด์•ผํ•˜๋Š” ๋™์‹œ์— 0๋ณด๋‹ค ํฐ ์˜คํ”„์…‹์˜ ํ•ญ๋ชฉ๊ณผ ์—ฐ์†์ ์œผ๋กœ ์—ฐ๊ฒฐ๋˜๋Š” ๊ฒƒ์ฒ˜๋Ÿผ ๋ณด์ด๊ธฐ ๋•Œ๋ฌธ์— ๋ชฉ๋ก์˜ ์‹œ์ž‘ ๋ถ€๋ถ„์„ ์ฒ˜๋ฆฌํ•˜๊ธฐ๊ฐ€ ๋” ์–ด๋ ต์Šต๋‹ˆ๋‹ค. ์•„๋งˆ๋„ ๋ชฉ๋ก ์‹œ์ž‘ ๋ถ€๋ถ„ ๊ทผ์ฒ˜์— "์•ˆ์ „ ์˜์—ญ"์ด๋ผ๋Š” ๋˜ ๋‹ค๋ฅธ ์ž„๊ณ„ ๊ฐ’์„ ์‚ฌ์šฉํ•  ์ˆ˜ ์žˆ์Šต๋‹ˆ๋‹ค (์˜ˆ : ์Šคํฌ๋กค ์˜คํ”„์…‹์ด ์–ด๋–ค ์ ˆ๋Œ€ ๊ฐ’๋ณด๋‹ค ์ž‘์€ ๊ฒฝ์šฐ). ๋ชฉ๋ก์ด ํ•ด๋‹น ์ง€์ ๊นŒ์ง€ ๋ชจ๋“  ์…€์„ ์ธก์ •ํ•˜์—ฌ ์˜ฌ๋ฐ”๋ฅด๊ฒŒ ์ •๋ ฌ๋˜๋„๋ก ๊ฐ•์ œํ•ฉ๋‹ˆ๋‹ค. ์ด ๊ฐ•์ œ ์ธก์ •์˜ ๋น„์šฉ์€ ํ•ญ๋ชฉ ์ˆ˜๊ฐ€ ์ ๊ธฐ ๋•Œ๋ฌธ์— ์ƒ๋Œ€์ ์œผ๋กœ ๋‚ฎ์Šต๋‹ˆ๋‹ค.
    screen shot 2018-06-10 at 5 04 42 pm

์œ„์˜ ์ ‘๊ทผ ๋ฐฉ์‹์œผ๋กœ ์—ฌ์ „ํžˆ ์˜ฌ๋ฐ”๋ฅด๊ฒŒ ์ฒ˜๋ฆฌ๋˜์ง€ ์•Š๋Š” ํ•œ ๊ฐ€์ง€ ๊ฒฝ์šฐ๋Š” "์•ˆ์ „ ์˜์—ญ"์™ธ๋ถ€์— ์„ค์ •๋œ ์Šคํฌ๋กค ์•ต์ปค์ด์ง€๋งŒ ์•ˆ์ „ ์˜์—ญ ๋‚ด๋ถ€์—์žˆ๋Š” ํ˜„์žฌ ์Šคํฌ๋กค์ž…๋‹ˆ๋‹ค (์•„๋ž˜ ์ฐธ์กฐ). ์‚ฌ์šฉ์ž๊ฐ€ ๋ชฉ๋ก์˜ ์‹œ์ž‘ ๋ถ€๋ถ„์œผ๋กœ ์ฒœ์ฒœํžˆ ๋’ค๋กœ ์Šคํฌ๋กคํ•˜๋ฉด ์Šคํฌ๋กค ๋ฒ„๋ฒ… ๊ฑฐ๋ฆผ์—†์ด ์ฒซ ๋ฒˆ์งธ ์…€์„ 0์— ๋งž์ถ”๊ธฐ๊ฐ€ ์–ด๋ ค์šธ ์ˆ˜ ์žˆ์Šต๋‹ˆ๋‹ค.
screen shot 2018-06-10 at 5 08 26 pm

๐Ÿ‘‹ help wanted

๊ฐ€์žฅ ์œ ์šฉํ•œ ๋Œ“๊ธ€

์ด ํ”„๋กœ์ ํŠธ์—๋Š” "๋‹น์‹ ๋“ค"์ด ์—†์Šต๋‹ˆ๋‹ค. ํ•œ ์‚ฌ๋žŒ์ด ๊ด€๋ฆฌํ•ฉ๋‹ˆ๋‹ค.

๊ทธ๋ฆฌ๊ณ  ๊ฐ™์€ ์ผ์— ๋Œ€ํ•ด ๋ถˆํ‰ํ•˜๋ฉด์„œ ๊ฐ™์€ ๋‚  ์—ฌ๋Ÿฌ ๋ฌธ์ œ์— ๋Œ€ํ•œ ์˜๊ฒฌ์„ ๋‚จ๊ธฐ๋Š” ๊ฒƒ์€ ์ผ์ข…์˜ ๊ณ ๋ คํ•˜์ง€ ์•Š์Šต๋‹ˆ๋‹ค. ๊ผญ react-virtualized๋ฅผ ์‚ฌ์šฉํ•˜์„ธ์š”.

๋ชจ๋“  132 ๋Œ“๊ธ€

์ง„ํ–‰์ค‘์ธ MVP๋Š” https://github.com/bvaughn/react-window/compare/master...issues/6 ์—์„œ

๋‚˜๋Š” mui-downshift ๋‚ด์—์„œ ์ด๊ฒƒ์„ ์‚ฌ์šฉํ•˜๊ณ  ํ˜„์žฌ ์—ฌ์ „ํžˆ UNSAFE_componentWillReceiveProps ํ•˜๊ณ  ์žˆ์ง€๋งŒ ๊ฐ€๊นŒ์šด ์žฅ๋ž˜์— (๋™์  ์ฝ˜ํ…์ธ  ๋†’์ด๋ฅผ ์‚ฌ์šฉํ•  ์ˆ˜์žˆ๊ฒŒ๋˜๋ฉด) react-window ๋กœ ์ด์‹ ํ•  ๊ณ„ํš์ž…๋‹ˆ๋‹ค.

์ด๊ฒƒ์€ IOS์˜ UITableView์—์„œ ์žฌ์‚ฌ์šฉ ๊ฐ€๋Šฅํ•œ ๋ฉ”์ปค๋‹ˆ์ฆ˜์ž…๋‹ˆ๊นŒ?

@luoboding ๊ท€ํ•˜์˜ ์งˆ๋ฌธ์„ ์ดํ•ดํ•˜์ง€ ๋ชปํ•ฉ๋‹ˆ๋‹ค. ์ž์„ธํžˆ ์„ค๋ช…ํ•ด ์ฃผ์‹œ๊ฒ ์Šต๋‹ˆ๊นŒ?

@bvaughn ์ฃ„์†กํ•ฉ๋‹ˆ๋‹ค, ๋‚ด ์นœ๊ตฌ, ๋‚ด ์˜์–ด๋Š”๋ณ„๋กœ ์ข‹์ง€ ์•Š์Šต๋‹ˆ๋‹ค.

๋‚ด ํ”„๋กœ์ ํŠธ์— ๋ฌธ์ œ๊ฐ€ ์žˆ์Šต๋‹ˆ๋‹ค. ์„ ํƒ ์š”์†Œ์— ์ˆ˜์ฒœ ๊ฐœ์˜ ์˜ต์…˜์ด ์žˆ์Šต๋‹ˆ๋‹ค. ํŽ˜์ด์ง€๋ฅผ ๋‹ค์‹œ๋กœ๋“œ ํ•  ๋•Œ ๋งค์šฐ ๋Š๋ฆฌ๊ณ  ์žผ์ด ๋ฐœ์ƒํ•ฉ๋‹ˆ๋‹ค. ๋” ๋‚˜์€ ๊ตฌ์„ฑ ์š”์†Œ๋ฅผ ์ž‘์„ฑํ•˜๋ ค๊ณ ํ–ˆ์Šต๋‹ˆ๋‹ค. IOS ๊ฐœ๋ฐœ์ž์˜€์œผ๋ฉฐ โ€‹โ€‹๋‹ค์Œ์—์„œ ์žฌ์‚ฌ์šฉ ๊ฐ€๋Šฅํ•œ ๋ฉ”์ปค๋‹ˆ์ฆ˜์„ ์•Œ๊ณ  ์žˆ์Šต๋‹ˆ๋‹ค. IOS์˜ UITableView, 500px ๋†’์ด ์„ ํƒ ์š”์†Œ๊ฐ€ ํ•„์š”ํ•œ ๊ฒฝ์šฐ ์˜ต์…˜ ์š”์†Œ์˜ ๋†’์ด๋ฅผ 100px๋กœ ๊ตฌ์„ฑํ•˜๋ฏ€๋กœ ์˜ต์…˜ ์š”์†Œ ์ˆ˜์™€ ๋Œ€๊ธฐ์—ด ์šฉ๋Ÿ‰ (ํ˜„์žฌ ํ‘œ์‹œ๋œ ๋ฐ์ดํ„ฐ ์†Œ์Šค ๋Œ€๊ธฐ์—ด)์„ ์ƒ์„ฑ (Math.floor (500/100))ํ•˜๋ฉด๋ฉ๋‹ˆ๋‹ค. ), ์„ ํƒ ์š”์†Œ๋ฅผ ์œ„๋‚˜ ์•„๋ž˜๋กœ ์Šคํฌ๋กค ํ•  ๋•Œ ํ์— ๋ฐ€์–ด ๋„ฃ๊ฑฐ๋‚˜ ํŒํ•˜์—ฌ ๋‹ค์‹œ ๋ Œ๋”๋งํ•ฉ๋‹ˆ๋‹ค.

๋‚ด ํ”„๋กœ์ ํŠธ์—์„œ ๋ฐ˜์‘ ์ฐฝ์„ ๊ฐ€์ ธ์˜ค๊ณ  ์‹ถ์Šต๋‹ˆ๋‹ค. ์ œ๊ฐ€ ์–ธ๊ธ‰ ํ•œ๋Œ€๋กœ ์ž‘๋™ํ•ฉ๋‹ˆ๊นŒ?

๋‹น์‹ ์ด ์„ค๋ช…ํ•˜๊ณ ์žˆ๋Š” ๊ฒƒ์€ ๋ฐ˜์‘ ์œˆ๋„์šฐ (๊ทธ๋ฆฌ๊ณ  ์œˆ๋„์šฐ, ๋˜๋Š” ์˜ค ํด๋ฃจ ์ „ ์ปฌ๋ง, ์ผ๋ฐ˜์ ์œผ๋กœ)์˜ ์ž‘๋™ ๋ฐฉ์‹์ž…๋‹ˆ๋‹ค. ํ•˜์ง€๋งŒ์ด ๋ฌธ์ œ์™€๋Š” ๊ด€๋ จ์ด ์—†์Šต๋‹ˆ๋‹ค. ์ด๊ฒƒ์€ ์œˆ๋„์šฐ ์ฝ˜ํ…์ธ ๋ฅผ ์ ์‹œ์— ์ธก์ •ํ•˜๋Š” ๊ฒƒ์ž…๋‹ˆ๋‹ค. ๊ท€ํ•˜์˜ ๊ฒฝ์šฐ ๊ฐœ์ฒด์˜ ๋†’์ด๊ฐ€ ๊ณ ์ •๋˜์–ด ์žˆ์œผ๋ฏ€๋กœ FixedSizeList ๊ตฌ์„ฑ ์š”์†Œ๋ฅผ ์‚ฌ์šฉํ•  ์ˆ˜ ์žˆ์Šต๋‹ˆ๋‹ค. https://react-window.now.sh/#/examples/list/fixed -size

๋ฐ˜์‘ ์ฐฝ์—์„œ ๊ธฐ๋ณธ์ ์œผ๋กœ ํ•ด๊ฒฐ ๋œ ์•ต์ปค๋ง์„ ๋ณด๋Š” ๊ฒƒ์ด ์ข‹์Šต๋‹ˆ๋‹ค.

๊ทธ๊ฑด ๊ทธ๋ ‡๊ณ , ๋‹ค์ด์–ด๊ทธ๋žจ์—์„œ ๋„ˆ๋ฌด ๋งŽ์ด ๋ฐ”๋ฅผ ๊ฒฝ์šฐ ๋ฏธ์•ˆํ•ฉ๋‹ˆ๋‹ค ... ๐Ÿ˜…

@bvaughn ์–ธ์ œ์ด ๊ธฐ๋Šฅ์„ ์ถœ์‹œ ํ•  ์˜ˆ์ •

์ง€๊ธˆ์ด ์ž‘์—…์„ ์™„๋ฃŒ ํ•  ์‹œ๊ฐ„ (๋ฐ ์—๋„ˆ์ง€)์„ ์ฐพ๋Š” ๋ฐ ์–ด๋ ค์›€์ด ์žˆ๊ธฐ ๋•Œ๋ฌธ์—์ด ๊ธฐ๋Šฅ์—†์ด 1.0.0์„ ๊ฒŒ์‹œํ–ˆ์Šต๋‹ˆ๋‹ค. ์•ž์œผ๋กœ๋„ ์ถ”๊ฐ€ ํ•  ๊ณ„ํš์ž…๋‹ˆ๋‹ค. ์–ธ์ œ์— ๋Œ€ํ•œ ๊ฒฌ์ ์ด ์—†์Šต๋‹ˆ๋‹ค.

Polymer์˜ "์ฒ  ๋ชฉ๋ก"์ด ์—ฌ๊ธฐ์—์„œ ์ œ์•ˆํ•˜๋Š” ๊ฒƒ๊ณผ ์œ ์‚ฌํ•œ ๊ธฐ์ˆ ์„ ์‚ฌ์šฉํ•˜๋Š” ๊ฒƒ ๊ฐ™์Šต๋‹ˆ๋‹ค : https://github.com/domenic/infinite-list-study-group/blob/master/studies/Polymer-iron-list.md #virtual -list-sizing

์ด๊ฒƒ์€ ์šฐ๋ฆฌ์—๊ฒŒ ์ •๋ง ์œ ์šฉ ํ•  ๊ฒƒ์ž…๋‹ˆ๋‹ค. ์ง€๊ธˆ์€ CSS๋ฅผ ๊ฐ€์ƒ ๋ชฉ๋ก์— ์ „๋‹ฌํ•˜๊ธฐ ์œ„ํ•ด ๋†’์ด ๊ณ„์‚ฐ์„ ๋ณต์ œํ•˜๋Š” ๊ตฌ์„ฑ ์š”์†Œ ๋…ผ๋ฆฌ์™€ ๋™๊ธฐํ™”ํ•ด์•ผํ•˜๋Š” ๊ฒƒ์ฒ˜๋Ÿผ ๋ณด์ž…๋‹ˆ๋‹ค.

@kevinder ๊ฐ€ ์ ์‹œ์— ์ธก์ • ๋œ ์ฝ˜ํ…์ธ ๋ฅผ ์ฒ˜๋ฆฌํ•˜๋Š” ๋ฐฉ๋ฒ•์„ ๊ณต์œ  ํ•  ์ˆ˜ ์žˆ์Šต๋‹ˆ๊นŒ? ๋ฏธ๋ฆฌ ๊ฐ์‚ฌ๋“œ๋ฆฝ๋‹ˆ๋‹ค

@carlosagsmendes ๊ฐ€ ์ด๊ฒƒ์ด ๋„์›€์ด ๋ ์ง€ ํ™•์‹คํ•˜์ง€ ์•Š์ง€๋งŒ ์ฑ„ํŒ… ๊ธฐ๋ก์„ ํ‘œ์‹œํ•˜๊ธฐ ์œ„ํ•ด ์ด๊ฒƒ์„ ์‚ฌ์šฉํ•  ๋•Œ ๋‚ด๊ฐ€ํ•˜๋Š” ์ผ์ž…๋‹ˆ๋‹ค.

1.) ์ƒ์„ฑ์ž์—์„œ ๋ชฉ๋ก ๋ฐ ChatHistory ๊ตฌ์„ฑ ์š”์†Œ์— ๋Œ€ํ•œ ์ฐธ์กฐ๋ฅผ ๋งŒ๋“ญ๋‹ˆ๋‹ค.

  constructor(props) {
    super(props);
    this.listRef = createRef();
    this.chatHistoryRef = createRef();
    this.listHeight = 0;
  }

๊ทธ๋Ÿฐ ๋‹ค์Œ ๋ชฉ๋ก ๋ Œ๋”๋ง์„ ๋‹ด๋‹นํ•˜๋Š” ChatHistory refs๋ฅผ ์ „๋‹ฌํ•ฉ๋‹ˆ๋‹ค.

2.) ๋ถ€๋ชจ ๊ตฌ์„ฑ ์š”์†Œ์˜ componentDidMount ์—์„œ ChatHistory ref๋ฅผ ์‚ฌ์šฉํ•˜์—ฌ ์š”์†Œ์˜ ๋†’์ด๋ฅผ ๊ฐ€์ ธ์˜ต๋‹ˆ๋‹ค.

componentDidMount() {
    this.listHeight = this.chatHistoryRef.current.offsetHeight;
}

3.) ๋ถ€๋ชจ ๊ตฌ์„ฑ ์š”์†Œ์—์„œ ๋‚˜๋Š” chathistory ์„ธ๋ถ€ ์‚ฌํ•ญ๊ณผ ํ•จ๊ป˜ ๋ฐฐ์—ด์„ ์ƒํƒœ๋กœ ์œ ์ง€ํ•ฉ๋‹ˆ๋‹ค. ํ•ด๋‹น ๋ฐฐ์—ด์— ์ƒˆ ํ•ญ๋ชฉ์„ ์ถ”๊ฐ€ ํ•  ๋•Œ ๋‹ค์Œ๊ณผ ๊ฐ™์ดํ•ฉ๋‹ˆ๋‹ค.

  // find out how many pixels in height the text is going to use
  const size = getSize({
    text: displayText,
    className: styles.message,
  });

  let { height } = size;
  height += 20; // adds some spacing in pixels between messages
...rest of items needed for the chat history item..add them all to an array and update state

getSize ์€ https://github.com/schickling/calculate-size๋ฅผ ๊ธฐ๋ฐ˜์œผ๋กœํ•˜์ง€๋งŒ ํด๋ž˜์Šค ์ด๋ฆ„ ์ˆ˜๋ฝ์„ ์ง€์›ํ•˜๋„๋ก ์ˆ˜์ •ํ–ˆ์Šต๋‹ˆ๋‹ค. ํ•ด๋‹น ํด๋ž˜์Šค๋Š” ๊ฐœ๋ณ„ ๋ฉ”์‹œ์ง€๋ฅผ ํ‘œ์‹œํ•˜๊ธฐ์œ„ํ•œ ์ปจํ…Œ์ด๋„ˆ๋กœ ์‚ฌ์šฉ๋˜๋Š” ๊ฒƒ๊ณผ ๋™์ผํ•ฉ๋‹ˆ๋‹ค.

์ด๊ฒƒ์„ ๋‹ฌ์„ฑํ•˜๋Š” ๋” ์ข‹์€ ๋ฐฉ๋ฒ•์ด ์žˆ๋‹ค๊ณ  ํ™•์‹ ํ•˜์ง€๋งŒ ๊ฝค ๋น ๋ฅด๋ฉฐ ์•„์ง ๋ฌธ์ œ๊ฐ€ ๋ฐœ์ƒํ•˜์ง€ ์•Š์•˜์Šต๋‹ˆ๋‹ค.

@osdlge : ์ฝ”๋“œ ์ƒŒ๋“œ ๋ฐ•์Šค (๋˜๋Š” ์ด์™€ ์œ ์‚ฌํ•œ)์™€ ๊ฐ™์ด ๋‚ด๊ฐ€ ํ™•์ธํ•  ์ˆ˜์žˆ๋Š” ๋ชจ๋“  ๊ณณ์—์„œ์ด ๋ฐ๋ชจ๋ฅผ ๊ฐ€์งˆ ๊ฐ€๋Šฅ์„ฑ์ด ์žˆ์Šต๋‹ˆ๊นŒ?

@bvaughn ํ™•์‹คํžˆ, ๋‚ด ์ฝ”๋“œ์˜ ๊ด€๋ จ ๋ถ€๋ถ„์„ https://codesandbox.io/s/5z282z7q1l๋กœ ์ถ”์ถœํ–ˆ์Šต๋‹ˆ๋‹ค.

๊ณต์œ  ํ•ด์ฃผ์…”์„œ ๊ฐ์‚ฌํ•ฉ๋‹ˆ๋‹ค! ๐Ÿ˜„

์ง„ํ–‰์ค‘์ธ ์ผ๋ถ€ ์ž‘์—…์„ ๊ฒŒ์œผ๋ฅด๊ฒŒ ์ธก์ • ๋œ ์ฝ˜ํ…์ธ ์— ๋Œ€ํ•œ ์ดˆ๊ธฐ ์ ‘๊ทผ ๋ฐฉ์‹์„ issue / 6์ด๋ผ๋Š” ๋ธŒ๋žœ์น˜์— ํ‘ธ์‹œํ–ˆ์Šต๋‹ˆ๋‹ค.

๋ฐ๋ชจ๋„ ๋ฐฐํฌํ–ˆ์Šต๋‹ˆ๋‹ค.
https://react-window-next.now.sh/#/examples/list/dynamic -size

์•„์ฃผ ๋ฉ‹์ง€๋‹ค.

๋‚˜๋Š” ์—ฌ์ „ํžˆ ์ด์Šˆ / 6 ๋ธŒ๋žœ์น˜ ์†Œ์Šค์™€์ด ํ† ๋ก ์„ ์ง„ํ–‰ํ•˜๋ฉด์„œ ๋ฌดํ•œ ์Šคํฌ๋กค๋ง์˜ ์ผ๋ฐ˜์ ์ธ ๋ฌธ์ œ๋ฅผ ์ดํ•ดํ•˜๋ ค๊ณ  ๋…ธ๋ ฅํ•˜๊ณ  ์žˆ์Šต๋‹ˆ๋‹ค. ๋”ฐ๋ผ์„œ ๋‹ค์Œ ์งˆ๋ฌธ์€ ์˜๋ฏธ๊ฐ€ ์—†์„ ์ˆ˜ ์žˆ์ง€๋งŒ ์—ฌ๊ธฐ์— ๋” ์ดํ•ดํ•˜๊ณ  ์‹ถ์Šต๋‹ˆ๋‹ค.

์œ„์˜ ์–ธ๊ธ‰ ์ด ๋งํฌ ๋œ ๊ธฐ์‚ฌ ๋‚˜ CSS Scroll Anchoring ์‚ฌ์–‘ ์—์„œ์™€ ๊ฐ™์€ ๊ธฐ์ˆ  ๋กœ

๋ฏธ๋ฆฌ ๊ฐ์‚ฌ๋“œ๋ฆฝ๋‹ˆ๋‹ค

์ฒซ ๋ฒˆ์งธ ๋งํฌ์™€๋Š” ์ ‘์„  ์ ์œผ๋กœ ๊ด€๋ จ์ด ์žˆ์ง€๋งŒ ๋‘ ๋ฒˆ์งธ ๋งํฌ์™€๋Š” ๊ด€๋ จ์ด ์—†์Šต๋‹ˆ๋‹ค. ๋‹ค๋ฅธ ์‚ฌ์–‘์ด๋‚˜ ์ œ์•ˆ๊ณผ ๊ด€๋ จ์ด ์—†์–ด์„œ๊ฐ€ ์•„๋‹ˆ๋ผ ๋‚˜์—๊ฒŒ ์˜๋ฏธ๊ฐ€ ์žˆ๊ธฐ ๋•Œ๋ฌธ์—์ด ๋ฌธ์ œ์— ์‚ฌ์šฉํ•˜๊ธฐ๋กœ ์„ ํƒํ•œ ์šฉ์–ด์ž…๋‹ˆ๋‹ค.

๋˜ํ•œ NPM์— ๋Œ€ํ•œ ์‚ฌ์ „ ์ถœ์‹œ ๋ฒ„์ „์˜ react-window๋ฅผ "next"(์˜ˆ : yarn add react-window@next )๋กœ ๊ฒŒ์‹œํ–ˆ์Šต๋‹ˆ๋‹ค.

์ด ์ฝ”๋“œ ์ƒŒ๋“œ ๋ฐ•์Šค๋ฅผ ํฌํฌํ•˜์—ฌ ๊ฐ€์ง€๊ณ  ๋†€ ์ˆ˜ ์žˆ์Šต๋‹ˆ๋‹ค.
https://codesandbox.io/s/5x8vlm0o7n

๋ฐฉ๊ธˆ ํ…Œ์ŠคํŠธํ–ˆ์Šต๋‹ˆ๋‹ค. ๋‚˜๋Š” 10000 ๊ฐœ์˜ ๋‹จ๋ฝ์„ ์‹œ๋„ํ•˜๊ณ  ๋์œผ๋กœ ์ ํ”„ํ•˜๋ ค๊ณ ํ–ˆ๋‹ค. ์œกํฌ์˜€๋‹ค.
๋‚ด๊ฐ€ ์˜ฌ๋ฐ”๋ฅด๊ฒŒ ์ดํ•ดํ–ˆ๋‹ค๋ฉด ๋์œผ๋กœ ์ถ”์ •๋˜๋Š” ํ–‰๋งŒ ์ธก์ • ํ–ˆ์–ด์•ผ ํ–ˆ์œผ๋ฏ€๋กœ ์ฆ‰์‹œ ๋์œผ๋กœ ์ ํ”„ํ–ˆ์„ ๊ฒƒ์ž…๋‹ˆ๋‹ค. ์ด ์˜ฌ๋ฐ”๋ฅธ์ง€?

2018 ๋…„ 10 ์›” 12 ์ผ 12:53์— Brian Vaughn [email protected] ์€ ๋‹ค์Œ๊ณผ ๊ฐ™์ด ์ผ์Šต๋‹ˆ๋‹ค.

๋˜ํ•œ NPM์— ๋Œ€ํ•œ ์‚ฌ์ „ ๋ฆด๋ฆฌ์Šค ๋ฒ„์ „์˜ react-window๋ฅผ "next"๋กœ ๊ฒŒ์‹œํ–ˆ์Šต๋‹ˆ๋‹ค (์˜ˆ : yarn add react-window @ next).

์ด ์ฝ”๋“œ ์ƒŒ๋“œ ๋ฐ•์Šค๋ฅผ ํฌํฌํ•˜์—ฌ ๊ฐ€์ง€๊ณ  ๋†€ ์ˆ˜ ์žˆ์Šต๋‹ˆ๋‹ค.
https://codesandbox.io/s/5x8vlm0o7n https://codesandbox.io/s/5x8vlm0o7n
โ€”
์ด ์Šค๋ ˆ๋“œ๋ฅผ ๊ตฌ๋…ํ–ˆ๊ธฐ ๋•Œ๋ฌธ์—์ด ๋ฉ”์‹œ์ง€๊ฐ€ ์ „์†ก๋˜์—ˆ์Šต๋‹ˆ๋‹ค.
์ด ์ด๋ฉ”์ผ์— ์ง์ ‘ ๋‹ต์žฅํ•˜๊ฑฐ๋‚˜ GitHub https://github.com/bvaughn/react-window/issues/6#issuecomment-429271555 ์—์„œ ๋ณด๊ฑฐ๋‚˜ https://github.com/notifications/unsubscribe-auth/ ์Šค๋ ˆ๋“œ๋ฅผ ์Œ์†Œ๊ฑฐํ•ฉ๋‹ˆ๋‹ค.

์•„๋‹ˆ์š”, ์ œ๊ฐ€ ํ‘ธ์‹œ ํ•œ ์ดˆ๊ธฐ ๋ถ„๊ธฐ๋Š” ์•Œ๊ณ ๋ฆฌ์ฆ˜์„ ๊ตฌํ˜„ํ•˜์ง€ ์•Š์Šต๋‹ˆ๋‹ค.
์ด ๋ฌธ์ œ์— ์„ค๋ช…๋˜์–ด ์žˆ์Šต๋‹ˆ๋‹ค. ๋” ์ˆœ์ง„ํ•œ ์ ‘๊ทผ ๋ฐฉ์‹์ด ํ•„์š”ํ•ฉ๋‹ˆ๋‹ค.
๋‚˜์ค‘์— ์ฝ˜ํ…์ธ ๋ฅผ ๋ Œ๋”๋งํ•˜๊ธฐ ์ „์— ์ด์ „ ์ฝ˜ํ…์ธ ๋ฅผ ์ธก์ •ํ•ฉ๋‹ˆ๋‹ค.

ํ˜ผ๋ž€์„ ๋“œ๋ ค ์ฃ„์†กํ•ฉ๋‹ˆ๋‹ค!

2018 ๋…„ 10 ์›” 12 ์ผ ๊ธˆ์š”์ผ ์˜คํ›„ 6:34 akraines [email protected] ์ž‘์„ฑ :

๋ฐฉ๊ธˆ ํ…Œ์ŠคํŠธํ–ˆ์Šต๋‹ˆ๋‹ค. ๋‚˜๋Š” 10000 ๊ฐœ์˜ ๋‹จ๋ฝ์„ ์‹œ๋„ํ•˜๊ณ 
์ข…๋ฃŒ. ์œกํฌ์˜€๋‹ค.
๋‚ด๊ฐ€ ์˜ฌ๋ฐ”๋ฅด๊ฒŒ ์ดํ•ดํ–ˆ๋‹ค๋ฉด ์ถ”์ • ๋œ ํ–‰๋งŒ ์ธก์ •ํ–ˆ์„ ๊ฒƒ์ž…๋‹ˆ๋‹ค.
๊ทธ๋ž˜์„œ ๊ทธ๊ฒƒ์€ ์ฆ‰์„์—์„œ
์ข…๋ฃŒ. ์ด ์˜ฌ๋ฐ”๋ฅธ์ง€?

2018 ๋…„ 10 ์›” 12 ์ผ 12:53์— Brian Vaughn [email protected] ์€ ๋‹ค์Œ๊ณผ ๊ฐ™์ด ์ผ์Šต๋‹ˆ๋‹ค.

๋˜ํ•œ NPM์— ๋Œ€ํ•œ ๋ฐ˜์‘ ์ฐฝ ์‹œํ—˜ํŒ ๋ฒ„์ „์„ ๋‹ค์Œ๊ณผ ๊ฐ™์ด ๊ฒŒ์‹œํ–ˆ์Šต๋‹ˆ๋‹ค.
"next"(์˜ˆ : yarn add react-window @ next).

์ด ์ฝ”๋“œ ์ƒŒ๋“œ ๋ฐ•์Šค๋ฅผ ํฌํฌํ•˜์—ฌ ๊ฐ€์ง€๊ณ  ๋†€ ์ˆ˜ ์žˆ์Šต๋‹ˆ๋‹ค.
https://codesandbox.io/s/5x8vlm0o7n < https://codesandbox.io/s/5x8vlm0o7n

โ€”
์ด ์Šค๋ ˆ๋“œ๋ฅผ ๊ตฌ๋…ํ–ˆ๊ธฐ ๋•Œ๋ฌธ์—์ด ๋ฉ”์‹œ์ง€๊ฐ€ ์ „์†ก๋˜์—ˆ์Šต๋‹ˆ๋‹ค.
์ด ์ด๋ฉ”์ผ์— ์ง์ ‘ ํšŒ์‹ ํ•˜๊ณ  GitHub์—์„œ ํ™•์ธํ•˜์‹ญ์‹œ์˜ค. <
https://github.com/bvaughn/react-window/issues/6#issuecomment-429271555>,
๋˜๋Š” ์Šค๋ ˆ๋“œ ์Œ์†Œ๊ฑฐ <
https://github.com/notifications/unsubscribe-auth/AOf2h7RmSEyGmyrEdMY6GgyZFjCKlDDFks5ukGafgaJpZM4UTb3P
.

โ€”
๋‹น์‹ ์ด ์–ธ๊ธ‰ ๋˜์—ˆ๊ธฐ ๋•Œ๋ฌธ์— ์ด๊ฒƒ์„ ๋ฐ›๊ณ  ์žˆ์Šต๋‹ˆ๋‹ค.
์ด ์ด๋ฉ”์ผ์— ์ง์ ‘ ๋‹ต์žฅํ•˜๊ณ  GitHub์—์„œ ํ™•์ธํ•˜์„ธ์š”.
https://github.com/bvaughn/react-window/issues/6#issuecomment-429282228 ,
๋˜๋Š” ์Šค๋ ˆ๋“œ ์Œ์†Œ๊ฑฐ
https://github.com/notifications/unsubscribe-auth/AABznR5R1N0ErukleIfvaLQORF_NECgRks5ukHBHgaJpZM4UTb3P
.

์•ผ,
๊ณต์‹ ์ถœ์‹œ์— ๋Œ€ํ•œ ๊ฒฌ์ ์ด ์žˆ๋Š”์ง€ ๋ฌผ์–ด๋ณด๊ณ  ์‹ถ์—ˆ์Šต๋‹ˆ๋‹ค.

์šฐ๋ฆฌ ํŒ€์€ ์šฐ๋ฆฌ๊ฐ€ ์‹œ์ž‘ํ•œ ์ƒˆ ํ”„๋กœ์ ํŠธ์— react-virtualized ๋ฅผ ์‚ฌ์šฉํ•˜์ง€๋งŒ ์Šคํฌ๋กค ์—… ๋ฐ ํŠน์ • ํ–‰ ์ธ๋ฑ์Šค๋กœ ์ ํ”„ํ•˜๋Š” ๊ธฐ๋Šฅ์ด ํ•„์š”ํ•ฉ๋‹ˆ๋‹ค (ํ–‰์— ์ด๋ฏธ์ง€ ๋ฐ ๊ธฐํƒ€ ๋ณ€๊ฒฝ ๋‚ด์šฉ์ด ํฌํ•จ ๋œ ๋™์  ๋‚ด์šฉ์ด ์žˆ๋‹ค๊ณ  ๊ฐ€์ • ํ•  ์ˆ˜ ์žˆ์œผ๋ฏ€๋กœ).

์•ŒํŒŒ ๋ฆด๋ฆฌ์Šค์—์„œ react-window ๋กœ ๋งˆ์ด๊ทธ๋ ˆ์ด์…˜ํ•˜๋Š” ๊ฒƒ์ด ์ข‹์Šต๋‹ˆ๋‹ค. ์•„๋‹ˆ๋ฉด ๊ณต์‹ ์ถœ์‹œ๋ฅผ ๊ธฐ๋‹ค๋ ค์•ผํ•ฉ๋‹ˆ๊นŒ?

๋˜ํ•œ์ด ๊ธฐ๋Šฅ์„ ์™„์„ฑํ•˜๋Š” ๋ฐ ๊ธฐ์—ฌํ•  ์ˆ˜์žˆ๋Š” ๋ฐฉ๋ฒ•์ด ์žˆ๋‹ค๋ฉด ๋„์›€์„ ๋“œ๋ฆฌ๊ณ  ์‹ถ์Šต๋‹ˆ๋‹ค ๐Ÿ˜„

์•ˆํƒ€๊น๊ฒŒ๋„ ์ง€๊ธˆ์€ ๋งŽ์€ ํ…Œ์ŠคํŠธ๋ฅผ ์ˆ˜ํ–‰ํ•˜์ง€ ์•Š์•˜๊ธฐ ๋•Œ๋ฌธ์— ํ˜„์žฌ ๋ฆด๋ฆฌ์Šค ์ผ์ •์„ ์ •ํ•  ์ˆ˜ ์—†์Šต๋‹ˆ๋‹ค. ๊ทธ๋“ค).

๊ธฐ์—ฌํ•˜๊ณ  ์‹ถ๋‹ค๋ฉด ํ•œ ๊ฐ€์ง€ ๋ฐฉ๋ฒ•์€ ์•ŒํŒŒ ๋ฆด๋ฆฌ์Šค๋ฅผ ํ…Œ์ŠคํŠธํ•˜๊ณ  ์–ผ๋งˆ๋‚˜ ์ž˜ ์ž‘๋™ํ•˜๋Š”์ง€ ์•Œ๋ ค์ฃผ๊ณ  ๋ฒ„๊ทธ๋ฅผ ๋ฐœ๊ฒฌํ•˜๋ฉด ์•Œ๋ ค์ฃผ๋Š” ๊ฒƒ์ž…๋‹ˆ๋‹ค.

์กฐ๋งŒ๊ฐ„ ์ด๊ฒƒ์— ๋” ์ดˆ์ ์„ ๋งž์ถœ ๊ฒƒ์ด์ง€๋งŒ ์–ผ๋งˆ๋‚˜ ๋นจ๋ฆฌ ๋งํ•  ์ˆ˜๋Š” ์—†์Šต๋‹ˆ๋‹ค. ํŠนํžˆ ๋‹ค์Œ ์ฃผ ๋˜๋Š” ์ดํ‹€ ๋™์•ˆ ๋‚˜๋Š” React conf์— ์‚ฐ๋งŒ ํ•ด์ ธ 16.6 ๋ฆด๋ฆฌ์Šค๋ฅผ ์ค€๋น„ํ–ˆ์Šต๋‹ˆ๋‹ค.

@bvaughn ํ›Œ๋ฅญํ•œ ์ž‘์—… ๐Ÿ‘ ๋“œ๋””์–ด ๋†€ ์‹œ๊ฐ„์ด ์žˆ์Šต๋‹ˆ๋‹ค. ๐Ÿ•น

display: none ๋ชฉ๋ก์„ ์ˆจ๊ธธ ๋•Œ ์•ฝ๊ฐ„์˜ ์ˆ˜์ •์ด ํ•„์š”ํ•œ ๊ฒƒ ๊ฐ™์Šต๋‹ˆ๋‹ค. .

๋ฌธ์ œ๋ฅผ ์ œ์‹œํ•˜๋Š” ๊ฐ„๋‹จํ•œ ์ฝ”๋“œ ์ƒŒ๋“œ ๋ฐ•์Šค :
https://codesandbox.io/s/p7vq18wmjq

๋””์Šคํ”Œ๋ ˆ์ด ์—†์Œ์„ ํŠธ๋ฆฌ๊ฑฐํ•˜๋ฉด ๋ชจ๋“  ํ•˜์œ„ ํ•ญ๋ชฉ์ด offsetHeight === 0 ๊ฐ€์ง€๊ธฐ ๋•Œ๋ฌธ์— ๋ฐœ์ƒํ•ฉ๋‹ˆ๋‹ค.
resize๋Š” kiks๋ฅผ ๊ด€์ฐฐํ•˜๊ณ  ์ƒˆ๋กœ์šด ๊ฐ’์„ ์—…๋ฐ์ดํŠธํ•ฉ๋‹ˆ๋‹ค. react-window ๋Š” ๋ฐœ์‹ ์ž๊ฐ€ ์ˆจ๊ธธ ๊ฒฝ์šฐ์ด ์ƒํ™ฉ์„ ์‹ ๊ฒฝ ์“ฐ์ง€ ์•Š์•„์•ผํ•˜๋ฉฐ, ๊ธฐ๋ณธ์€ handleNewMeasurements ์ฐจ๋‹จํ•˜์—ฌ ์ฒ˜๋ฆฌํ•ด์•ผํ•ฉ๋‹ˆ๋‹ค.

์ด ์ค„์ด
https://github.com/bvaughn/react-window/blob/issues/6/src/DynamicSizeList.js#L443
๋ณ€๊ฒฝ ๋  ๊ฒƒ์ด๋‹ค

handleNewMeasurements: instance._handleNewMeasurements

๊ทธ๋Ÿฐ ๋‹ค์Œ ๊ธฐ๋ณธ ๋กœ์ง์„ ์žฌ์ •์˜ ํ•  ์ˆ˜ ์žˆ์Šต๋‹ˆ๋‹ค.

let _handleNewMeasurements

<DynamicSizeList  
  ref={current => {
    if (current) {
      _handleNewMeasurements = current._handleNewMeasurements
      current._handleNewMeasurements = (...args) => {
        if (!isHidden) {
          return _handleNewMeasurements(...args)
        }
      }
    }
  }}
  {...otherProps}

์Šคํฌ๋กค์ด ์ง„ํ–‰๋˜๋Š” ๋™์•ˆ ํฌ๊ธฐ๊ฐ€ ์กฐ์ • ๋œ ํ•ญ๋ชฉ์„ ์„ค๋ช…ํ•˜๊ธฐ ์œ„ํ•ด margin-top ๋ฅผ ์‚ฌ์šฉํ•˜์—ฌ Firefox ๋ถ€๋“œ๋Ÿฌ์šด ์Šคํฌ๋กค ๋ฒ„๊ทธ๋ฅผ ์ˆ˜์ •ํ•˜๋Š” ์—…๋ฐ์ดํŠธ๋ฅผ์ด ๋ธŒ๋žœ์น˜์— ํ‘ธ์‹œํ–ˆ์Šต๋‹ˆ๋‹ค (๊ทธ๋ฆฌ๊ณ  NPM์— ์ƒˆ @next ํƒœ๊ทธ๋ฅผ ๊ฒŒ์‹œํ–ˆ์Šต๋‹ˆ๋‹ค). ๋‚ด๊ฐ€ ์›ํ•˜๋Š” ๊ฒƒ๋ณด๋‹ค ๋” ๋ณต์žกํ•˜์ง€๋งŒ ์ง€๊ธˆ์€ ์ด๊ฒƒ์„ ์ฒ˜๋ฆฌํ•˜๋Š” ๋” ์ข‹์€ ๋ฐฉ๋ฒ•์„ ๋ชจ๋ฅด๊ฒ ์Šต๋‹ˆ๋‹ค. (๊ทนํ•œ์˜ ๊ฒฝ์šฐ์—๋„ ์—ฌ์ „ํžˆ ๊ฑฐ์นœ ๊ฐ€์žฅ์ž๋ฆฌ๊ฐ€์žˆ์„ ์ˆ˜ ์žˆ๋‹ค๊ณ  ์ƒ๊ฐํ•˜๊ธฐ ๋•Œ๋ฌธ์—์ด ์ ‘๊ทผ ๋ฐฉ์‹์— ๋Œ€ํ•ด ๋” ๋งŽ์€ ํ…Œ์ŠคํŠธ๋ฅผ ์ˆ˜ํ–‰ํ•ด์•ผํ•ฉ๋‹ˆ๋‹ค.)

์œ„์˜ ํ”ผ๋“œ๋ฐฑ์— ๊ฐ์‚ฌ๋“œ๋ฆฝ๋‹ˆ๋‹ค, @piecyk. ์•„์ง ํŒŒํ—ค์น  ์‹œ๊ฐ„์ด ์—†์—ˆ์Šต๋‹ˆ๋‹ค. (์ด๊ฒƒ์€ ํ˜„์žฌ ์ €์—๊ฒŒ ์—ฌ์ „ํžˆ ์ผ์ข…์˜ ๋ถ€์ˆ˜์  ์ธ ํ”„๋กœ์ ํŠธ์ž…๋‹ˆ๋‹ค.)

์ ์–ด๋„ Firefox์— ๋Œ€ํ•ด scrollBy ์ฐฌ์„ฑํ•˜์—ฌ ๋งˆ์ง„ ํ•ดํ‚น์„ ์ œ๊ฑฐ ํ•  ์ˆ˜์žˆ์„ ๊ฒƒ ๊ฐ™์Šต๋‹ˆ๋‹ค. ๊ทธ๋ž˜๋„ IE์™€ Edge๋ฅผ ๋จผ์ € ํ…Œ์ŠคํŠธํ•ด์•ผํ•ฉ๋‹ˆ๋‹ค. ๊ทธ๋“ค ์ž์‹ ์˜ ์–ด๋ ค์›€์ด์žˆ์„ ์ˆ˜ ์žˆ์Šต๋‹ˆ๋‹ค.

๋„ค @bvaughn ์•Œ์•„์š”, ๋ฉ‹์ง„ ์ž‘ํ’ˆ ๐Ÿ‘ ์‹œ๊ฐ„์„ ์–ด๋–ป๊ฒŒ ์ฐพ๋Š” ์ง€ ๋ชจ๋ฅด๊ฒ ์–ด์š”! ๐Ÿฅ‡ ์ข‹์•„์š”!

๊ทธ๋Ÿฌ๋‚˜ ๋ชฉ๋ก์ด ๋””์Šคํ”Œ๋ ˆ์ด ์—†์Œ์œผ๋กœ ์ˆจ๊ฒจ์ง„ ์ผ๋ถ€ DOM ์š”์†Œ์—์žˆ์„ ๋•Œ ๋ฌธ์ œ๋กœ ๋Œ์•„๊ฐ€ ๋ณด๊ฒ ์Šต๋‹ˆ๋‹ค. ๊ธฐ๋ณธ์ ์œผ๋กœ ๋ž˜ํผ์— ๋†’์ด, ๋„ˆ๋น„๊ฐ€ ์žˆ๋Š”์ง€ ํ™•์ธํ•ด์•ผํ•ฉ๋‹ˆ๋‹ค. ๊ทธ๋ ‡์ง€ ์•Š์€ ๊ฒฝ์šฐ ๋ Œ๋”๋ง์„ ์‹œ์ž‘ํ•˜๊ณ  ์‹ถ์ง€ ์•Š์Šต๋‹ˆ๋‹ค (ํ˜„์žฌ ๋ Œ๋”๋ง์„ ์‹œ๋„ํ•ฉ๋‹ˆ๋‹ค. ์ „์ฒด ๋ชฉ๋ก) ๋‚ด์ผ ๊ทธ๊ฒƒ์„ ๊ณ ์น˜๊ธฐ ์œ„ํ•ด ๋…ธ๋ ฅํ•  ๊ฒƒ์ž…๋‹ˆ๋‹ค (๋ฌด์–ธ๊ฐ€ ์ˆจ๊ฒจ์ ธ ์žˆ์Šต๋‹ˆ๋‹ค)

์˜ˆ. ์„ค๋ช…ํ•˜์‹œ๋Š” ๋ฌธ์ œ์˜ ํ•ต์‹ฌ์„ ์ดํ•ดํ•ฉ๋‹ˆ๋‹ค. ๊ทธ๋ž˜๋„ ๋” ๋งŽ์€ ์ธ์Šคํ„ด์Šค ๋ฉ”์„œ๋“œ๋ฅผ ์žฌ์ •์˜ / ์›์ˆญ์ด ํŒจ์น˜ํ•˜์—ฌ ํ•ดํ‚นํ•˜๋Š” ์ƒ๊ฐ์ด ์‹ซ๊ธฐ ๋•Œ๋ฌธ์— ๋จผ์ € ์ข€ ๋” ์ƒ๊ฐํ•˜๊ณ  ์‹ถ์Šต๋‹ˆ๋‹ค.

@next ํŒจํ‚ค์ง€๊ฐ€ ์†์ƒ๋œ ๊ฒƒ ๊ฐ™์Šต๋‹ˆ๊นŒ?

https://codesandbox.io/s/5x8vlm0o7n

๊ทธ๊ฒƒ์ด ์งˆ๋ฌธ์„ ๋‚จ๊ธฐ๊ธฐ์— ์ ์ ˆํ•œ ์žฅ์†Œ์ธ์ง€ ๋ชจ๋ฅด๊ฒ ์Šต๋‹ˆ๋‹ค. ๋‚ด๊ฐ€ ํ‹€๋ ธ๋‹ค๋ฉด ์‹ค๋ก€ํ•ฉ๋‹ˆ๋‹ค. ๊ฐ„๋‹จํžˆ ๋งํ•ด์„œ :

  • ๋‚ด๊ฐ€ ์‚ฌ์šฉํ–ˆ์Šต๋‹ˆ๋‹ค DynamicSizeList ๊ณผ ํ•จ๊ป˜ AutoResizer ๋ฉ‹์ง€๊ฒŒํ•˜๊ณ  ์ž‘๋™ ์ผ๋ฐ˜์ ์ž…๋‹ˆ๋‹ค. ๋ช…์„ฑ!
  • ์ฝ˜ํ…์ธ ๋ฅผ ํ™•์žฅํ•˜๊ณ  (๋ณด์กฐ ์ •๋ณด๊ฐ€์žˆ๋Š” div ์ถ”๊ฐ€) ์ถ•์†Œ ํ•  ์ˆ˜์žˆ๋Š” ํ–‰์„ ์†Œ๊ฐœํ•˜๋ผ๋Š” ์š”์ฒญ์„ ๋ฐ›์•˜์Šต๋‹ˆ๋‹ค.
  • ๋˜ํ•œ ์ „์—ญ ํ™•์žฅ / ์ถ•์†Œ ์ž‘์—…์„ ์ˆ˜์‹ ํ•˜๋Š” ์ด๋Ÿฌํ•œ ํ–‰์— (redux๋ฅผ ํ†ตํ•ด) ์†Œํ’ˆ์„ ์ถ”๊ฐ€ํ–ˆ์Šต๋‹ˆ๋‹ค.
  • ์žฌ๋ฏธ์žˆ๋Š” ์ผ์ด ์‹œ์ž‘๋ฉ๋‹ˆ๋‹ค. ํ™•์žฅ / ์ถ•์†Œ๋ฅผ ํด๋ฆญํ•˜๋ฉด ๋ชจ๋“  ๊ฒƒ์ด ๋ฉ‹์ ธ ๋ณด์ž…๋‹ˆ๋‹ค!
  • ์กฐ๊ธˆ ์Šคํฌ๋กค ํ•œ ๋‹ค์Œ ๋ชจ๋“  ํ–‰์„ ํ™•์žฅ / ์ถ•์†Œํ•˜๋ฉด ์ถ•์†Œ ๋œ ํ–‰์˜ ์ˆ˜๋Š” ํ™•์žฅ ๋œ ํ–‰์˜ ์ˆ˜์™€ ๋™์ผํ•ฉ๋‹ˆ๋‹ค. ๋ฆฌ ํŠธ๋ž™ํŠธ๋ฅผ ๋‹ค์‹œ ํ™•์žฅํ•˜๋ฉด ์ˆซ์ž๊ฐ€ ์ ˆ๋ฐ˜์œผ๋กœ ๋Š˜์–ด๋‚ฉ๋‹ˆ๋‹ค.
    (์ฆ‰, 30 ๊ฐœ ํ–‰์ด ์ทจ์†Œ๋จ-> 10 ๊ฐœ ํ™•์žฅ ๋จ-> ์ทจ์†Œ๋จ ํด๋ฆญ-> 10 ๊ฐœ ํ–‰์ด ์ทจ์†Œ๋จ-> ํ™•์žฅ ํด๋ฆญ-> 3 ๊ฐœ ํ–‰ ํ™•์žฅ ๋จ-> ์ทจ์†Œ ํด๋ฆญ-> 3 ๊ฐœ ํ–‰ ์ทจ์†Œ๋จ).

JSON.parse (JSON.stringify (data)) ํ•ดํ‚น์œผ๋กœ ๋‹ค๋ฅด์ง€๋งŒ ๋™์ผํ•œ ๊ฐ์ฒด๋ฅผ ์ œ๊ณตํ•˜์—ฌ itemData๋ฅผ ๋‹ค์‹œ๋กœ๋“œํ•˜๋ ค๊ณ ํ–ˆ์Šต๋‹ˆ๋‹ค. ๋ถˆ์šด :-(

๋‚˜๋Š” ๋†’์ด์˜ ์˜ค์‚ฐ์„ ์˜์‹ฌํ•œ๋‹ค. ์ด ๋ฌธ์ œ๋ฅผ ๊ทน๋ณต ํ•  ์•„์ด๋””์–ด๊ฐ€ ์žˆ์Šต๋‹ˆ๊นŒ?

codesandbox ์˜ˆ์ œ๋ฅผ ๊ณต์œ ํ•ด ์ฃผ์‹œ๊ฒ ์Šต๋‹ˆ๊นŒ? ๋น„์Šทํ•œ ์ผ์„ํ•ด์•ผ ์šฐ๋ฆฌ๊ฐ€ ์„œ๋กœ ๋„์šธ ์ˆ˜ ์žˆ์„์ง€๋„ ๋ชฐ๋ผ

@vtripolitakis ๋ฐฉ๊ธˆ ํ™•์žฅ ๊ฐ€๋Šฅํ•œ ํ–‰์ด ์žˆ๋Š” ํ† ๋ก  ๋งํฌ์ž…๋‹ˆ๋‹ค.

@carlosagsmendes ๊ฐ์‚ฌํ•ฉ๋‹ˆ๋‹ค.ํ•˜์ง€๋งŒ DynamicSizeList ์‚ฌ์šฉํ•จ์— ๋”ฐ๋ผ ์ œ ์‚ฌ๋ก€ ์—ฐ๊ตฌ๋Š” ์•ฝ๊ฐ„ ๋‹ค๋ฆ…๋‹ˆ๋‹ค. :-(

๊ทธ๋ž˜์„œ ๋ฌธ์ œ์˜ ์›์ธ์„ ์ฐพ์•˜์Šต๋‹ˆ๋‹ค.
state.scrollOffset ์—์„œ ์Œ์ˆ˜ ๊ฐ’์„ ์‚ฌ์šฉํ–ˆ์Šต๋‹ˆ๋‹ค.

src/DynamicSizeList.js ์—์„œ 299 ํ–‰์— ๋‹ค์Œ ์ฝ”๋“œ๋ฅผ ์ถ”๊ฐ€ํ•ด์•ผํ•ฉ๋‹ˆ๋‹ค.

if (sizeDeltaForStateUpdate < 0) {
          sizeDeltaForStateUpdate = 0;
        }

ํ  .. ํ•œ๋ˆˆ์— ์ˆ˜์ •์ด ์˜ณ์„ ๊ฑฐ๋ผ๊ณ ๋Š” ์ƒ๊ฐํ•˜์ง€ ๋ชปํ–ˆ์Šต๋‹ˆ๋‹ค. ํฌ๊ธฐ ๋ธํƒ€๋Š” ํ•ฉ๋ฒ•์ ์œผ๋กœ ์Œ์ˆ˜ ์ผ ์ˆ˜ ์žˆ์Šต๋‹ˆ๋‹ค.

state.scrollOffset ๊ฐ’์ด ์—…๋ฐ์ดํŠธ๋˜๋Š” ๊ณณ ์ฃผ๋ณ€์— ๊ฒฝ๋น„์› ( Math.max(0, prevState.scrollOffset + sizeDeltaForStateUpdate) )์ด ์žˆ์–ด์•ผํ• ๊นŒ์š”?

์•ˆ๋…•ํ•˜์„ธ์š”, ์ œ ์ผ€์ด์Šค๋ฅผ ๋””๋ฒ„๊น…ํ–ˆ์„ ๋•Œ sizeDeltaTotal ์€ ์Œ์ˆ˜ ๊ฐ’์„ ์ทจํ•˜๊ณ  ๊ทธ์— ๋”ฐ๋ผ sizeDeltaForStateUpdate ์Œ์ˆ˜๋ฅผ ๋งŒ๋“ค์–ด ์ƒํƒœ ์—…๋ฐ์ดํŠธ ํ›„ ์Œ์ˆ˜ state.scrollOffset ์‚ฐ์ถœํ–ˆ์Šต๋‹ˆ๋‹ค.

์ด๊ฒƒ์€ ํ•ญ๋ชฉ์„ ํ™•์žฅ ๋ฐ ์ถ•์†Œ ํ•œ ๋‹ค์Œ scrollOffset 0 ๋ฐ ๋ฐฉํ–ฅ backwards ์„ ์‚ฌ์šฉํ•˜์—ฌ ๋งจ ์œ„๋กœ ์Šคํฌ๋กคํ–ˆ์„ ๋•Œ ๋ฐœ์ƒํ–ˆ์Šต๋‹ˆ๋‹ค. ๊ทธ๋Ÿฐ ๋‹ค์Œ ๋ช‡ ๋ฒˆ ํ™•์žฅ ๋ฐ ์ถ•์†Œํ•˜๋ฉด ๋„ค๊ฑฐํ‹ฐ๋ธŒ๋ฅผ ์–ป์—ˆ์Šต๋‹ˆ๋‹ค.
์˜ˆ, ๊ท€ํ•˜์˜ ์ œ์•ˆ์€ ๋˜‘๊ฐ™์ด ์ข‹์„ ๊ฒƒ์ž…๋‹ˆ๋‹ค. ~ ์ง€๊ธˆ ํ…Œ์ŠคํŠธ ์ค‘์ž…๋‹ˆ๋‹ค. ~ ์ œ๋Œ€๋กœ ์ž‘๋™ํ•ฉ๋‹ˆ๋‹ค.

@marcneander ๋ฒ„์ „ 1.4.0-alpha.1 ์‚ฌ์šฉํ•ด๋ณด๊ธฐ

๋ชฉ๋ก์ด ์ˆจ๊ฒจ์ ธ์žˆ์„ ๋•Œ ํฌ๊ธฐ ์กฐ์ • ์ด๋ฒคํŠธ๋ฅผ ๋ฌด์‹œํ•˜๋Š” ๊ฒƒ๊ณผ ๊ด€๋ จํ•˜์—ฌ https://github.com/piecyk/react-window/commit/acfd88822156611cfd38872acdafbbefd2d0f78f
@bvaughn ๋‹น์‹ ์€ ์–ด๋–ป๊ฒŒ ์ƒ๊ฐํ•˜์‹ญ๋‹ˆ๊นŒ?

์ฑ„ํŒ… ์ƒ์ž ์Šคํƒ€์ผ ์•ฑ์—์„œ ์ž๋™ ์Šคํฌ๋กค์„ ์ถ”๊ฐ€ํ•˜๋ ค๊ณ ํ•˜๋Š”๋ฐ DynamicSizeList does not support scrolling to items that have not yet measured. scrollToItem() was called with index 111 but the last measured item was 110. ๋ฌธ์ œ๊ฐ€ ๋ฐœ์ƒํ•ฉ๋‹ˆ๋‹ค.

scrollToItem(items.length-1) ์—์„œ componentDidUpdate scrollToItem(items.length-1) ๋กœ ์ „ํ™”ํ•˜๋ ค๊ณ ํ•ฉ๋‹ˆ๋‹ค

์˜๋„ ๋œ ๋™์ž‘์ž…๋‹ˆ๊นŒ?

์˜ˆ, ์•„๋งˆ๋„ ๊ทธ๋Ÿฐ ๊ฒƒ์ด @piecyk ์ž‘๋™ ํ•  ์ˆ˜ ์žˆ์Šต๋‹ˆ๋‹ค ๐Ÿ‘

์˜๋„ ๋œ ๋™์ž‘์ž…๋‹ˆ๊นŒ?

@xaviergmail ์ฒ˜๋Ÿผ ๋“ค๋ฆฌ์ง€ ์•Š์Šต๋‹ˆ๋‹ค. ๋ฒ„๊ทธ ์ผ ์ˆ˜๋„ ์žˆ์Šต๋‹ˆ๋‹ค.

์•ˆ๋…•ํ•˜์„ธ์š” @bvaughn ์ด ๋ฌธ์ œ๋ฅผ ํ•ด๊ฒฐํ•˜๋ ค๋Š” ๊ฒƒ์€ ์•„๋‹ˆ์ง€๋งŒ ์—ฌ๊ธฐ์„œ ๋„์›€์ด ๋  ์ˆ˜์žˆ๋Š” Flex 4 DataGrid ๋‚ด๋ถ€์˜ ๊น”๋”ํ•œ ํฌ์†Œ ๋ฐฐ์—ด ๊ตฌํ˜„ ์ด ์žˆ๋‹ค๊ณ  ๋งํ•˜๊ณ  ์‹ถ์—ˆ์Šต๋‹ˆ๋‹ค. ๋‚˜๋Š” Flash๊ฐ€ : -1 :๋ผ๋Š” ๊ฒƒ์„ ์•Œ๊ณ  ์žˆ์ง€๋งŒ, Flex์˜ ๋งˆ์ง€๋ง‰ ๋ฒ„์ „์€ ์‹ค์ œ๋กœ ๊ฝค ํ›Œ๋ฅญํ•œ ๊ฐ€์ƒํ™” ๋ ˆ์ด์•„์›ƒ ์—”์ง„์„ ๊ฐ€์ง€๊ณ ์žˆ์—ˆ์Šต๋‹ˆ๋‹ค. ์™œ๋ƒํ•˜๋ฉด Flash :-)

LinearLayoutVector๋Š” ๋‹จ์ผ ์ฐจ์›์—์„œ ํ•ญ๋ชฉ ์ธ๋ฑ์Šค์™€ ํ”ฝ์…€ ์œ„์น˜ ๊ฐ„์˜ ๋งคํ•‘์„์œ„ํ•œ ํฌ์†Œ ๋ฐฐ์—ด์ž…๋‹ˆ๋‹ค. ์„ธ ๊ฐ€์ง€ ๊ธฐ๋ณธ ์ž‘์—…์€ ๋‹ค์Œ๊ณผ ๊ฐ™์Šต๋‹ˆ๋‹ค.

interface LinearLayoutVector {
   start: (index) => position;
     end: (index) => position;
  indexOf: (position) => index;
}

๋‚ด๋ถ€์ ์œผ๋กœ ํ•ญ๋ชฉ ์œ„์น˜๋ฅผ ์ €์žฅํ•˜๊ธฐ ์œ„ํ•ด 2์˜ ๊ฑฐ๋“ญ ์ œ๊ณฑ์œผ๋กœ ๋ฒ„ํ‚ท์„ ํ• ๋‹นํ•ฉ๋‹ˆ๋‹ค (ํŠน์ • ํŒŒ์›Œ๋Š” ๋” ํฌ๊ฑฐ๋‚˜ ๋” ์ž‘์€ ํ•ญ๋ชฉ ํฌ๊ธฐ๋ฅผ ๋” ์ž˜ ์ˆ˜์šฉํ•˜๋„๋ก ์กฐ์ •ํ•  ์ˆ˜ ์žˆ์Œ). ์ด๋ฅผ ํ†ตํ•ด ์ผ์ • ์‹œ๊ฐ„ O (1) index -> position ์กฐํšŒ ๋ฐ position -> index ์กฐํšŒ๋ฅผ์œ„ํ•œ ํšจ์œจ์ ์ธ ์„ ํ˜• ๋ธ”๋ก ์Šค์บ”์ด ๊ฐ€๋Šฅํ•ฉ๋‹ˆ๋‹ค. ํŒจ๋”ฉ, ๊ฐ„๊ฒฉ, ๊ธฐ๋ณธ ํฌ๊ธฐ ๋ฐ ์ž„์˜ ์•ก์„ธ์Šค ์‚ฝ์ž…, ์ œ๊ฑฐ ๋ฐ ์—…๋ฐ์ดํŠธ๋ฅผ ์ง€์›ํ•ฉ๋‹ˆ๋‹ค.

์•ฝ 6 ๋…„ ์ „ ๋ชจ๋ฐ”์ผ ์šฉ ๊ฐ€์ƒํ™” ๋œ UI๋ฅผ ๋งŽ์ด ํ•  ๋•Œ JS๋กœ ํฌํŒ…ํ–ˆ์Šต๋‹ˆ๋‹ค . ๊ฐ€๋…์„ฑ์„ ์œ„ํ•ด ES6 ์—…๋ฐ์ดํŠธ๋ฅผ ์‚ฌ์šฉํ•  ์ˆ˜ ์žˆ์œผ๋ฉฐ ์œ ํ˜• ๋ฐฐ์—ด๋กœ ์ „ํ™˜ํ•˜์—ฌ ๋” ๋งŽ์€ ์†๋„๋ฅผ ์งค ์ˆ˜ ์žˆ์ง€๋งŒ ๊ธฐ๋ณธ ๋…ผ๋ฆฌ๋Š” ๊ฑด์ „ํ•ฉ๋‹ˆ๋‹ค.

LLV๋กœ CellSizeAndPositionManager ์˜ ๋‚ด๋ถ€๋ฅผ ์ „ํ™˜ ํ•œ ๋ช‡ ์ฃผ ์ „์— ๋ฐ˜์‘ ๊ฐ€์ƒํ™”๋ฅผ ์œ„ํ•œ react-window ์— ์œ ์‚ฌํ•œ PR์„ ์ œ์ถœํ•ด ๋“œ๋ฆฌ๊ฒ ์Šต๋‹ˆ๋‹ค.

์•ˆ๋…•ํ•˜์„ธ์š” @trxcllnt ๐Ÿ‘‹

PR ๊ณต์œ ์— ๊ด€์‹ฌ์ด ์žˆ์œผ์‹œ๋ฉด ๊ธฐ๊บผ์ด ์‚ดํŽด ๋ณด๊ฒ ์Šต๋‹ˆ๋‹ค. issues/6 ๋ธŒ๋žœ์น˜ (WIP PR # 102)๋ฅผ ์ƒ๋Œ€๋กœ ์ด๊ธธ ์ˆ˜ ์žˆ์Šต๋‹ˆ๋‹ค.

ํ•œ๋ˆˆ์— linear-layout-vector ์€ (๋Š”) ํ…Œ์ŠคํŠธ๊ฐ€ ์—†๊ฑฐ๋‚˜ ๋„ˆ๋ฌด ๋งŽ์ด ์‚ฌ์šฉ๋˜๋Š” ๊ฒƒ ๊ฐ™์ง€ ์•Š๊ธฐ ๋•Œ๋ฌธ์— ์ดˆ๊ธฐ์— ์•ฝ๊ฐ„์˜ ๊บผ๋ฆผ์ด ์žˆ์—ˆ์ง€๋งŒ ์—ฌ์ „ํžˆ ์‚ดํŽด๋ณผ ์˜ํ–ฅ์ด ์žˆ์Šต๋‹ˆ๋‹ค. ๋˜ํ•œ uglified + minified ํ›„ ๋ฒˆ๋“ค์— ์ถ”๊ฐ€๋˜๋Š” ๋ฌด๊ฒŒ๋ฅผ ํ™•์ธํ•˜๊ณ  ์‹ถ์ง€๋งŒ ๋„ˆ๋ฌด ๋งŽ์ด ์ถ”๊ฐ€ ๋  ๊ฒƒ์œผ๋กœ ์˜ˆ์ƒํ•˜์ง€ ์•Š์Šต๋‹ˆ๋‹ค. ๐Ÿ˜„

@bvaughn ๋•€์ด

๋Œ“๊ธ€์„ ๋‹ฌ๊ณ  ๋‚˜์„œ https://github.com/trxcllnt/virt-list์— ๋Œ€ํ•œ ํฌํŠธ ์ž‘์—…์„ ์ˆ˜ํ–‰ ํ•œ ๋ฐ๋ชจ๋ฅผ ๊ธฐ์–ตํ–ˆ์Šต๋‹ˆ๋‹ค

@bvaughn ์ง€๋‚œ 1 ๋…„ ๋™์•ˆ issues / 6 ๋ธŒ๋žœ์น˜์—์„œ ์ง„ํ–‰๋œ ๋ชจ๋“  ์ž‘์—…์— ๊ฐ์‚ฌ๋“œ๋ฆฝ๋‹ˆ๋‹ค!
ํ˜„์žฌ ^1.6.0-alpha.1 ํ…Œ์ŠคํŠธ ์ค‘์ด๋ฉฐ ํ•ด๋‹น ๋ฒ„์ „์œผ๋กœ ํ”„๋กœ๋•์…˜์œผ๋กœ ๋ฐฐ์†ก ํ•  ๊ณ„ํš์ž…๋‹ˆ๋‹ค.

์ด ๋ฌธ์ œ๋ฅผ๋ณด๊ณ ์žˆ๋Š” ๋‹ค๋ฅธ ์‚ฌ๋žŒ์„ ์œ„ํ•ด ์ƒˆ๋กœ์šด DynamicSizeList ๋กœ ์ž‘์—…ํ•˜๊ธฐ ์œ„ํ•ด ํ•„์š”ํ•œ ์ž‘์—…์„ ๊ฒŒ์‹œํ•˜๊ณ  ์ง€์ ์—์„œ ์ตœ์‹  ๋ฒ„์ „์„ ์‚ฌ์šฉํ•˜๋Š” ๊ฒƒ์œผ๋กœ ์ƒ๊ฐํ–ˆ์Šต๋‹ˆ๋‹ค.

์œ„์— ๋งํฌ ๋œ ๋ฌธ์„œ์™€ issues / 6 ๋ธŒ๋žœ์น˜ ์—์„œ ์ƒ์„ฑ ๋œ ๋ฌธ์„œ๋ฅผ

Warning: Function components cannot be given refs. Attempts to access this ref will fail. Did you mean to use React.forwardRef()?

๊ทธ๋ž˜์„œ ์ˆ˜์ •์€ ๋‹น์‹ ์ด ํ…Œ์ŠคํŠธ ์—์„œํ•˜๋Š” ์ผ์„ ๋ชจ๋ฐฉํ•˜๊ณ  ...

import { DynamicSizeList as List } from 'react-window';
import AutoSizer from 'react-virtualized-auto-sizer';

// in constructor(props) for handling scrolling
this.listRef = React.createRef();

// in render()
const allItems = [...];
const Renderer = ({ forwardedRef, style, index, ...rest }) => (
  <div ref={forwardedRef} style={style}>
    <MyCoolComponent index={index} otherProps={otherPropsBasedOnAllItems} />
  </div>
);

const RefForwarder = React.forwardRef((props, ref) => (
  <Renderer forwardedRef={ref} {...props} />
));

return <div style={{ display: 'flex', flexDirection: 'column', height: '100%' }}>
  <div style={{ flexGrow: 0, flexShrink: 0, width: '100%', position: 'sticky', top: 0, zIndex: zIndexHideLayers }}>
    <MyCoolComponentThatControlsScrolling listRef={this.listRef} />
  </div>
  <div style={{ flex: 1, width: '100%' }}>
    <AutoSizer>
      {({ height, width }) => (
        <List ref={this.listRef} itemCount={allItems.length} width={width} height={height}>
          {RefForwarder}
        </List>
      )}
    </AutoSizer>
  </div>
</div>;

๋‚ด ์˜ˆ์ œ์—๋Š” ํ•ด๋‹น ๋ฌธ์„œ ํŽ˜์ด์ง€์—์„œ ์›ํ•˜๋Š” ๊ฒƒ๋ณด๋‹ค ๋” ๋งŽ์€ ๊ฒƒ์ด ํฌํ•จ๋˜์–ด ์žˆ์ง€๋งŒ ๋ฌธ์„œ ์—…๋ฐ์ดํŠธ๊ฐ€ ๋” ์‰ฌ์›Œ์ง€๊ธฐ๋ฅผ ๋ฐ”๋ž๋‹ˆ๋‹ค.

ํ˜„์žฌ ๋ฒ„์ „์˜ ๋ธŒ๋žœ์น˜์— ๋Œ€ํ•œ ํ”ผ๋“œ๋ฐฑ?
๐Ÿ’ฏ ์ž˜ ์ž‘๋™ํ•ฉ๋‹ˆ๋‹ค
๐ŸŽ‰ ๋ชจ๋“  ์ž‘์—…์— ๋‹ค์‹œ ํ•œ ๋ฒˆ ๊ฐ์‚ฌ๋“œ๋ฆฝ๋‹ˆ๋‹ค!

ํŽธ์ง‘ : DynamicSizeList ๋Š”์ด ๋ผ์ด๋ธŒ๋Ÿฌ๋ฆฌ๋ฅผ ์ง€๊ธˆ ์‚ฌ์šฉํ•˜๊ธฐ ์‰ฝ๊ฒŒ ๋งŒ๋“ญ๋‹ˆ๋‹ค.

์„ธ๋ถ€ ์ •๋ณด๋ฅผ ๊ณต์œ ํ•ด ์ฃผ์…”์„œ ๊ฐ์‚ฌํ•ฉ๋‹ˆ๋‹ค! ์ด ๋ฌธ์ œ๋ฅผ ๋‹ค์‹œ ์ฐพ์„ ์ˆ˜์žˆ๋Š” ๋Œ€์—ญํญ์ด ํ™•๋ณด๋˜๋ฉด ์ž์„ธํžˆ ์‚ดํŽด ๋ณด๊ฒ ์Šต๋‹ˆ๋‹ค.

์ด ์ ‘๊ทผ ๋ฐฉ์‹ ์€ ์ด๋ฒˆ ํ˜ธ์˜ ์›๋ž˜ ์ œ์•ˆ๊ณผ ํ•จ๊ป˜ ์‚ฌ์šฉํ•  ์ˆ˜ ์žˆ๋‹ค๊ณ  ์ƒ๊ฐ

ํ•ญ๋ชฉ์˜ ์ด์ „ ํฌ๊ธฐ๋ฅผ ์‚ฌ์šฉํ•˜๋Š” ๋Œ€์‹  ์˜ˆ์ƒ ํฌ๊ธฐ๋ฅผ ์‚ฌ์šฉํ•˜๊ณ  ๋ˆ„๊ตฐ๊ฐ€๊ฐ€ ์Šคํฌ๋กค ํ•  ๋•Œ ์‹ค์ œ ํฌ๊ธฐ๋กœ ๋‹ค๋“ฌ์„ ์ˆ˜ ์žˆ์Šต๋‹ˆ๋‹ค. (์ด์ „์— ์ธก์ • ๋œ ํฌ๊ธฐ๊ฐ€ ๋” ์ •ํ™•ํ•  ๊ฐ€๋Šฅ์„ฑ์ด ์žˆ๋‹ค๋Š” ์‚ฌ์‹ค์„ ์ œ์™ธํ•˜๊ณ ๋Š” "์ด์ „์— ์ธก์ • ๋œ ํฌ๊ธฐ"์™€ "์˜ˆ์ƒ ํฌ๊ธฐ"์‚ฌ์ด์— ์ค‘์š”ํ•œ ์ฐจ์ด๊ฐ€ ์—†๋‹ค๊ณ  ์ƒ๊ฐํ•ฉ๋‹ˆ๋‹ค. ๊ทธ๋ž˜๋„ ํ—ˆ์šฉ ํ•  ์ˆ˜ ์žˆ๊ธฐ ๋•Œ๋ฌธ์— ์ด๊ฒƒ์€ ํ—ˆ์šฉ ๊ฐ€๋Šฅํ•œ ์ƒ์ถฉ ๊ด€๊ณ„ ์ผ ์ˆ˜ ์žˆ์Šต๋‹ˆ๋‹ค. ์šฐ๋ฆฌ๋Š” ์ด์ „์— ์˜จ ๊ฒƒ์„ ๋ Œ๋”๋งํ•˜์ง€ ์•Š๊ณ  ๋ฐ์ดํ„ฐ์˜ ์ž„์˜์˜ ์œ„์น˜๋กœ ์ ํ”„ ํ•  ์ˆ˜ ์žˆ์œผ๋ฉฐ _ ๊ทธ๋ฆฌ๊ณ  _ ํ•ญ๋ชฉ ํฌ๊ธฐ ์บ์‹œ๋ฅผ ์œ ์ง€ํ•˜์ง€ ์•Š์•„๋„๋ฉ๋‹ˆ๋‹ค.)

์ด๊ฒƒ์€ ์Šคํฌ๋กค ๊ณ ์ • ๋ฌธ์ œ๋ฅผ ์ƒ๋‹นํžˆ ๋‹จ์ˆœํ™” ํ•  ์ˆ˜ ์žˆ๋‹ค๊ณ  ์ƒ๊ฐํ•ฉ๋‹ˆ๋‹ค. ์ดˆ๊ธฐ ์ ํ”„ (์„ค๋ช… ๋œ๋Œ€๋กœ)๋ฅผ ์ˆ˜ํ–‰ ํ•œ ๋‹ค์Œ "์ด์ „"(์œ„ ๋˜๋Š” ์™ผ์ชฝ)์ด ๋ชจ๋‘ ์˜ˆ์ƒ ํฌ๊ธฐ ์ธ ๊ฒƒ์ฒ˜๋Ÿผ ๊ฐ€์žฅ ํ•  ์ˆ˜ ์žˆ์Šต๋‹ˆ๋‹ค. ๊ทธ๋Ÿฐ ๋‹ค์Œ ์Šคํฌ๋กคํ•˜๋ฉด์„œ ๋‹ค๋“ฌ์Šต๋‹ˆ๋‹ค.

์ž‘๋™ ํ•  ์ˆ˜ ์žˆ์„๊นŒ์š”?

@bvaughn ์ด๋ ‡๊ฒŒํ•˜๋ฉด ์ฑ„ํŒ…์ฒ˜๋Ÿผ ์ฒ˜์Œ์— "ํ•˜๋‹จ"์œผ๋กœ ์Šคํฌ๋กคํ•˜์—ฌ @xaviergmail ์ด ํ•ด๊ฒฐ ํ•œ ๋ฌธ์ œ๊ฐ€ ํ•ด๊ฒฐ๋ฉ๋‹ˆ๊นŒ? ์ž‘๋™ํ•˜์ง€ ์•Š๋Š” ์˜ˆ์ œ์˜ codesandbox๋ฅผ ๋งŒ๋“ค์—ˆ์Šต๋‹ˆ๋‹ค. ๊ทธ๋ ‡์ง€ ์•Š์€ ๊ฒฝ์šฐ ํ•ด๊ฒฐ ๋ฐฉ๋ฒ•์ด ์žˆ์Šต๋‹ˆ๊นŒ?

https://codesandbox.io/s/vr648ywy3

์ด ๋ฌธ์ œ์— ๋Œ€ํ•œ ์˜๊ฒฌ์€ ๋ฌธ์ œ ํ•ด๊ฒฐ์ด ์•„๋‹Œ API ํ† ๋ก ์— ์ค‘์ ์„ ๋‘๋„๋กํ•˜๊ฒ ์Šต๋‹ˆ๋‹ค.

์งˆ๋ฌธ์— ๋Œ€ํ•ด Stack Overflow๋ฅผ ์ œ์•ˆํ•ฉ๋‹ˆ๋‹ค.

์ด API์—์„œ resetAfterIndex๋ฅผ ๋…ธ์ถœ ํ•  ์ˆ˜ ์žˆ์Šต๋‹ˆ๊นŒ? DynamicSizeList์—์„œ ์ถ”๊ฐ€, ํŽธ์ง‘ ๋ฐ ์ œ๊ฑฐํ•˜๊ณ  ์ตœ์†Œํ•œ ์ˆ˜์ง‘ ํ•  ์ˆ˜์žˆ๋Š” ํ•ญ๋ชฉ์—์„œ ๋†’์ด๋ฅผ ์ˆ˜์ •ํ•˜๊ธฐ ์œ„ํ•ด ํ˜ธ์ถœํ•˜๋Š” ๋ฉ”์„œ๋“œ๊ฐ€ ๋  ๊ฒƒ์ž…๋‹ˆ๋‹ค. ๊ทธ๋ ‡์ฃ ?

@bvaughn ์€ ์ฃผ๋ง ๋™์•ˆ ์•ต์ปค ์ธ๋ฑ์Šค๊ฐ€์žˆ๋Š” ํ•ญ๋ชฉ์„ ๋ฐฐ์น˜ํ•˜๊ณ  ๋ชฉ๋ก์„ ์Šคํฌ๋กคํ•˜์—ฌ ์‚ฌ์šฉ์ž๊ฐ€๋ณด๊ณ ์žˆ๋Š” ๋‚ด์šฉ์„ ์ •๋ ฌํ•˜๋Š” ์•„์ด๋””์–ด๋ฅผ ๊ฐ€์ง€๊ณ  ๋†€์•˜์Šต๋‹ˆ๋‹ค. ์บ์‹œ๊ฐ€ ์ž‘๋™ํ•˜๋Š” ๋ฐฉ์‹์„ ๋ณ€๊ฒฝํ•ด์•ผํ•ฉ๋‹ˆ๋‹ค (์ด wip์—์„œ๋Š” ํ•ญ์ƒ ์ง€์›Œ์ง) ... ์–ด๋–ป๊ฒŒ ์ƒ๊ฐํ•˜์‹ญ๋‹ˆ๊นŒ?

poc ๊ตฌํ˜„ https://github.com/piecyk/react-window/pull/2/files
๋‹ค์Œ์€ ๋ธŒ๋žœ์น˜ ๋นŒ๋“œ๋ฅผ ์‹คํ–‰ํ•˜๋Š” ์ฝ”๋“œ ์ƒŒ๋“œ ๋ฐ•์Šค์ž…๋‹ˆ๋‹ค.
https://codesandbox.io/s/4x1q1n6nn9

์–ด-์˜ค ํŒŒ์ด์–ด ํญ์Šค๋Š” ํฌ๋กฌ์ฒ˜๋Ÿผ ๋น ๋ฅธ ์Šคํฌ๋กค์„ ํ•  ๋•Œ ๋ Œ๋”๋ง์„ ๋”ฐ๋ผ ์žก์„ ์ˆ˜ ์—†์Šต๋‹ˆ๋‹ค ๐Ÿคทโ€โ™‚๏ธ

์ฑ„ํŒ… ์ƒ์ž ์Šคํƒ€์ผ ์•ฑ์—์„œ ์ž๋™ ์Šคํฌ๋กค์„ ์ถ”๊ฐ€ํ•˜๋ ค๊ณ ํ•˜๋Š”๋ฐ DynamicSizeList does not support scrolling to items that have not yet measured. scrollToItem() was called with index 111 but the last measured item was 110. ๋ฌธ์ œ๊ฐ€ ๋ฐœ์ƒํ•ฉ๋‹ˆ๋‹ค.

scrollToItem(items.length-1) ์—์„œ componentDidUpdate scrollToItem(items.length-1) ๋กœ ์ „ํ™”ํ•˜๋ ค๊ณ ํ•ฉ๋‹ˆ๋‹ค

์˜๋„ ๋œ ๋™์ž‘์ž…๋‹ˆ๊นŒ?

์กฐ๊ธˆ ๋Šฆ์—ˆ์ง€๋งŒ ์ด ๋ฐ˜์‘ ํ›„ํฌ๋กœ ๊ทธ ๋ฌธ์ œ๋ฅผ ํ•ด๊ฒฐํ•˜๋ ค๊ณ ํ•ฉ๋‹ˆ๋‹ค.

์ตœ์„ ์˜ ํ•ด๊ฒฐ์ฑ…์€ ์•„๋‹ˆ์ง€๋งŒ ์—ฌ์ „ํžˆ ์ž‘์—… ์ค‘์ž…๋‹ˆ๋‹ค. ์ข€ ๋” ์ผ๋ฐ˜์ ์ด๊ณ  ๊ฐ„๋‹จํ•˜๊ฒŒ ๋งŒ๋“ค๊ณ  ํŒจํ‚ค์ง€๋ฅผ ๋งŒ๋“ค ์ˆ˜ ์žˆ์„๊นŒ์š”?

์ด๊ฒƒ์ด ์ง€๊ธˆ ์–ด๋–ป๊ฒŒ ์ž‘๋™ํ•˜๋Š”์ง€ ๋ณด์—ฌ์ฃผ๋Š” GIF :
https://cl.ly/87ca5ac94deb

์ด ์ฑ„ํŒ…๊ณผ ๊ฐ™์€ ํ–‰๋™์— ๋Œ€ํ•œ ํ•ด๊ฒฐ์ฑ…์— ๋Œ€ํ•ด ์ด์•ผ๊ธฐํ•˜๊ธฐ ์œ„ํ•ด ์ƒˆ๋กœ์šด ๋ฌธ์ œ๋ฅผ ์—ด โ€‹โ€‹์ˆ˜ ์žˆ์Šต๋‹ˆ๊นŒ?

uh-oh firefox๋Š”์ด ์ ‘๊ทผ ๋ฐฉ์‹์„ ์‚ฌ์šฉํ•˜์—ฌ ํฌ๋กฌ์ฒ˜๋Ÿผ ๋น ๋ฅธ ์Šคํฌ๋กค๋ง์„ ํ•  ๋•Œ ๋ Œ๋”๋ง์„ ๋”ฐ๋ผ๊ฐˆ ์ˆ˜ ์—†์Šต๋‹ˆ๋‹ค.

Firefox Nightly ๋ฒ„์ „ 68์—์„œ ์ž‘๋™ํ•˜๋Š” ๊ฒƒ ๊ฐ™์Šต๋‹ˆ๋‹ค.

@bvaughn ํ”ผ๋“œ๋ฅผ ์ƒ์„ฑํ•˜๊ธฐ ์œ„ํ•ด InfiniteLoader ๋ฐ Autosizer ๊ตฌ์„ฑ ์š”์†Œ์™€ ํ•จ๊ป˜ DynamicSizeList๋ฅผ ์‚ฌ์šฉํ•˜๊ณ  ์žˆ์Šต๋‹ˆ๋‹ค. ๋‚˜๋Š” ๋‚ด๊ฐ€ ์ง€๊ธˆ๊นŒ์ง€ ๋ณธ ๊ฒƒ์„ ์ข‹์•„ํ•œ๋‹ค.

API ๋ฐ ๋™์ž‘ ์ธก๋ฉด์—์„œ :

  1. FixedSizeList์—์žˆ๋Š” ๋ฐฉ์‹์œผ๋กœ itemKey ์ฝœ๋ฐฑ์—์„œ ๋‘ ๋ฒˆ์งธ ์ธ์ˆ˜๋กœ ๋ฐ์ดํ„ฐ ๊ฐ์ฒด๋ฅผ ๊ฐ€์ ธ์˜ฌ ์ˆ˜ ์žˆ์Šต๋‹ˆ๊นŒ?

  2. ๋ฐ์ดํ„ฐ ๊ฐœ์ฒด๊ฐ€ ํ•„ํ„ฐ๋ง / ์ˆ˜์ • ๋  ๋•Œ ๋‚ด๋ถ€ ์ปจํ…Œ์ด๋„ˆ ๋†’์ด๋ฅผ ์žฌ์„ค์ • ํ•  ์ˆ˜ ์žˆ์Šต๋‹ˆ๊นŒ?

๋‚ด๊ฐ€ ์‚ฌ์šฉํ•˜๊ณ  DynamicSizeList ์—์„œ 1.6.0-alpha.1 ์™€ InfiniteLoader ์ž ์‹œ ๋™์•ˆ ์ง€๊ธˆ๊ณผ๋Š” ํฐ ์ž‘์—…์„ํ•˜๊ณ ์žˆ๋‹ค. ๋ฉ‹์ง„ ๊ธฐ๋Šฅ์— ๊ฐ์‚ฌ๋“œ๋ฆฝ๋‹ˆ๋‹ค!

๊ทธ๋Ÿฌ๋‚˜ ์ด์ œ scrollToItem() ๋ฅผ ์‚ฌ์šฉํ•ด์•ผํ•ฉ๋‹ˆ๋‹ค. ์œ„์˜ ์ฃผ์„๊ณผ ์œ ์‚ฌํ•˜์ง€๋งŒ ์•„์ง ์ธก์ • ๋œ ๊ฒƒ์ด ์ „ํ˜€ ์—†๊ธฐ ๋•Œ๋ฌธ์— ๊ตฌ๋ณ„๋ฉ๋‹ˆ๋‹ค.

DynamicSizeList does not support scrolling to items that yave not yet measured. scrollToItem() was called with index 9 but the last measured item was -1.

๊ธด setTimeout ํ›„์— ์ „ํ™”๋ฅผ ๊ฑธ์–ด ๋ณด์•˜ ๊ธฐ ๋•Œ๋ฌธ์— ํƒ€์ด๋ฐ๊ณผ ๊ด€๋ จ๋œ ๊ฒƒ ๊ฐ™์ง€ ์•Š์Šต๋‹ˆ๋‹ค. ๊ทธ๋ ‡๋‹ค๋ฉด ๊ฐ•์ œ๋กœ ์ธก์ • ํ•  ์ˆ˜ ์žˆ์Šต๋‹ˆ๊นŒ? ์•„๋‹ˆ๋ฉด ํ•ด๊ฒฐ ๋ฐฉ๋ฒ•์ด ์žˆ์Šต๋‹ˆ๊นŒ?

ํŽธ์ง‘ : ์‹ ๊ฒฝ ์“ฐ์ง€ ๋งˆ์‹ญ์‹œ์˜ค, initialScrollOffset ๋‚ด๊ฐ€ ํ•„์š”ํ•œ ๊ฒƒ์„ํ–ˆ์Šต๋‹ˆ๋‹ค.

findDOMNode๋ฅผ ์‚ฌ์šฉํ•˜๋Š” ์ด์œ ๋Š” ๋ฌด์—‡์ž…๋‹ˆ๊นŒ?

@next ๋ธŒ๋žœ์น˜์— ๋Œ€ํ•œ ์œ ํ˜• ์ •์˜๊ฐ€ ์žˆ์Šต๋‹ˆ๊นŒ?

@WillSquire ์•„๋‹ˆ, ๊ทธ๋“ค์€ํ•˜์ง€ ์•Š์Šต๋‹ˆ๋‹ค. ๋˜ํ•œ DefinitelyTyped์˜ @next ํƒœ๊ทธ์—์„œ ๋ฆด๋ฆฌ์Šค ํ•  ์ˆ˜ ์žˆ๋Š”์ง€ ํ™•์‹คํ•˜์ง€ ์•Š์Šต๋‹ˆ๋‹ค (์ž˜๋ชป๋˜์—ˆ์„ ์ˆ˜๋„ ์žˆ์Šต๋‹ˆ๋‹ค). ๋˜ํ•œ API๊ฐ€ ์—ฌ์ „ํžˆ ๋ณ€๊ฒฝ ๋  ์ˆ˜ ์žˆ์œผ๋ฏ€๋กœ์ด ๋ถ„๊ธฐ๊ฐ€ ๋งˆ์นจ๋‚ด ๋ณ‘ํ•ฉ๋˜๊ณ  ์ƒˆ ๋ฒ„์ „์ด ์ถœ์‹œ ๋  ๋•Œ๊นŒ์ง€ ๊ธฐ๋‹ค๋ฆฌ๋Š” ๊ฒƒ์ด ๋” ๋‚˜์„ ๊ฒƒ์ด๋ผ๊ณ  ์ƒ๊ฐํ•ฉ๋‹ˆ๋‹ค.

@bvaughn ๋‚˜๋Š”์ด์—์„œ ์‚ฌ์šฉ ๊ธฐ๊บผ์ด ํ•œ devhub ,ํ•˜์ง€๋งŒ ๋‚œ ํ†ตํ•ฉ์— ํˆฌ์žํ•˜๊ธฐ ์ „์— ๋‹น์‹ ์€ ์ข‹์€ ๋ชจ์–‘์— ์ด๋ฏธ ๋‚˜ ์—ฌ์ „ํžˆ ์ฐจ๋‹จ ๋ฌธ์ œ๊ฐ€ ์žˆ๋‹ค๊ณ  ์ƒ๊ฐํ•ฉ๋‹ˆ๊นŒ?

@brunolemos 102

๊ณ„์† ์•Œ๋ ค์ค˜!

~ ์‚ฌ์šฉํ•˜๋ ค๊ณ ํ–ˆ์ง€๋งŒ ์ง€๊ธˆ๊นŒ์ง€ ์„ฑ๊ณตํ•˜์ง€ ๋ชปํ–ˆ์Šต๋‹ˆ๋‹ค. ~

์ž‘๋™ํ–ˆ์ง€๋งŒ ์„ฑ๋Šฅ์ด ์ข‹์ง€ ์•Š์Šต๋‹ˆ๋‹ค. ๋‚ด ํ•ญ๋ชฉ ๋ Œ๋”๋ง์ด ๋น„์‹ธ๊ฑฐ๋‚˜ ๋‹ค๋ฅธ ๊ฒƒ์ผ ์ˆ˜ ์žˆ์Šต๋‹ˆ๋‹ค.

https://github.com/devhubapp/devhub/pull/152

์ปจํ…Œ์ด๋„ˆ ๋†’์ด๊ฐ€ 100 % ์ธ AutoSizer๋ฅผ ์‚ฌ์šฉํ•  ๋•Œ ์ตœ์‹  ๋ฒ„์ „์—์„œ ๋ฌธ์ œ๊ฐ€ ๋ฐœ์ƒํ•œ ๊ฒƒ ๊ฐ™์Šต๋‹ˆ๋‹ค.

ํŽธ์ง‘ : 100vh ๋ฐ calc ()๋ฅผ ์‚ฌ์šฉํ•˜์—ฌ ํ•ด๊ฒฐ ๋ฐฉ๋ฒ•์„ ์ฐพ์„ ์ˆ˜์žˆ์—ˆ์Šต๋‹ˆ๋‹ค.

๋ญ”๊ฐ€๊ฐ€ ๊ณ ์žฅ ๋‚ฌ์„ ์ˆ˜ ์žˆ์Šต๋‹ˆ๋‹ค

์‹คํ–‰ํ•˜๊ธฐ์—๋Š” ๋„ˆ๋ฌด ๋ชจํ˜ธํ•ฉ๋‹ˆ๋‹ค. ์˜ˆ์ƒ๋˜๋Š” ๋™์ž‘๊ณผ ํ•จ๊ป˜ ์žฌํ˜„์„ ๊ณต์œ  ํ•˜์‹œ๊ฒ ์Šต๋‹ˆ๊นŒ?

1.6.0-alpha.1์˜ DynamicSizeList๋ฅผ ๋‹ค๋ฅธ ํ•„ํ„ฐ์™€ ๋ณต์žกํ•œ ์นด๋“œ๋ณด๊ธฐ์™€ ํ•จ๊ป˜ ์‚ฌ์šฉํ•˜๊ณ  ์žˆ์Šต๋‹ˆ๋‹ค. ๊ทธ๋Ÿฌ๋‚˜ ์šฐ๋ฆฌ๋Š” ๋†’์ด์™€ ๋„ˆ๋น„๋กœ ๊ฐ์‹ธ ์•ผํ•ฉ๋‹ˆ๋‹ค. ๋‚˜๋ฅผ ์œ„ํ•ด ์ž˜ ์ž‘๋™ํ•ฉ๋‹ˆ๋‹ค.

๊ฐ์‚ฌํ•ฉ๋‹ˆ๋‹ค

์•ˆ๋…•ํ•˜์„ธ์š”, DynamicSizeList ์‹œ๋„ํ•˜๊ณ  ์žˆ์ง€๋งŒ ๋ชจ๋“  ํ•ญ๋ชฉ์ด ์„œ๋กœ ์œ„์— ๋ Œ๋”๋ง๋ฉ๋‹ˆ๋‹ค. ์Šคํƒ€์ผ ์†์„ฑ์„ ๋ Œ๋”๋ง ๋œ ํ•ญ๋ชฉ์— ์ „๋‹ฌํ•˜์ง€๋งŒ style ๋ฅผ ๊ธฐ๋กํ•˜๋ฉด height ๊ฐ€ ๊ฐ ํ•ญ๋ชฉ์— ๋Œ€ํ•ด ์ •์˜๋˜์ง€ ์•Š์€ ๊ฒƒ์œผ๋กœ ํ™•์ธ๋ฉ๋‹ˆ๋‹ค. top ๋ฐ left ํ•ญ์ƒ 0 ์ž…๋‹ˆ๋‹ค.
๋‚ด๊ฐ€ ์—ฌ๊ธฐ์„œ ๋ฌด์—‡์„ ๋†“์ณค์Šต๋‹ˆ๊นŒ :-)?

@ graphee-gabriel ๋‹น์‹ ์€ ๋ณต์ œ ์˜ˆ๋ฅผ ๋†“์ณค์Šต๋‹ˆ๋‹ค.

ํ•ญ๋ชฉ์ด ์›๋ž˜ ํฌ๊ธฐ๋กœ ๋ Œ๋”๋ง๋˜๋„๋กํ•˜๊ธฐ ์œ„ํ•ด ์ฒ˜์Œ์—๋Š” ๋†’์ด๋ฅผ ์˜๋„์ ์œผ๋กœ ์ง€์ •ํ•˜์ง€ ์•Š์•˜์Šต๋‹ˆ๋‹ค.

์ข‹์•„, ๋…ผ๋ฆฌ๋ฅผ ์ดํ•ด ํ–ˆ์œผ๋‹ˆ ํ•ญ๋ชฉ์ด ์„œ๋กœ ์œ„์— ๋ Œ๋”๋ง๋˜๋Š” ์ด์œ ๊ฐ€ ์•„๋‹™๋‹ˆ๋‹ค.
๊ฐ€๋Šฅํ•œ ํ•œ ๋งŽ์€ ๋ฐ์ดํ„ฐ๋ฅผ ์ œ๊ณต ํ•  ๊ฒƒ์ž…๋‹ˆ๋‹ค. ์ผ๋ฐ˜์ ์ธ ์‹ค์ˆ˜๋ฅผํ–ˆ๊ฑฐ๋‚˜์ด ๋ฌธ์ œ๋กœ ์ด์–ด์ง€๋Š” ๋ช…๋ฐฑํ•œ ๋‹จ๊ณ„ (์˜ˆ : ์Šคํƒ€์ผ ๊ฐœ์ฒด๋ฅผ ์ „๋‹ฌํ•˜์ง€ ์•Š์Œ)๋ฅผ ๋†“์นœ ๊ฒƒ ๊ฐ™์Šต๋‹ˆ๋‹ค.

Screen Shot 2019-07-07 at 18 08 53

import React from 'react'
import { DynamicSizeList as List } from 'react-window'

import Layout from '../Layout'
import Text from '../Text'
import withScreenDimensions from '../withScreenDimensions'

class ListView extends React.Component {
  state = {
    availableHeight: 0
  }

  componentDidMount() {
    const checkForHeightChange = () => {
      if (this.containerDiv) {
        const { offsetHeight } = this.containerDiv
        if (this.offsetHeight !== offsetHeight) {
          this.offsetHeight = offsetHeight
          this.setState({ availableHeight: offsetHeight })
        }
      }
    }
    checkForHeightChange()
    this.intervalId = setInterval(checkForHeightChange, 10)
  }

  componentWillUnmount() {
    clearInterval(this.intervalId)
  }

  render() {
    const {
      data,
      renderItem,
      emptyText,
      dimensions,
    } = this.props
    const { width } = dimensions
    const { availableHeight } = this.state
    return (
      <Layout
        centerVertical
        style={{
          height: '100%',
        }}>
        {data && data.length > 0 ? (
          <div
            style={{
              display: 'flex',
              flex: 1,
              height: '100%',
              backgroundColor: 'red',
              alignItems: 'stretch',
              justifyContent: 'stretch',
            }}
            ref={ref => this.containerDiv = ref}
          >
            <List
              height={availableHeight}
              itemCount={data.length}
              width={width > 800 ? 800 : width}
            >
              {({ index, style }) => {
                console.log('style', style)
                return (
                  <div style={style}>
                    {renderItem({
                      item: data[index], index
                    })}
                  </div>
                )
              }}
            </List>
          </div>
        ) : (
            <Text bold center padding accent>{emptyText}</Text>
          )}
      </Layout>
    )
  }
}


export default withScreenDimensions(ListView)

์ด๊ฒƒ์„ ๋ณผ ์ˆ˜์žˆ๋Š” ์ฝ”๋“œ ์ƒŒ๋“œ ๋ฐ•์Šค๋ฅผ ๊ณต์œ  ํ•˜์‹œ๊ฒ ์Šต๋‹ˆ๊นŒ?

ํ•ญ๋ชฉ ๋ Œ๋”๋Ÿฌ์— ์ธ๋ผ์ธ ํ•จ์ˆ˜๋ฅผ ์‚ฌ์šฉํ•˜์ง€ ์•Š๋Š” ๊ฒƒ์ด ์ข‹์Šต๋‹ˆ๋‹ค. ๋ถ€๋ชจ๊ฐ€ ๋ Œ๋”๋ง ๋  ๋•Œ๋งˆ๋‹ค ๋ณ€๊ฒฝ๋˜๊ธฐ ๋•Œ๋ฌธ์— ๋ถˆํ•„์š”ํ•œ ๋‹ค์‹œ ๋งˆ์šดํŠธ๊ฐ€ ๋ฐœ์ƒํ•˜๊ธฐ ๋•Œ๋ฌธ์ž…๋‹ˆ๋‹ค. (์ด๊ฒƒ์ด ๋ชจ๋“  ์˜ˆ์ œ๊ฐ€ ์ธ๋ผ์ธ ํ•จ์ˆ˜๋ฅผ ํ”ผํ•˜๋Š” ์ด์œ ์ž…๋‹ˆ๋‹ค.)

@ graphee-gabriel ๋‚˜๋Š” ์ด๊ฒƒ๋„ ๊ฐ€์ง€๊ณ  ์žˆ์—ˆ์ง€๋งŒ ๋ฌธ์„œ๋Š” ๊ทธ๊ฒƒ์„ ์–ธ๊ธ‰ํ•˜์ง€ ์•Š์•˜์ง€๋งŒ ref๋ฅผ๋ฐ›๋Š” ํ–‰ ๊ตฌ์„ฑ ์š”์†Œ๋ฅผ ์ง€์›ํ•ด์•ผํ•ฉ๋‹ˆ๋‹ค.

Row = React.forwardRef(
      (row, ref) => (
        <div ref={ref} style={row.style}>
          {renderItem({
            item: data[row.index],
            index: row.index,
          })}
        </div>
      ),
    )

์•ˆ๋…•ํ•˜์„ธ์š”, ์—ฌ๊ธฐ ์žˆ์Šต๋‹ˆ๋‹ค.

https://codesandbox.io/s/sweet-sea-irxl8?fontsize=14

์˜ˆ, ์‹ค์ œ๋กœ ์ธ๋ผ์ธ ํ•จ์ˆ˜์˜ ๊ฒฝ์šฐ ๋ฐ˜์‘ ์ฐฝ์œผ๋กœ ๋งˆ์ด๊ทธ๋ ˆ์ด์…˜ํ•˜๋ ค๊ณ  ์‹œ๋„ํ•œ ์ •๋ง ์˜ค๋ž˜๋œ ์ฝ”๋“œ์ด๋ฉฐ ์—ฌ๊ธฐ์„œ๋„ ๊ฐœ์„ ํ•˜๋Š” ๋ฐ ์‹œ๊ฐ„์ด ๊ฑธ๋ฆฌ์ง€ ์•Š์•˜์Šต๋‹ˆ๋‹ค.
์˜๊ฒฌ์„ ๋ณด๋‚ด ์ฃผ์…”์„œ ๊ฐ์‚ฌํ•ฉ๋‹ˆ๋‹ค. ์ด ์ƒŒ๋“œ ๋ฐ•์Šค์—์„œ ์ฐพ์€ ๋‚ด์šฉ์„ ์•Œ๋ ค์ฃผ์„ธ์š”.

Annnnnd ์ƒŒ๋“œ ๋ฐ•์Šค๋ฅผํ•˜๊ธฐ ์ „์— @brunolemos ๋ฉ”์‹œ์ง€๋ฅผ ํ™•์ธํ•ด์•ผํ–ˆ์Šต๋‹ˆ๋‹ค.
์ด๊ฒƒ์€ ๋ˆ„๋ฝ ๋œ ๋‹จ๊ณ„์ด๋ฉฐ ๋‚ด ๋ฌธ์ œ๋ฅผ ํ•ด๊ฒฐํ–ˆ์Šต๋‹ˆ๋‹ค. ๊ฐ์‚ฌํ•ฉ๋‹ˆ๋‹ค!

๋˜ ๋‹ค๋ฅธ ๋ฌธ์ œ๊ฐ€ ๋ฐœ์ƒํ•˜์—ฌ @bvaughn์„ ์žฌํ˜„ ํ•  ์ˆ˜ ์žˆ๋„๋ก ์ƒŒ๋“œ ๋ฐ•์Šค๋ฅผ ์—…๋ฐ์ดํŠธํ–ˆ์Šต๋‹ˆ๋‹ค.
์—ฌ๊ธฐ์—์„œ ์ฐพ๊ธฐ : https://codesandbox.io/s/sweet-sea-irxl8

์ด์ œ ๋ชฉ๋ก์€ ์ž˜ ์ž‘๋™ํ•˜์ง€๋งŒ ์ด์ƒํ•˜๊ฒŒ๋„ ์ฝ˜ํ…์ธ ์™€ ํ•จ๊ป˜ ๋Š˜์–ด๋‚˜๊ณ  ๋‹ค์‹œ ์ค„์–ด๋“ค์ง€ ์•Š์Šต๋‹ˆ๋‹ค.

์˜๋ฏธ:

  1. 6 ๊ฐœ ํ•ญ๋ชฉ์„ ํ‘œ์‹œํ•˜๋ฉด ๋๊นŒ์ง€ ์Šคํฌ๋กคํ•˜๋ฉด ๋ชจ๋“  ๊ฒƒ์ด ์ •์ƒ์ž…๋‹ˆ๋‹ค.
  2. ๋‚ด์šฉ์„ ๋ณ€๊ฒฝํ•˜์—ฌ 20 ๊ฐœ ํ•ญ๋ชฉ์„ ํ‘œ์‹œํ•˜๊ณ  ๋๊นŒ์ง€ ์Šคํฌ๋กคํ•˜์‹ญ์‹œ์˜ค.
  3. ์ฝ˜ํ…์ธ ๋ฅผ 6 ๊ฐœ ํ•ญ๋ชฉ์œผ๋กœ ๋‹ค์‹œ ๋ณ€๊ฒฝํ•˜๊ณ  ๋งˆ์ง€๋ง‰ ํ•ญ๋ชฉ๊นŒ์ง€ ์Šคํฌ๋กคํ•˜์ง€๋งŒ ์ด์ „ ์ฝ˜ํ…์ธ  (20 ๊ฐœ ํ•ญ๋ชฉ ๋ฐ์ดํ„ฐ ์ง‘ํ•ฉ)์—์„œ ๋‚จ์•„์žˆ๋Š” ๊ฒƒ์ฒ˜๋Ÿผ ๋ณด์ด๋Š” ๊ณต๋ฐฑ์—์„œ ๊ณ„์† ์Šคํฌ๋กค ํ•  ์ˆ˜ ์žˆ์Šต๋‹ˆ๋‹ค.

๋˜ ๋‹ค๋ฅธ ๋ฌธ์ œ๊ฐ€ ๋ฐœ์ƒํ•˜์—ฌ @bvaughn์„ ์žฌํ˜„ ํ•  ์ˆ˜ ์žˆ๋„๋ก ์ƒŒ๋“œ ๋ฐ•์Šค๋ฅผ ์—…๋ฐ์ดํŠธํ–ˆ์Šต๋‹ˆ๋‹ค.
์—ฌ๊ธฐ์—์„œ ์ฐพ๊ธฐ : https://codesandbox.io/s/sweet-sea-irxl8

์ด์ œ ๋ชฉ๋ก์€ ์ž˜ ์ž‘๋™ํ•˜์ง€๋งŒ ์ด์ƒํ•˜๊ฒŒ๋„ ์ฝ˜ํ…์ธ ์™€ ํ•จ๊ป˜ ๋Š˜์–ด๋‚˜๊ณ  ๋‹ค์‹œ ์ค„์–ด๋“ค์ง€ ์•Š์Šต๋‹ˆ๋‹ค.

์˜๋ฏธ:

  1. 6 ๊ฐœ ํ•ญ๋ชฉ์„ ํ‘œ์‹œํ•˜๋ฉด ๋๊นŒ์ง€ ์Šคํฌ๋กคํ•˜๋ฉด ๋ชจ๋“  ๊ฒƒ์ด ์ •์ƒ์ž…๋‹ˆ๋‹ค.
  2. ๋‚ด์šฉ์„ ๋ณ€๊ฒฝํ•˜์—ฌ 20 ๊ฐœ ํ•ญ๋ชฉ์„ ํ‘œ์‹œํ•˜๊ณ  ๋๊นŒ์ง€ ์Šคํฌ๋กคํ•˜์‹ญ์‹œ์˜ค.
  3. ์ฝ˜ํ…์ธ ๋ฅผ 6 ๊ฐœ ํ•ญ๋ชฉ์œผ๋กœ ๋‹ค์‹œ ๋ณ€๊ฒฝํ•˜๊ณ  ๋งˆ์ง€๋ง‰ ํ•ญ๋ชฉ๊นŒ์ง€ ์Šคํฌ๋กคํ•˜์ง€๋งŒ ์ด์ „ ์ฝ˜ํ…์ธ  (20 ๊ฐœ ํ•ญ๋ชฉ ๋ฐ์ดํ„ฐ ์ง‘ํ•ฉ)์—์„œ ๋‚จ์•„์žˆ๋Š” ๊ฒƒ์ฒ˜๋Ÿผ ๋ณด์ด๋Š” ๊ณต๋ฐฑ์—์„œ ๊ณ„์† ์Šคํฌ๋กค ํ•  ์ˆ˜ ์žˆ์Šต๋‹ˆ๋‹ค.

๊ฐ™์€ ๋ฌธ์ œ๊ฐ€ ์žˆ์Šต๋‹ˆ๋‹ค

์ด๊ฒƒ์ด ๋ฐ”๋กœ ๋‚ด๊ฐ€ ํ•„์š”ํ•œ ๊ฒƒ์ž…๋‹ˆ๋‹ค.
1.6.0-alpha.1์˜ DynamicSizeList๋ฅผ react-virtualized-auto-sizer ๋ฐ react-window-infinite-loader์™€ ํ•จ๊ป˜ ์‚ฌ์šฉํ•˜์—ฌ ๋งค์šฐ ์ข‹์€ ๊ฒฐ๊ณผ๋ฅผ ์–ป์—ˆ์Šต๋‹ˆ๋‹ค.
์ด ์ž‘์—…์„ ์ง„ํ–‰ํ•˜๊ธฐ ์œ„ํ•ด ์ œ๊ฐ€ ๋„์šธ ์ˆ˜์žˆ๋Š” ๊ฒƒ์ด ์žˆ์Šต๋‹ˆ๊นŒ?

์•ˆ๋…•ํ•˜์„ธ์š” @bvaughn , https://github.com/bvaughn/react-window/issues/6#issuecomment -509213284์—์„œ codesandbox๋ฅผ ํ™•์ธํ•  ์‹œ๊ฐ„์ด ์žˆ์—ˆ์Šต๋‹ˆ๊นŒ?

์•ˆ๋…•ํ•˜์„ธ์š”, ์ฑ„ํŒ… ์•ฑ์— DynamicSizeList๋ฅผ ์‚ฌ์šฉํ•˜๊ณ  ์žˆ์Šต๋‹ˆ๋‹ค.
๋ฉ‹์ง„ ๊ธฐ๋Šฅ์— ๊ฐ์‚ฌ๋“œ๋ฆฝ๋‹ˆ๋‹ค.

๊ทธ๋Ÿฌ๋‚˜ ์„ฑ๋Šฅ์ด ๋–จ์–ด์ง€๊ณ  ์Šคํฌ๋ฆฝํŠธ ์ฒ˜๋ฆฌ๊ฐ€ ๋งŽ์€ ๋ฌธ์ œ๊ฐ€ ์žˆ์Šต๋‹ˆ๋‹ค.
์Šคํฌ๋กค ํ•  ๋•Œ CPU๋Š” ํ•ญ์ƒ ์ƒ์Šนํ•˜๊ณ  ์ข…์ข… 100 %์— ๋„๋‹ฌํ•ฉ๋‹ˆ๋‹ค.
์†”๋ฃจ์…˜์— ๋Œ€ํ•œ ์•„์ด๋””์–ด๊ฐ€ ์žˆ์Šต๋‹ˆ๊นŒ?

import { useChatList } from '../../../hooks/chat/useChatList';
import LoadingSpinner from '../../../utils/LoadingSpinner';

import dynamic from 'next/dynamic';
import * as React from 'react';
import AutoSizer from 'react-virtualized-auto-sizer';
// @ts-ignore
import { DynamicSizeList as List } from 'react-window';
import { Message } from 'src/app/typings';

const { useRef, useCallback } = React;

const RowItem = React.memo(
  ({ forwardedRef, style, index, data }: any) => {
    const item = data[index] as Message;
    if (item) {
      return (
        <div id={item.messageId} ref={forwardedRef} style={style}>
          {item.text && item.text.plainText}
        </div>
      );
    }
    return null;
  },
  (prevProps, newProps) => {
    const { index, data } = prevProps;
    const { index: newIndex, data: newData } = newProps;
    let isMemo = true;
    isMemo = isMemo && index === newIndex;
    isMemo = isMemo && data.length === newData.length;
    return isMemo;
  }
);

function ChatList() {
  const listRef = useRef<HTMLInputElement>();

  const { formatMessages: messages, isLoadingMessages } = useChatList();

  const keyCreator = useCallback((index: number) => `ChatList/RowItem/${messages[index].messageId}`, [messages]);

  if (isLoadingMessages && (!messages || messages.length <= 0)) {
    return <LoadingSpinner />;
  }
  return (
    <div style={{ flex: 1, height: '100%', width: '100%' }}>
      <AutoSizer>
        {({ height, width }) => (
          <List
            ref={(lref: HTMLInputElement) => {
              if (lref !== null) {
                listRef.current = lref;
              }
            }}
            itemCount={messages.length}
            itemData={messages}
            itemKey={keyCreator}
            height={height}
            width={width}
            overscanCount={10}
          >
            {React.forwardRef((props, ref) => (
              <RowItem forwardedRef={ref} {...props} />
            ))}
          </List>
        )}
      </AutoSizer>
    </div>
  );
}

export default ChatList;

ใ‚นใ‚ฏใƒชใƒผใƒณใ‚ทใƒงใƒƒใƒˆ 2019-07-14 11 49 54

์•ˆ๋…•ํ•˜์„ธ์š” @bvaughn , ์ž˜
์ž‘์—…์žฅ ํฌ๊ธฐ๋ฅผ ์กฐ์ •ํ•  ๋•Œ ํ•ญ๋ชฉ ๋†’์ด๋ฅผ ๋‹ค์‹œ ๊ณ„์‚ฐํ•˜๋Š” ์˜ฌ๋ฐ”๋ฅธ ๋ฐฉ๋ฒ•์€ ๋ฌด์—‡์ž…๋‹ˆ๊นŒ? ์œ„์˜ ์˜๊ฒฌ์„ ํ†ตํ•ด ๋ช‡ ๊ฐ€์ง€ ๋ฐ๋ชจ๋ฅผ ๋งŒ๋“ค๊ฒ ์Šต๋‹ˆ๋‹ค. https://codesandbox.io/s/angry-hill-tcy2m
๋งˆ์šฐ์Šค๋กœ ์ž‘์—…์žฅ์˜ ๋„ˆ๋น„๊ฐ€ ๋ณ€๊ฒฝ๋˜๋ฉด ๋ชจ๋“  ํ•ญ๋ชฉ ๋†’์ด๋ฅผ ๋‹ค์‹œ ๊ณ„์‚ฐํ•ด์•ผํ•ฉ๋‹ˆ๋‹ค (VariableSizeList ๊ตฌ์„ฑ ์š”์†Œ์˜ ๋‚ด๋ถ€ ๋†’์ด ์บ์‹œ๋ฅผ ์ง€์šธ ์ˆ˜ ์žˆ์Œ) ...

๋™์  ๋ชฉ๋ก์— ๋Œ€ํ•œ ํ•ด๊ฒฐ์ฑ…์ด ์žˆ์Šต๋‹ˆ๊นŒ? ๋ฐฉ๊ธˆ 4 ์‹œ๊ฐ„์„ ๋ณด๋ƒˆ์Šต๋‹ˆ๋‹ค.
๋ชจ๋“  ๋Œ“๊ธ€์„ ์ฝ์€ ํ›„ ๐Ÿ˜ 
๋‹น์‹ ์ด ์ž‘๋™ํ•˜๋Š” ํ•ด๊ฒฐ์ฑ…์ด ์žˆ๋‹ค๋ฉด ์ €์—๊ฒŒ ์ œ๊ณตํ•˜์‹ญ์‹œ์˜ค

์ด ํ”„๋กœ์ ํŠธ์—๋Š” "๋‹น์‹ ๋“ค"์ด ์—†์Šต๋‹ˆ๋‹ค. ํ•œ ์‚ฌ๋žŒ์ด ๊ด€๋ฆฌํ•ฉ๋‹ˆ๋‹ค.

๊ทธ๋ฆฌ๊ณ  ๊ฐ™์€ ์ผ์— ๋Œ€ํ•ด ๋ถˆํ‰ํ•˜๋ฉด์„œ ๊ฐ™์€ ๋‚  ์—ฌ๋Ÿฌ ๋ฌธ์ œ์— ๋Œ€ํ•œ ์˜๊ฒฌ์„ ๋‚จ๊ธฐ๋Š” ๊ฒƒ์€ ์ผ์ข…์˜ ๊ณ ๋ คํ•˜์ง€ ์•Š์Šต๋‹ˆ๋‹ค. ๊ผญ react-virtualized๋ฅผ ์‚ฌ์šฉํ•˜์„ธ์š”.

์ด ๋ธŒ๋ผ์ด์–ธ ๊ฐ™์€ ๋Œ“๊ธ€์„ ๋‚จ๊ฒจ ์ฃผ์…”์„œ ์ •๋ง ์ฃ„์†กํ•ฉ๋‹ˆ๋‹ค ๋‚˜์ค‘์—์ด ๋ฌธ์ œ๋ฅผ ๋ฐœ๊ฒฌ ํ•œ ๋‹ค์Œ ๋ชจ๋“  ๋Œ“๊ธ€์„ ์ฝ์—ˆ์œผ๋ฉฐ ๋‹ค๋ฅธ ์‚ฌ๋žŒ๋“ค์ด ์ตœ์†Œํ•œ ๋‹น์‹ ์„ ๋•๊ณ  ์žˆ๋‹ค๊ณ  ์ƒ๊ฐํ–ˆ์Šต๋‹ˆ๋‹ค.

@ShivamJoker ๊ฑฐ์˜ ์ž‘๋™ํ•˜๊ฒŒ๋˜์—ˆ์Šต๋‹ˆ๋‹ค. ์™„๋ฒฝํ•˜๊ฒŒ ์ž‘๋™ํ•˜๋Š” ๋ฐ ๋‚จ์€ ์œ ์ผํ•œ ๊ฒƒ์€ ์ฝ˜ํ…์ธ ๋ฅผ ๋” ์ ์€ ํ•ญ๋ชฉ์œผ๋กœ ๋ณ€๊ฒฝ ํ•œ ํ›„์—๋„ ๊ณ„์†

@bvaughn https://github.com/bvaughn/react-window/issues/6#issuecomment -509213284์˜ ์ƒŒ๋“œ ๋ฐ•์Šค์—์„œ ์˜ˆ์ œ๋ฅผ ํ™•์ธํ•  ์‹œ๊ฐ„์ด ์žˆ์Šต๋‹ˆ๊นŒ?

=> https://codesandbox.io/s/sweet-sea-irxl8

๋” ์งง์€ ๋ชฉ๋ก์œผ๋กœ ์‹œ์ž‘ํ•˜๋ฏ€๋กœ ๋‹ค์Œ๊ณผ ๊ฐ™์Šต๋‹ˆ๋‹ค.

  • ๋ชฉ๋ก ๋๊นŒ์ง€ ์•„๋ž˜๋กœ ์Šคํฌ๋กค
  • ์œ„๋กœ ์Šคํฌ๋กคํ•˜์—ฌ Show Long List ํด๋ฆญํ•˜์‹ญ์‹œ์˜ค.
  • ๋๊นŒ์ง€ ์•„๋ž˜๋กœ ์Šคํฌ๋กค
  • ์œ„๋กœ ์Šคํฌ๋กคํ•˜์—ฌ Show Short List
  • ๋งˆ์ง€๋ง‰์œผ๋กœ ๋งˆ์ง€๋ง‰์œผ๋กœ ํ•œ ๋ฒˆ ์•„๋ž˜๋กœ ์Šคํฌ๋กคํ•˜์—ฌ ์งง์€ ๋ชฉ๋ก ๋’ค์— ๋งŽ์€ ๊ณต๋ฐฑ์ด ์žˆ๋Š”์ง€ ํ™•์ธํ•ฉ๋‹ˆ๋‹ค.

๊ฐ์‚ฌํ•ฉ๋‹ˆ๋‹ค!

@ShivamJoker ๊ฑฐ์˜ ์ž‘๋™ํ•˜๊ฒŒ๋˜์—ˆ์Šต๋‹ˆ๋‹ค. ์™„๋ฒฝํ•˜๊ฒŒ ์ž‘๋™ํ•˜๋Š” ๋ฐ ๋‚จ์€ ์œ ์ผํ•œ ๊ฒƒ์€ ์ฝ˜ํ…์ธ ๋ฅผ ๋” ์ ์€ ํ•ญ๋ชฉ์œผ๋กœ ๋ณ€๊ฒฝ ํ•œ ํ›„์—๋„ ๊ณ„์†

@bvaughn # 6 (์ฝ”๋ฉ˜ํŠธ) ์˜ ์ƒŒ๋“œ ๋ฐ•์Šค์—์„œ ์˜ˆ์ œ๋ฅผ ํ™•์ธํ•  ์‹œ๊ฐ„์ด ์žˆ์Šต๋‹ˆ๊นŒ?

=> https://codesandbox.io/s/sweet-sea-irxl8

๋” ์งง์€ ๋ชฉ๋ก์œผ๋กœ ์‹œ์ž‘ํ•˜๋ฏ€๋กœ ๋‹ค์Œ๊ณผ ๊ฐ™์Šต๋‹ˆ๋‹ค.

  • ๋ชฉ๋ก ๋๊นŒ์ง€ ์•„๋ž˜๋กœ ์Šคํฌ๋กค
  • ์œ„๋กœ ์Šคํฌ๋กคํ•˜์—ฌ Show Long List ํด๋ฆญํ•˜์‹ญ์‹œ์˜ค.
  • ๋๊นŒ์ง€ ์•„๋ž˜๋กœ ์Šคํฌ๋กค
  • ์œ„๋กœ ์Šคํฌ๋กคํ•˜์—ฌ Show Short List
  • ๋งˆ์ง€๋ง‰์œผ๋กœ ๋งˆ์ง€๋ง‰์œผ๋กœ ํ•œ ๋ฒˆ ์•„๋ž˜๋กœ ์Šคํฌ๋กคํ•˜์—ฌ ์งง์€ ๋ชฉ๋ก ๋’ค์— ๋งŽ์€ ๊ณต๋ฐฑ์ด ์žˆ๋Š”์ง€ ํ™•์ธํ•ฉ๋‹ˆ๋‹ค.

๊ฐ์‚ฌํ•ฉ๋‹ˆ๋‹ค!

์˜ˆ, ๊ธฐ๋ณธ์ ์œผ๋กœ ๋‚ด๋ถ€ ์ปจํ…Œ์ด๋„ˆ๋Š” ๋ฐ์ดํ„ฐ ํ•„ํ„ฐ๋ง / ๋ณ€๊ฒฝ์‹œ ๋†’์ด๋ฅผ ์žฌ์„ค์ •ํ•ด์•ผํ•ฉ๋‹ˆ๋‹ค.

@ShivamJoker ๊ฑฐ์˜ ์ž‘๋™ํ•˜๊ฒŒ๋˜์—ˆ์Šต๋‹ˆ๋‹ค. ์™„๋ฒฝํ•˜๊ฒŒ ์ž‘๋™ํ•˜๋Š” ๋ฐ ๋‚จ์€ ์œ ์ผํ•œ ๊ฒƒ์€ ์ฝ˜ํ…์ธ ๋ฅผ ๋” ์ ์€ ํ•ญ๋ชฉ์œผ๋กœ ๋ณ€๊ฒฝ ํ•œ ํ›„์—๋„ ๊ณ„์†

@bvaughn # 6 (์ฝ”๋ฉ˜ํŠธ) ์˜ ์ƒŒ๋“œ ๋ฐ•์Šค์—์„œ ์˜ˆ์ œ๋ฅผ ํ™•์ธํ•  ์‹œ๊ฐ„์ด ์žˆ์Šต๋‹ˆ๊นŒ?

=> https://codesandbox.io/s/sweet-sea-irxl8

๋” ์งง์€ ๋ชฉ๋ก์œผ๋กœ ์‹œ์ž‘ํ•˜๋ฏ€๋กœ ๋‹ค์Œ๊ณผ ๊ฐ™์Šต๋‹ˆ๋‹ค.

  • ๋ชฉ๋ก ๋๊นŒ์ง€ ์•„๋ž˜๋กœ ์Šคํฌ๋กค
  • ์œ„๋กœ ์Šคํฌ๋กคํ•˜์—ฌ Show Long List ํด๋ฆญํ•˜์‹ญ์‹œ์˜ค.
  • ๋๊นŒ์ง€ ์•„๋ž˜๋กœ ์Šคํฌ๋กค
  • ์œ„๋กœ ์Šคํฌ๋กคํ•˜์—ฌ Show Short List
  • ๋งˆ์ง€๋ง‰์œผ๋กœ ๋งˆ์ง€๋ง‰์œผ๋กœ ํ•œ ๋ฒˆ ์•„๋ž˜๋กœ ์Šคํฌ๋กคํ•˜์—ฌ ์งง์€ ๋ชฉ๋ก ๋’ค์— ๋งŽ์€ ๊ณต๋ฐฑ์ด ์žˆ๋Š”์ง€ ํ™•์ธํ•ฉ๋‹ˆ๋‹ค.

๊ฐ์‚ฌํ•ฉ๋‹ˆ๋‹ค!

๊ฐ์‚ฌํ•ฉ๋‹ˆ๋‹ค ๋‹ค๋ฅธ ์‚ฌ์šฉ์ž์—๊ฒŒ๋„ ์ž˜ ์ž‘๋™ํ•˜๊ธฐ๋ฅผ ๋ฐ”๋ผ๋Š” ๋™์ผํ•œ ๊ตฌํ˜„
์˜ˆ, ์Šคํฌ๋กค์˜ ๋†’์ด ๋ฌธ์ œ๋„ ๋ณด์•˜์Šต๋‹ˆ๋‹ค.

@ graphee-gabrielํ•˜์ง€๋งŒ ๋‚ด ์•ฑ ๋ฐ”๊ฐ€ ์•„๋ž˜๋กœ ์Šคํฌ๋กค ํ•  ๋•Œ ์ˆจ๊ธฐ๋Š” ๋ฐ ์‚ฌ์šฉ๋˜๋Š” ๋ฌธ์ œ๊ฐ€ ํ•˜๋‚˜ ๋” ์žˆ์Šต๋‹ˆ๋‹ค. ์ง€๊ธˆ ๋ฐœ์ƒํ•˜์ง€ ์•Š๋Š” ์†”๋ฃจ์…˜์€ ๋ฌด์—‡์ž…๋‹ˆ๊นŒ?
image

์ข‹์€ ๋‚ . ๋ฐ๋ชจ ํ”„๋กœ์ ํŠธ์—์„œ DinamycSizeList๋ฅผ ์‚ฌ์šฉํ–ˆ์Šต๋‹ˆ๋‹ค. ๋ชจ๋“  ๊ฒƒ์ด ๊ดœ์ฐฎ ์•˜์ง€๋งŒ ์ž ์‹œ ํ›„ ๋ชฉ๋ก ๊ตฌ์„ฑ ์š”์†Œ๊ฐ€ ์ž˜๋ชป ์ž‘๋™ํ•˜๊ธฐ ์‹œ์ž‘ํ–ˆ์Šต๋‹ˆ๋‹ค. ์ฒ˜์Œ์—๋Š” ๋ฐ˜์‘ ์ฐฝ์ด ์˜์กดํ•˜๋Š” ๋ผ์ด๋ธŒ๋Ÿฌ๋ฆฌ๋ผ๊ณ  ์ƒ๊ฐํ–ˆ์Šต๋‹ˆ๋‹ค. ํ•˜์ง€๋งŒ ๋ฐ๋ชจ๋ฅผ ๋ณด๋ฉด
https://react-window-next.now.sh/#/examples/list/dynamic -size
๊ณผ๊ฑฐ์—๋Š” ์™„๋ฒฝํ•˜๊ฒŒ ์ž‘๋™ํ–ˆ์ง€๋งŒ ๊ฑฐ์˜ ๋™์ผํ•œ ๊ฒฐ๊ณผ๋ฅผ ๋ฐœ๊ฒฌํ–ˆ์Šต๋‹ˆ๋‹ค. ์ด๋Ÿฌํ•œ ๋ฒ„๊ทธ์˜ ์›์ธ์„ ์ œ์•ˆ ํ•ด ์ฃผ์‹œ๊ฒ ์Šต๋‹ˆ๊นŒ?

๋ฟก๋ฟก

์˜ˆ, ๊ธฐ๋ณธ์ ์œผ๋กœ ๋‚ด๋ถ€ ์ปจํ…Œ์ด๋„ˆ๋Š” ๋ฐ์ดํ„ฐ ํ•„ํ„ฐ๋ง / ๋ณ€๊ฒฝ์‹œ ๋†’์ด๋ฅผ ์žฌ์„ค์ •ํ•ด์•ผํ•ฉ๋‹ˆ๋‹ค.

์–ด๋–ป๊ฒŒํ•ด์•ผํ•˜๋‚˜์š” ์ƒํƒœ ๋†’์ด๋ฅผ ์ž…๋ ฅ ํ•ด ๋ณด์•˜์ง€๋งŒ ์ž‘๋™ํ•˜์ง€ ์•Š๋Š” ๊ฒƒ ๊ฐ™์Šต๋‹ˆ๋‹ค
์–ด๋–ค ํ•ด๊ฒฐ์ฑ…?

๋ฟก๋ฟก

์˜ˆ, ๊ธฐ๋ณธ์ ์œผ๋กœ ๋‚ด๋ถ€ ์ปจํ…Œ์ด๋„ˆ๋Š” ๋ฐ์ดํ„ฐ ํ•„ํ„ฐ๋ง / ๋ณ€๊ฒฝ์‹œ ๋†’์ด๋ฅผ ์žฌ์„ค์ •ํ•ด์•ผํ•ฉ๋‹ˆ๋‹ค.

์–ด๋–ป๊ฒŒํ•ด์•ผํ•˜๋‚˜์š” ์ƒํƒœ ๋†’์ด๋ฅผ ์ž…๋ ฅ ํ•ด ๋ณด์•˜์ง€๋งŒ ์ž‘๋™ํ•˜์ง€ ์•Š๋Š” ๊ฒƒ ๊ฐ™์Šต๋‹ˆ๋‹ค
์–ด๋–ค ํ•ด๊ฒฐ์ฑ…?

๋ผ์ด๋ธŒ๋Ÿฌ๋ฆฌ์—์„œ ๋‚ด๋ถ€์ ์œผ๋กœ ๊ตฌํ˜„ํ•ด์•ผํ•ฉ๋‹ˆ๋‹ค.

@ShivamJoker ๊ฑฐ์˜ ์ž‘๋™ํ•˜๊ฒŒ๋˜์—ˆ์Šต๋‹ˆ๋‹ค. ์™„๋ฒฝํ•˜๊ฒŒ ์ž‘๋™ํ•˜๋Š” ๋ฐ ๋‚จ์€ ์œ ์ผํ•œ ๊ฒƒ์€ ์ฝ˜ํ…์ธ ๋ฅผ ๋” ์ ์€ ํ•ญ๋ชฉ์œผ๋กœ ๋ณ€๊ฒฝ ํ•œ ํ›„์—๋„ ๊ณ„์†

@bvaughn # 6 (์ฝ”๋ฉ˜ํŠธ) ์˜ ์ƒŒ๋“œ ๋ฐ•์Šค์—์„œ ์˜ˆ์ œ๋ฅผ ํ™•์ธํ•  ์‹œ๊ฐ„์ด ์žˆ์Šต๋‹ˆ๊นŒ?

=> https://codesandbox.io/s/sweet-sea-irxl8

๋” ์งง์€ ๋ชฉ๋ก์œผ๋กœ ์‹œ์ž‘ํ•˜๋ฏ€๋กœ ๋‹ค์Œ๊ณผ ๊ฐ™์Šต๋‹ˆ๋‹ค.

  • ๋ชฉ๋ก ๋๊นŒ์ง€ ์•„๋ž˜๋กœ ์Šคํฌ๋กค
  • ์œ„๋กœ ์Šคํฌ๋กคํ•˜์—ฌ Show Long List ํด๋ฆญํ•˜์‹ญ์‹œ์˜ค.
  • ๋๊นŒ์ง€ ์•„๋ž˜๋กœ ์Šคํฌ๋กค
  • ์œ„๋กœ ์Šคํฌ๋กคํ•˜์—ฌ Show Short List
  • ๋งˆ์ง€๋ง‰์œผ๋กœ ๋งˆ์ง€๋ง‰์œผ๋กœ ํ•œ ๋ฒˆ ์•„๋ž˜๋กœ ์Šคํฌ๋กคํ•˜์—ฌ ์งง์€ ๋ชฉ๋ก ๋’ค์— ๋งŽ์€ ๊ณต๋ฐฑ์ด ์žˆ๋Š”์ง€ ํ™•์ธํ•ฉ๋‹ˆ๋‹ค.

๊ฐ์‚ฌํ•ฉ๋‹ˆ๋‹ค!

๊ณต๋ฐฑ์„ ๋ฐฉ์ง€ํ•˜๊ธฐ ์œ„ํ•ด ํ‚ค๋ฅผ ์„ค์ •ํ•  ์ˆ˜ ์žˆ์Šต๋‹ˆ๋‹ค.
https://codesandbox.io/s/blissful-voice-mzjsc

์•ˆ๋…•ํ•˜์„ธ์š” @bvaughn ์ด ๋ฉ‹์ง„ ํ”„๋กœ์ ํŠธ์— ๊ฐ์‚ฌ๋“œ๋ฆฝ๋‹ˆ๋‹ค!

ํ•„์ž๋Š” ์ œํ•œ์—†์ด ์–ด๋””์—์„œ๋‚˜ ์Šคํฌ๋กคํ•˜๋Š” ๋ฐฉ๋ฒ•๊ณผ ์ธก์ • ๋œ ํ•ญ๋ชฉ์ด ์•„๋‹Œ ํ•ญ๋ชฉ์œผ๋กœ ์Šคํฌ๋กคํ•˜๋Š” ๋ฐฉ๋ฒ•์„ ์•Œ์•„ ๋‚ด๋ ค๊ณ  DynamicLists ์ฝ”๋“œ์—์„œ ๊ฝค ๋งŽ์€ ์‹œ๊ฐ„์„ ๋ณด๋ƒˆ์Šต๋‹ˆ๋‹ค.

๋‚˜๋Š” lastMeasuredIndex ํ•˜๊ณ  ๋Œ€์‹  itemIsMeasured ํ•ญ๋ชฉ ๋‹น ํ™•์ธํ•จ์œผ๋กœ์จ https://github.com/bvaughn/react-window/compare/issues/6...Sauco82 : issues / 6์—์„œ ๊ทธ๋ ‡๊ฒŒ ํ•  ์ˆ˜์žˆ์—ˆ์Šต๋‹ˆ๋‹ค. itemIsMeasured , ๋ถ„๋ช…ํžˆ ๋‹ค๋ฅธ ๋งŽ์€ ๋ณ€๊ฒฝ ์‚ฌํ•ญ์ด ํ•„์š”ํ•ฉ๋‹ˆ๋‹ค.

์ €๋Š” ์˜คํ”ˆ ์†Œ์Šค ํ”„๋กœ์ ํŠธ์— ์ฐธ์—ฌํ•˜์ง€ ์•Š์•˜๊ณ  Flow๋ฅผ ์‚ฌ์šฉํ•œ ์ ์ด ์—†์—ˆ๊ธฐ ๋•Œ๋ฌธ์— ์ด๊ฒƒ์ด ์œ ์šฉํ•˜๊ฑฐ๋‚˜ ํฌํ•จ ํ•  ๊ฐ€์น˜๊ฐ€ ์žˆ๋Š”์ง€, PR์„ ์ง์ ‘ ์‹œ๋„ํ•˜๊ฑฐ๋‚˜ ์—ฌ๊ธฐ์„œ ๋…ผ์˜ํ•ด์•ผํ• ์ง€ ํ™•์‹คํ•˜์ง€ ์•Š์Šต๋‹ˆ๋‹ค.

๊ธฐ๊บผ์ด ๋„์™€ ๋“œ๋ฆฌ๊ฒ ์Šต๋‹ˆ๋‹ค. ํ•„์š”ํ•œ ๊ฒƒ์ด ์žˆ์œผ๋ฉด ์•Œ๋ ค์ฃผ์„ธ์š”.

์—ฌ๊ธฐ ํ›จ์”ฌ ๋” ๊ฐ„๋‹จํ•œ ์†”๋ฃจ์…˜์ด ์žˆ์Šต๋‹ˆ๋‹ค (ํฌ๊ธฐ๋ฅผ ๊ณ„์‚ฐํ•˜๊ธฐ ์œ„ํ•ด DOM์— ๊ณ ์ŠคํŠธ ์š”์†Œ๋ฅผ ์ถ”๊ฐ€ ํ•  ํ•„์š”๊ฐ€ ์—†์Œ).
์ฝ”๋“œ ์ƒŒ๋“œ ๋ฐ•์Šค

์—ฌ๊ธฐ ํ›จ์”ฌ ๋” ๊ฐ„๋‹จํ•œ ์†”๋ฃจ์…˜์ด ์žˆ์Šต๋‹ˆ๋‹ค (ํฌ๊ธฐ๋ฅผ ๊ณ„์‚ฐํ•˜๊ธฐ ์œ„ํ•ด DOM์— ๊ณ ์ŠคํŠธ ์š”์†Œ๋ฅผ ์ถ”๊ฐ€ ํ•  ํ•„์š”๊ฐ€ ์—†์Œ).
์ฝ”๋“œ ์ƒŒ๋“œ ๋ฐ•์Šค

๋Œ€๋ฐ•! ๊ทธ๊ฒƒ์€ ๋‚˜๋ฅผ ์œ„ํ•ด ์ž‘๋™ํ•ฉ๋‹ˆ๋‹ค. ์ข‹์€ ์ž‘์—….

@Kashkovsky ๋Š” ์—…๋ฐ์ดํŠธ ๋œ ๊ฒฝ์šฐ ํฌ๊ธฐ๋ฅผ ๊ณ„์‚ฐํ–ˆ์Šต๋‹ˆ๋‹ค.
๋ฐ itemSize ํ•œ ๋ฒˆ ํ˜ธ์ถœ

@ userbq201 @Kashkovsky ํ›Œ๋ฅญํ•œ ํ•ด๊ฒฐ ๋ฐฉ๋ฒ•! ์–ด๋–ป๊ฒŒ ๋“  ๋‚ด ๊ฒฝ์šฐ์—๋Š” ์ƒ์ž์—์„œ ์ž‘๋™ํ•˜์ง€ ์•Š์•˜์œผ๋ฏ€๋กœ ChatHistory.js ์ฝ”๋“œ๋ฅผ ๋‹ค์Œ๊ณผ ๊ฐ™์ด ์ˆ˜์ •ํ•ด์•ผํ–ˆ์Šต๋‹ˆ๋‹ค.

    const listRef = useRef(); // added
    const sizeMap = useRef({});
    const setSize = useCallback((index, size) => {
        sizeMap.current = {...sizeMap.current, [index]: size};
        listRef.current.resetAfterIndex(index); // added
    }, []);
    const getSize = useCallback(index => sizeMap.current[index] || 60, []);
    // ...
    <List ref={listRef}

๊ทธ๋ ‡์ง€ ์•Š์œผ๋ฉด ๋ชจ๋“  ํ•ญ๋ชฉ์ด ๋™์ผํ•œ ๊ธฐ๋ณธ ๋†’์ด๋กœ ๋ Œ๋”๋ง๋ฉ๋‹ˆ๋‹ค. ๊ท€ํ•˜์˜ ๊ฒฝ์šฐ์—๋Š” ๊ทธ๋Œ€๋กœ ์ž‘๋™ํ•ฉ๋‹ˆ๋‹ค. ์™œ ์ฐจ์ด์ ์ด ์žˆ๋Š”์ง€ ์„ค๋ช… ํ•  ์ˆ˜ ์—†์Šต๋‹ˆ๋‹ค ... ์•„๋งˆ๋„ @bvaughn์ด ํ•  ์ˆ˜ ์žˆ์Šต๋‹ˆ๋‹ค.

@bvaughn SSR์— ๋Œ€ํ•ด ์œ ์‚ฌํ•œ ๋™์ž‘์„ ํ™œ์„ฑํ™”ํ•ด์•ผํ•œ๋‹ค๋ฉด ์–ด๋–จ๊นŒ์š”? ๊ทธ์ชฝ์— ๋Œ€ํ•œ ํžŒํŠธ๊ฐ€ ์žˆ์Šต๋‹ˆ๊นŒ?

@bvaughn ์ €์ž…๋‹ˆ๊นŒ ์•„๋‹ˆ๋ฉด ๋ฐ๋ชจ ๊ฐ€ ์ž‘๋™ํ•˜์ง€ ์•Š์Šต๋‹ˆ๊นŒ?

@Kashkovsky @ kirill-konshin ๋ฐ @ userbq201 ๋ฉ‹์ง„ ๊ตฌํ˜„!

์ด ์†”๋ฃจ์…˜์œผ๋กœ ๋ฉ”๋ชจ ํ™”๋ฅผ ์‚ฌ์šฉํ•˜๋Š” ๋ฐฉ๋ฒ•์€ ๋ฌด์—‡์ž…๋‹ˆ๊นŒ?

memo ์—์„œ areEqual ChatMessage๋ฅผ ๋ž˜ํ•‘ํ•˜๋ ค๊ณ  ์‹œ๋„ํ–ˆ์ง€๋งŒ React๋Š” ๋ฉ”์‹œ์ง€๊ฐ€ ๋ชฉ๋ก์— ์ถ”๊ฐ€ ๋  ๋•Œ๋งˆ๋‹ค ๊ฐ ๊ฐœ์ฒด๋ฅผ ๋‹ค์‹œ ๋ Œ๋”๋งํ•ฉ๋‹ˆ๋‹ค.

๋‚ด ๋‹ค๋ฅธ FixedSizedLists์—์„œ๋Š” ๋ฉ”๋ชจ๊ฐ€ ํ•ด๋‹น memo / areEqual ๋ž˜ํผ๋กœ ์ž˜ ์ž‘๋™ํ•˜์ง€๋งŒ ref={root} ๊ฐ€ ์˜ํ–ฅ์„ ๋ฏธ์น  ์ˆ˜ ์žˆ์Šต๋‹ˆ๊นŒ?

React๊ฐ€ ์ปดํฌ๋„ŒํŠธ๋ฅผ ๋‹ค์‹œ ๋ Œ๋”๋งํ•˜๋Š”์ง€ ์‰ฝ๊ฒŒ ์•Œ ์ˆ˜ ์žˆ์Šต๋‹ˆ๋‹ค.

๋‚˜๋Š” ์—ฌ๊ธฐ์— ์˜ˆ์ œ๋ฅผ ํฌํฌํ–ˆ๋‹ค : https://codesandbox.io/s/dynamic-size-of-react-window-list-items-nb038


ํŽธ์ง‘ : ๋ฉ”๋ชจ๋ฅผ ์ˆ˜์ •ํ–ˆ์Šต๋‹ˆ๋‹ค-์ดˆ๊ธฐ ๊ธฐ๋Šฅ ๊ตฌ์„ฑ ์š”์†Œ๋ฅผ ๋ฉ”๋ชจ๋กœ ๊ฐ์‹ธ๋Š” ๊ฒƒ์ž…๋‹ˆ๋‹ค. ๋‚ด๊ฐ€ ํ•œ ๊ฒƒ์ฒ˜๋Ÿผ. ๋‹ค์Œ์€ ๋ˆ„๊ตฐ๊ฐ€ ์ž์‹ ์˜ ๋ชฉ๋ก์— ๋ณต์žกํ•œ DOM ๊ตฌ์กฐ๊ฐ€์žˆ๋Š” ๊ฒฝ์šฐ (๋˜๋Š” ๋‚ด๊ฐ€ํ•˜๋Š” ๊ฒƒ์ฒ˜๋Ÿผ ๋น„๋””์˜ค๋ฅผ ๋งคํ•‘ํ•ด์•ผํ•˜๋Š” ๊ฒฝ์šฐ) ๋ฉ”๋ชจ ํ™” ๋œ ์†”๋ฃจ์…˜์ž…๋‹ˆ๋‹ค. https://codesandbox.io/s/dynamic-size-of-react-window-list -์•„์ดํ…œ -errt4


ํŽธ์ง‘ 2 : ํ–‰์˜ ์ดˆ๊ธฐ ๋ Œ๋”๋ง์€ ์™„์ „ํžˆ ๊ดœ์ฐฎ์ง€ ๋งŒ resetAfterIndex ํ˜ธ์ถœํ•˜๋Š” ๊ฒƒ์€ ๊ด€๋ฆฌํ•˜๊ธฐ๊ฐ€ ๋งค์šฐ ์–ด๋ ต์Šต๋‹ˆ๋‹ค. ๋‚ด ๋ฐ์ดํ„ฐ๊ฐ€ ๋ณ€๊ฒฝ๋ฉ๋‹ˆ๋‹ค (์˜ˆ : ์‚ฌ์šฉ์ž๊ฐ€ ๋‹ค๋ฅธ ๋Œ€ํ™”๋ฅผ ์„ ํƒํ•˜๋Š” ๊ฒฝ์šฐ). ๊ทธ๋Ÿฌ๋‚˜ ์ง„์งœ ๋ฌธ์ œ๋Š” resetAfterIndex ๊ฐ€ ์ƒˆ setSize ๊ฐ€ ์™„๋ฃŒ๋˜๊ธฐ ์ „์— ์‹คํ–‰๋˜๋Š” ๊ฒƒ์ฒ˜๋Ÿผ ๋ณด์ธ๋‹ค๋Š” ๊ฒƒ์ž…๋‹ˆ๋‹ค. ๋”ฐ๋ผ์„œ ์บ์‹œ ๋œ ์Šคํƒ€์ผ์„ ์„ฑ๊ณต์ ์œผ๋กœ ์ง€์šฐ์ง€ ๋งŒ ๋ธŒ๋ผ์šฐ์ €๊ฐ€ ์ฝ˜ํ…์ธ  ํฌ๊ธฐ ์กฐ์ •์„ ์™„๋ฃŒํ•˜์ง€ ์•Š์•˜๊ธฐ ๋•Œ๋ฌธ์— ์ด์ „ ์Šคํƒ€์ผ์˜ ์ƒˆ ์บ์‹œ๋ฅผ ๋‹ค์‹œ ์ƒ์„ฑํ•ฉ๋‹ˆ๋‹ค.

๊ทธ๊ฒƒ์ด ๊ธ€๋กœ ์˜๋ฏธ๊ฐ€ ์žˆ๋Š”์ง€ ํ™•์‹คํ•˜์ง€ ์•Š์ง€๋งŒ ์ง€๊ธˆ์€ ์—ฌ๊ธฐ์— ํ•€์„ ๋„ฃ์–ด์•ผํ•ฉ๋‹ˆ๋‹ค. ๋ˆ„๊ตฐ๊ฐ€ ์„ฑ๊ณต์ ์œผ๋กœ ์ฝ˜ํ…์ธ ๋ฅผ ๋™์ ์œผ๋กœ ๋ณ€๊ฒฝํ•˜๊ณ  ์—…๋ฐ์ดํŠธ ๋œ ๋†’์ด ์Šคํƒ€์ผ์„ ์œ ์ง€ํ•˜๊ณ  ์žˆ๋Š”์ง€ ์•Œ๋ ค์ฃผ์„ธ์š”.

๋‹ค๋ฅธ ๋งŽ์€ ๋ฐ˜์‘ ์ฐฝ ๊ตฌํ˜„์ด ์žˆ์œผ๋ฏ€๋กœ์ด ์‚ฌ์šฉ ์‚ฌ๋ก€์— ๋Œ€ํ•ด ๋ฐ˜์‘ ๊ฐ€์ƒํ™”๋ฅผ ์‚ฌ์šฉํ•˜๋Š” ๋Œ€์‹  ์—ฌ๊ธฐ์—์„œ ์ข‹์€ ์†”๋ฃจ์…˜์„ ์ฐพ๋Š” ๊ฒƒ์ด ์ข‹์Šต๋‹ˆ๋‹ค.


ํŽธ์ง‘ 3 : ๋งˆ์นจ๋‚ด ๋ฐ˜ ์šฐ์•„ํ•œ ์†”๋ฃจ์…˜์„ ์ƒ๊ฐํ•ด ๋ƒˆ๊ธฐ ๋•Œ๋ฌธ์— ์ด๊ฒƒ์€ ์ตœ์ข… ํŽธ์ง‘์ด ๋  ๊ฒƒ์ž…๋‹ˆ๋‹ค.

1.) itemData๋ฅผ ๋ณ€๊ฒฝํ•ด์•ผํ•˜๋Š” ๊ฒฝ์šฐ (์˜ˆ : ๋Œ€ํ™”๊ฐ€ ๋ณ€๊ฒฝ ๋  ๋•Œ) ์ „์ฒด๋ฅผ ๋งˆ์šดํŠธ ํ•ด์ œํ•ฉ๋‹ˆ๋‹ค. ์ปดํฌ๋„ŒํŠธ๋ฅผ ์‚ฌ์šฉํ•œ ๋‹ค์Œ ์ƒˆ itemData๋กœ ๋‹ค์‹œ ๋งˆ์šดํŠธํ•˜์‹ญ์‹œ์˜ค. ์ด๊ฒƒ์€ setState ์ฝœ๋ฐฑ์„ ์‚ฌ์šฉํ•˜์—ฌ ์ˆ˜ํ–‰ ํ•  ์ˆ˜ ์žˆ์Šต๋‹ˆ๋‹ค. ์ด๋ ‡๊ฒŒํ•˜๋ฉด ๋ฐ์ดํ„ฐ๋ฅผ ๋ณ€๊ฒฝํ•  ๋•Œ ์ด์ „ ๋†’์ด ์Šคํƒ€์ผ์ด ์ ์šฉ๋˜์ง€ ์•Š์Šต๋‹ˆ๋‹ค.

2.) ChatMessage ๋ฅผ ํ†ตํ•ด ChatContext {sizeMap, setSize, listRef} ์„ ChatMessage ์ „๋‹ฌํ–ˆ์Šต๋‹ˆ๋‹ค. ๊ทธ๋Ÿฐ ์‹์œผ๋กœ ํฌ๊ธฐ๋ฅผ ๋งน๋ชฉ์ ์œผ๋กœ ์„ค์ •ํ•˜๋Š” ๋Œ€์‹  ChatMessage์— ํฌ๊ธฐ๋ฅผ ์„ค์ •ํ•˜๊ณ  ์ด์ „ ํฌ๊ธฐ์™€ ๋น„๊ตํ•˜๋„๋ก ์ง€์‹œ ํ•  ์ˆ˜ ์žˆ์Šต๋‹ˆ๋‹ค. ์ด์ „ ํฌ๊ธฐ๊ฐ€ ์ƒˆ๋กœ์šด ํฌ๊ธฐ์™€ ๋‹ค๋ฅธ ๊ฒฝ์šฐ, ๋‹ค์Œ ์ „ํ™” resetAfterIndex ์‹œ์ž‘ index ํž˜ ์—…๋ฐ์ดํŠธ์— ์ถฉ์‹ค ์ „๋‹ฌํ•ฉ๋‹ˆ๋‹ค.

๊ทธ๋ž˜์„œ ๋‚ด ์ƒˆ ChatMessage๋Š” ๋‹ค์Œ๊ณผ ๊ฐ™์Šต๋‹ˆ๋‹ค.

const ChatMessage = ({ message, index }) => {
    const { setSize, sizeMap, listRef } = useContext(ChatContext);
    const root = React.useRef();
    useEffect(() => {
        let oldSize = sizeMap[index];
        let newSize = root.current.getBoundingClientRect().height;
        setSize(index, newSize);
        if(newSize !== oldSize){
            listRef.current.resetAfterIndex(index,true);
        }
    }, [sizeMap, setSize, listRef]);

    return (
        <div ref={root}
             {message.body}
        </div>
    );
};
export default ChatMessage;

3.) ๊ธฐ๋ณธ์ ์œผ๋กœ ์ฒญ์ทจ์ž ์ธ ๊ฒƒ์„ ์ƒˆ๋กœ ๋งˆ์šดํŠธ ๋œ ๊ฒƒ์„ ๊ธฐ๋‹ค๋ฆฌ๋Š” ๊ตฌ์„ฑ ์š”์†Œ ๋ Œ๋”๋ง๋ฉ๋‹ˆ๋‹ค. ๋ Œ๋”๋ง๋˜๋ฉด ์•„๋ž˜์ชฝ์œผ๋กœ ์Šคํฌ๋กค๋ฉ๋‹ˆ๋‹ค. ์ด๋ ‡๊ฒŒํ•˜๋ฉด ํ•ด๋‹น ๋ฉ”์„œ๋“œ๊ฐ€ ํ˜ธ์ถœ๋˜๊ธฐ ์ „์— ๋ Œ๋”๋ง๋˜์ง€ ์•Š์•˜๊ธฐ ๋•Œ๋ฌธ์— scrollTo ํ•จ์ˆ˜๋ฅผ componentDidMount์— ์ง์ ‘ ๋„ฃ์„ ๋•Œ ๋ฐœ์ƒํ•˜๋Š” ๋ฌธ์ œ๊ฐ€ ํ•ด๊ฒฐ๋ฉ๋‹ˆ๋‹ค. ๊ทธ๋ž˜์„œ ๋‹ค์Œ๊ณผ ๊ฐ™์ด ๋ณด์ž…๋‹ˆ๋‹ค.

class Chat extends Component {
    constructor(props) {
        super(props);
        this.listRef = createRef();
        this.state = {
            initialScrollComplete: false,
            interval: null
        };
    }

    componentDidMount(){
        // Create interval to check if list is ready. Once ready, scroll to bottom of list.
        this.setState({interval: setInterval(()=>{
            if(this.listRef.current && !this.state.initialScrollComplete){
                this.listRef.current.scrollToItem(this.props.chatHistory.length - 1, "end");
                this.setState({initialScrollComplete: true});
            }
        },25)});
    }

    componentDidUpdate(prevProps, prevState) {

        // Clear interval if scroll has been completed
        if(!prevState.initialScrollComplete && this.state.initialScrollComplete){
            clearInterval(this.state.interval);
            this.setState({interval: null});
        }

        // If new message is transmitted, scroll to bottom
        if(prevProps.chatHistory && this.props.chatHistory && prevProps.chatHistory.length !== this.props.chatHistory.length){
            this.listRef.current.scrollToItem(this.props.chatHistory.length - 1, "end");
        }

    }

    render() {
        return <ChatHistory listRef={this.listRef} chatHistory={this.props.chatHistory}/>;
    }
}

์‚ฌํŒŒ๋ฆฌ์—์„œ ์ •๋ง ์ด์ƒํ•œ ํ–‰๋™์ด์žˆ๋Š” ๊ฒƒ ๊ฐ™์Šต๋‹ˆ๋‹ค.

DynamicSizedList div์˜ ๋†’์ด์™€ ํ–‰์˜ ๋†’์ด ๋˜๋Š” ์—ฌ๋ฐฑ ์ƒ๋‹จ์ด ์˜ฌ๋ฐ”๋ฅด๊ฒŒ ์ž‘๋™ํ•˜์ง€ ์•Š์Šต๋‹ˆ๋‹ค. ์ฝ˜ํ…์ธ ๊ฐ€ ๊ฒน์น˜๊ธฐ ์‹œ์ž‘ํ•ฉ๋‹ˆ๋‹ค.

์ฐฝ ๋„ˆ๋น„ / ํ–‰์˜ ๋‚ด์šฉ์ด ๋ณ€๊ฒฝ ๋  ๋•Œ ์ƒˆ ๋†’์ด๊ฐ€ ๋‹ค์‹œ ๊ณ„์‚ฐ๋˜๊ฑฐ๋‚˜ ๋‚ด์šฉ์˜ ์ƒˆ ๋†’์ด์™€ ํ•จ๊ป˜ ์ž‘๋™ํ•˜๋„๋ก ๋ณ€๊ฒฝ๋˜์ง€ ์•Š์Šต๋‹ˆ๋‹ค.

์ด ๋ฌธ์ œ๋ฅผ ํ•ด๊ฒฐํ•˜๋Š” ๊ฒƒ์œผ๋กœ ๋ณด์ด๋Š” ๊ฒƒ์€ ์ฝ˜ํ…์ธ ๋ฅผ ์Šคํฌ๋กค ํ•  ์ˆ˜์žˆ๋Š” ๊ฒฝ์šฐ ํ–‰์ด ๋” ์ด์ƒ ํ‘œ์‹œ๋˜์ง€ ์•Š๋Š” ์ง€์ ๊นŒ์ง€ ์Šคํฌ๋กคํ•˜๊ณ  ์œ„๋กœ ์Šคํฌ๋กคํ•˜๋ฉด ์˜ฌ๋ฐ”๋ฅด๊ฒŒ ๋ Œ๋”๋ง๋˜๋Š” ๊ฒƒ์ž…๋‹ˆ๋‹ค.

์ฝ˜ํ…์ธ ๊ฐ€ ์ฒซ ํŽ˜์ด์ง€๋กœ๋“œ์‹œ ์˜ฌ๋ฐ”๋ฅด๊ฒŒ ๋ Œ๋”๋ง๋˜์ง€ ์•Š์œผ๋ฏ€๋กœ ์ƒˆ๋กœ ๊ณ ์นจํ•ด๋„ ๋ฌธ์ œ๊ฐ€ ํ•ด๊ฒฐ๋˜์ง€ ์•Š๋Š” ๊ฒƒ ๊ฐ™์Šต๋‹ˆ๋‹ค.

ํฌ๋กฌ๊ณผ ํŒŒ์ด์–ด ํญ์Šค๋ฅผ ํฌํ•จํ•œ ๋‹ค๋ฅธ ๋ธŒ๋ผ์šฐ์ €์—์„œ๋„ ์™„๋ฒฝํ•˜๊ฒŒ ์ž‘๋™ํ•ฉ๋‹ˆ๋‹ค. Safari๋Š” ๋”์ฐํ•˜์ง€๋งŒ ์•ˆํƒ€๊น๊ฒŒ๋„ ์•ฑ์„ ์‚ฌ์šฉํ•˜๋Š” ์‚ฌ๋žŒ๋“ค์„ ์œ„ํ•ด ์—ฌ์ „ํžˆ ์ž‘๋™ํ•ด์•ผํ•ฉ๋‹ˆ๋‹ค.

Screenshot 2020-02-15 at 14 27 19

์ •๋ง ๋„์›€์ด ํ•„์š” ํ•ด์š”!

@tastyqbit Safari์™€ Internet Explorer์—์„œ๋„ ๊ฐ™์€ ๋ฌธ์ œ๊ฐ€ ๋ฐœ์ƒํ–ˆ์Šต๋‹ˆ๋‹ค. ์•ž์„œ ์–ธ๊ธ‰ํ–ˆ๋“ฏ์ด ํ™•์žฅ ๋œ ํ–‰์„์ง€๋‚˜ ์Šคํฌ๋กค ํ•œ ๋‹ค์Œ ๋’ค๋กœ ์Šคํฌ๋กคํ•˜๋ฉด ์˜ฌ๋ฐ”๋ฅด๊ฒŒ ๋ Œ๋”๋ง๋˜์ง€๋งŒ ์‹ค์ œ๋กœ ๋ฌธ์ œ๊ฐ€ ํ•ด๊ฒฐ๋˜์ง€๋Š” ์•Š์Šต๋‹ˆ๋‹ค.

ํ•ด๊ฒฐ ๋ฐฉ๋ฒ•์„ ์ฐพ์œผ๋ฉด ์•Œ๋ ค์ฃผ์‹ญ์‹œ์˜ค!

@afreix @tastyqbit Safari ๋ฐ Internet Explorer์—์„œ ๋ฐœ์ƒํ•œ ๋ฌธ์ œ๋Š” ํ•ด๋‹น ๋ธŒ๋ผ์šฐ์ €์—์„œ ResizeObserver์— ๋Œ€ํ•œ ์ง€์›์ด ๋ถ€์กฑํ•˜๊ธฐ ๋•Œ๋ฌธ์ด๋ผ๊ณ  ํ™•์‹ ํ•ฉ๋‹ˆ๋‹ค. ๋‚˜๋Š” ์ •ํ™•ํžˆ ๋‹น์‹ ์˜ ๋ฌธ์ œ๋ฅผ ๊ฐ€์ง€๊ณ  ์žˆ์—ˆ๊ณ  (๋’ค๋กœ ์Šคํฌ๋กคํ•˜์—ฌ ์ˆ˜์ •ํ–ˆ์Šต๋‹ˆ๋‹ค) polyfill์„ ์ถ”๊ฐ€ํ•˜๋ฉด ๋ฌธ์ œ๊ฐ€ ํ•ด๊ฒฐ๋˜์—ˆ์Šต๋‹ˆ๋‹ค. ํ˜ธํ™˜์„ฑ ํ‘œ๋Š” MDN ์„ ์ฐธ์กฐํ•˜์‹ญ์‹œ์˜ค.

ResizeObserver๊ฐ€ ์—†์œผ๋ฉด ์ฝ˜์†”์— ๊ฒฝ๊ณ ๊ฐ€ ์ƒ์„ฑ๋˜์–ด์•ผํ•œ๋‹ค๊ณ  ์ƒ๊ฐํ•ฉ๋‹ˆ๋‹ค.

https://codesandbox.io/s/agitated-jennings-o9nn6 ๊ณผ ๊ฐ™์€ ๊ฒƒ์€ ์–ด๋–ป์Šต๋‹ˆ๊นŒ?

# 102์˜ VariableSizeList + ItemMeasurer๋ฅผ ์‚ฌ์šฉํ•˜๋Š” ๊ธฐ๋ณธ ์ €๋Š” ์ด๊ฒƒ์ด ๋งค์šฐ ์ˆœ์ง„ํ•œ ์ ‘๊ทผ ๋ฐฉ์‹์ด๋ผ๋Š” ๊ฒƒ์„ ์•Œ๊ณ  ์žˆ์ง€๋งŒ ์ž„์‹œ ์†”๋ฃจ์…˜์œผ๋กœ ์ž‘๋™ํ•˜๋Š” ๊ฒƒ์ฒ˜๋Ÿผ ๋ณด์ž…๋‹ˆ๋‹ค (๊ทธ๋ ‡๊ฒŒ ๋‚˜์˜์ง€ ์•Š์Šต๋‹ˆ๋‹ค ๐Ÿ˜‚) ๐Ÿค”

์šฐ๋ฆฌ ํŒ€์—์„œ๋Š” ๋ฌด์ž‘์œ„ ํฌ๊ธฐ์˜ ํ…์ŠคํŠธ ๋ฐ์ดํ„ฐ๋ฅผ ๋Œ€๋Ÿ‰์œผ๋กœ ๋ Œ๋”๋งํ•ด์•ผ ํ•  ํ•„์š”์„ฑ์„ ๋ฐœ๊ฒฌํ–ˆ์Šต๋‹ˆ๋‹ค.
์šฐ๋ฆฌ์—๊ฒŒ๋Š” ํ•ญ๋ชฉ ์‚ฌ์ด๋ฅผ ์ •ํ™•ํ•˜๊ฒŒ ์ ํ”„ํ•˜๊ณ  ์ง€์—ฐ์—†์ด ์Šคํฌ๋กค ํ•  ์ˆ˜์žˆ๋Š” ๊ธฐ๋Šฅ์ด ํ•„์ˆ˜์˜€์Šต๋‹ˆ๋‹ค.
๊ฝค ๋งŽ์€ ์˜จ๋ผ์ธ ๊ฒ€์ƒ‰ ํ›„์— ๋‚˜๋Š” ํฌ๊ธฐ ํ•˜๊ณ ์ด ๋ผ์ด๋ธŒ๋Ÿฌ๋ฆฌ๋ฅผ ์ผ์Šต๋‹ˆ๋‹ค.
์—ฌ๋Ÿฌ๋ถ„ ์ค‘ ์ผ๋ถ€๋ฅผ์œ„ํ•œ ์ž„์‹œ ํ•ด๊ฒฐ์ฑ…์œผ๋กœ ๋„์›€์ด๋˜๊ธฐ๋ฅผ ๋ฐ”๋ž๋‹ˆ๋‹ค. : smile_cat :

์•ผ,
๋ช‡ ๊ฐ€์ง€ ์ž‘์—… ํ›„์— ๋ผ์ด๋ธŒ๋Ÿฌ๋ฆฌ ๊ฐ€ ๊ดœ์ฐฎ์€ ์ƒํƒœ๊ฐ€๋˜์—ˆ๊ณ  ํ•ญ๋ชฉ์ด ์ฒ˜์Œ ๋ Œ๋”๋ง ๋œ ํ›„ ํฌ๊ธฐ๊ฐ€ ๋ณ€๊ฒฝ๋˜์ง€ ์•Š์œผ๋ฉด ์ข‹์€ ์†”๋ฃจ์…˜์ด ๋  ์ˆ˜ ์žˆ๋‹ค๊ณ  ์ƒ๊ฐํ•ฉ๋‹ˆ๋‹ค.

@ gnir-work ์ฐฝ์˜ ํฌ๊ธฐ๊ฐ€ ์กฐ์ •๋˜๊ณ  ์ปจํ…Œ์ด๋„ˆ ํฌ๊ธฐ๊ฐ€ ๋ณ€๊ฒฝ๋˜์–ด ๋ชฉ๋ก ํฌ๊ธฐ๊ฐ€ ์กฐ์ •๋˜๋ฉด ์–ด๋–ป๊ฒŒ๋ฉ๋‹ˆ๊นŒ?

์ด ์Šค๋ ˆ๋“œ๋ฅผ ์ฝ์œผ๋ฉด ๋„ˆ๋น„๊ฐ€ ๋ณ€๊ฒฝ ๋  ์ˆ˜์žˆ๋Š” ํ•ญ๋ชฉ์„ ์ฒ˜๋ฆฌํ•˜๋Š” ๋” ์ข‹์€ ๋ฐฉ๋ฒ•์ด์žˆ์„ ์ˆ˜ ์žˆ๋‹ค๊ณ  ์ƒ๊ฐํ•ฉ๋‹ˆ๋‹ค.

์—ฌ๊ธฐ์„œ '๋ณ€์ˆ˜'์˜ ์ •์˜๋Š” ์ „์ฒด ์„ธํŠธ์— ๊ฑธ์ณ ๊ฐ€๋ณ€์ ์ž…๋‹ˆ๋‹ค. ์‹ค์ œ ํ•ญ๋ชฉ ํฌ๊ธฐ๋Š” ๋™์ ์ด ์•„๋‹ˆ๋ผ ์ •์ ์ž…๋‹ˆ๋‹ค. ํ…์ŠคํŠธ๊ฐ€ ๋ณ€๊ฒฝ๋˜๋ฉด ํฌ๊ธฐ๊ฐ€ ๋ณ€๊ฒฝ๋˜๊ฑฐ๋‚˜ ๋ณ€ํ˜•๋˜๋Š” ๋™์•ˆ ํฌ๊ธฐ๊ฐ€ ๋ณ€๊ฒฝ ๋  ์ˆ˜ ์žˆ์œผ๋ฏ€๋กœ ๋™์ ์ด ๋” ๋‚˜์€ ์šฉ์–ด ์ผ ์ˆ˜ ์žˆ์Šต๋‹ˆ๋‹ค.

์ด๊ฒƒ์ด ์ž‘๋™ํ•˜๋Š” ๋ฐฉ๋ฒ•์€ ๋ถ€๋ชจ์˜ ์Šคํฌ๋กค์„ ๋“ฃ๋Š” ๊ฒƒ์ž…๋‹ˆ๋‹ค.

์•Œ๊ณ ๋ฆฌ์ฆ˜์€ ๋‹ค์Œ๊ณผ ๊ฐ™์ด ์ž‘๋™ํ•ฉ๋‹ˆ๋‹ค.

  • ๊ฐ ํ•ญ๋ชฉ์˜ ์˜ˆ์ƒ ํฌ๊ธฐ๋ฅผ ๊ณ„์‚ฐํ•ฉ๋‹ˆ๋‹ค. ์ด๊ฒƒ์€ ๋งค์šฐ ํšจ์œจ์ ์ด์–ด์•ผํ•ฉ๋‹ˆ๋‹ค. ์™„๋ฒฝ ํ•  ํ•„์š”๋Š” ์—†์Šต๋‹ˆ๋‹ค. +-20 %๋Š” ๊ดœ์ฐฎ์Šต๋‹ˆ๋‹ค.

  • ๋ณด์ด๋Š” ์•„์ดํ…œ ๋งŒ ๋ Œ๋”๋ง + 20 % ๋” ๋งํ•ด์„œ ์‚ฌ์šฉ์ž๊ฐ€ ์Šคํฌ๋กคํ•ด๋„ ๋ณ€๊ฒฝ ์‚ฌํ•ญ์ด ๋ณด์ด์ง€ ์•Š๋„๋กํ•ฉ๋‹ˆ๋‹ค.

  • '๋†’์ด'๊ฐ€ ์˜ˆ์ƒ ๋†’์ด๋กœ ์„ค์ •๋œ ๋‹ค๋ฅธ ๋ชจ๋“  ํ•ญ๋ชฉ์— ๋Œ€ํ•ด '์œ ๋ น'์ด ์žˆ์Šต๋‹ˆ๋‹ค. ๋‹จ์ง€ ๋นˆ div์ž…๋‹ˆ๋‹ค. ์ด๋ ‡๊ฒŒํ•˜๋ฉด ์Šคํฌ๋กค ๋ง‰๋Œ€๊ฐ€ ์˜ค๋ฅธ์ชฝ์œผ๋กœ ๋ณด์ž…๋‹ˆ๋‹ค.

  • ํ•ญ๋ชฉ์€ ๋ทฐํฌํŠธ์—์žˆ์„ ๋•Œ๋งŒ ํ‘œ์‹œ๋ฉ๋‹ˆ๋‹ค. ๊ทธ ์™ธ์— ์œ ๋ น ์•„์ดํ…œ์ด ํ‘œ์‹œ๋ฉ๋‹ˆ๋‹ค.

์œ ์ผํ•œ ๋‹จ์ ์€ ์Šคํฌ๋กค๋ฐ” ๋†’์ด๊ฐ€ ์•ฝ๊ฐ„ ๋ณ€๊ฒฝ๋œ๋‹ค๋Š” ๊ฒƒ์ž…๋‹ˆ๋‹ค. ์ด๊ฒƒ์ด ์‚ฌ์šฉ์ž์˜์ฃผ์˜๋ฅผ ์‚ฐ๋งŒํ•˜๊ฒŒํ• ์ง€ ํ™•์‹คํ•˜์ง€ ์•Š์Šต๋‹ˆ๋‹ค. ์Šคํฌ๋กค ๋ชฉ๋ก์ด ํฐ ๊ฒฝ์šฐ ์ผ ์ˆ˜ ์žˆ์Šต๋‹ˆ๋‹ค. ์˜ˆ์ƒ ํฌ๊ธฐ๊ฐ€ ์Šคํฌ๋กค ๋ง‰๋Œ€ ๊ธธ์ด์— ์˜ํ–ฅ์„์ฃผ์ง€ ์•Š๋„๋ก ๋ฒ„ํผ๋ฅผ ๋Š˜๋ฆฌ๊ฑฐ๋‚˜ ์ค„์ž„์œผ๋กœ์จ์ด๋ฅผ ์†์ผ ์ˆ˜ ์žˆ์Šต๋‹ˆ๋‹ค.

@ gnir-work ์ฐฝ์˜ ํฌ๊ธฐ๊ฐ€ ์กฐ์ •๋˜๊ณ  ์ปจํ…Œ์ด๋„ˆ ํฌ๊ธฐ๊ฐ€ ๋ณ€๊ฒฝ๋˜์–ด ๋ชฉ๋ก ํฌ๊ธฐ๊ฐ€ ์กฐ์ •๋˜๋ฉด ์–ด๋–ป๊ฒŒ๋ฉ๋‹ˆ๊นŒ?

์ตœ์‹  ๋ฒ„์ „ ( 2.2.0 )๋ถ€ํ„ฐ ๊ตฌ์„ฑ ์š”์†Œ๋Š” ์ „์ฒด ๋ชฉ๋ก์˜ ํฌ๊ธฐ (๋†’์ด ๋ฐ ๋„ˆ๋น„) ๋ณ€๊ฒฝ์„ ์ง€์›ํ•ฉ๋‹ˆ๋‹ค.

์ด ์Šค๋ ˆ๋“œ๋ฅผ ์ฝ์œผ๋ฉด ๋„ˆ๋น„๊ฐ€ ๋ณ€๊ฒฝ ๋  ์ˆ˜์žˆ๋Š” ํ•ญ๋ชฉ์„ ์ฒ˜๋ฆฌํ•˜๋Š” ๋” ์ข‹์€ ๋ฐฉ๋ฒ•์ด์žˆ์„ ์ˆ˜ ์žˆ๋‹ค๊ณ  ์ƒ๊ฐํ•ฉ๋‹ˆ๋‹ค.

์—ฌ๊ธฐ์„œ '๋ณ€์ˆ˜'์˜ ์ •์˜๋Š” ์ „์ฒด ์„ธํŠธ์— ๊ฑธ์ณ ๊ฐ€๋ณ€์ ์ž…๋‹ˆ๋‹ค. ์‹ค์ œ ํ•ญ๋ชฉ ํฌ๊ธฐ๋Š” ๋™์ ์ด ์•„๋‹ˆ๋ผ ์ •์ ์ž…๋‹ˆ๋‹ค. ํ…์ŠคํŠธ๊ฐ€ ๋ณ€๊ฒฝ๋˜๋ฉด ํฌ๊ธฐ๊ฐ€ ๋ณ€๊ฒฝ๋˜๊ฑฐ๋‚˜ ๋ณ€ํ˜•๋˜๋Š” ๋™์•ˆ ํฌ๊ธฐ๊ฐ€ ๋ณ€๊ฒฝ ๋  ์ˆ˜ ์žˆ์œผ๋ฏ€๋กœ ๋™์ ์ด ๋” ๋‚˜์€ ์šฉ์–ด ์ผ ์ˆ˜ ์žˆ์Šต๋‹ˆ๋‹ค.

์ด๊ฒƒ์ด ์ž‘๋™ํ•˜๋Š” ๋ฐฉ๋ฒ•์€ ๋ถ€๋ชจ์˜ ์Šคํฌ๋กค์„ ๋“ฃ๋Š” ๊ฒƒ์ž…๋‹ˆ๋‹ค.

์•Œ๊ณ ๋ฆฌ์ฆ˜์€ ๋‹ค์Œ๊ณผ ๊ฐ™์ด ์ž‘๋™ํ•ฉ๋‹ˆ๋‹ค.

  • ๊ฐ ํ•ญ๋ชฉ์˜ ์˜ˆ์ƒ ํฌ๊ธฐ๋ฅผ ๊ณ„์‚ฐํ•ฉ๋‹ˆ๋‹ค. ์ด๊ฒƒ์€ ๋งค์šฐ ํšจ์œจ์ ์ด์–ด์•ผํ•ฉ๋‹ˆ๋‹ค. ์™„๋ฒฝ ํ•  ํ•„์š”๋Š” ์—†์Šต๋‹ˆ๋‹ค. +-20 %๋Š” ๊ดœ์ฐฎ์Šต๋‹ˆ๋‹ค.
  • ๋ณด์ด๋Š” ์•„์ดํ…œ ๋งŒ ๋ Œ๋”๋ง + 20 % ๋” ๋งํ•ด์„œ ์‚ฌ์šฉ์ž๊ฐ€ ์Šคํฌ๋กคํ•ด๋„ ๋ณ€๊ฒฝ ์‚ฌํ•ญ์ด ๋ณด์ด์ง€ ์•Š๋„๋กํ•ฉ๋‹ˆ๋‹ค.
  • '๋†’์ด'๊ฐ€ ์˜ˆ์ƒ ๋†’์ด๋กœ ์„ค์ •๋œ ๋‹ค๋ฅธ ๋ชจ๋“  ํ•ญ๋ชฉ์— ๋Œ€ํ•ด '์œ ๋ น'์ด ์žˆ์Šต๋‹ˆ๋‹ค. ๋‹จ์ง€ ๋นˆ div์ž…๋‹ˆ๋‹ค. ์ด๋ ‡๊ฒŒํ•˜๋ฉด ์Šคํฌ๋กค ๋ง‰๋Œ€๊ฐ€ ์˜ค๋ฅธ์ชฝ์œผ๋กœ ๋ณด์ž…๋‹ˆ๋‹ค.
  • ํ•ญ๋ชฉ์€ ๋ทฐํฌํŠธ์—์žˆ์„ ๋•Œ๋งŒ ํ‘œ์‹œ๋ฉ๋‹ˆ๋‹ค. ๊ทธ ์™ธ์— ์œ ๋ น ์•„์ดํ…œ์ด ํ‘œ์‹œ๋ฉ๋‹ˆ๋‹ค.

์œ ์ผํ•œ ๋‹จ์ ์€ ์Šคํฌ๋กค๋ฐ” ๋†’์ด๊ฐ€ ์•ฝ๊ฐ„ ๋ณ€๊ฒฝ๋œ๋‹ค๋Š” ๊ฒƒ์ž…๋‹ˆ๋‹ค. ์ด๊ฒƒ์ด ์‚ฌ์šฉ์ž์˜์ฃผ์˜๋ฅผ ์‚ฐ๋งŒํ•˜๊ฒŒํ• ์ง€ ํ™•์‹คํ•˜์ง€ ์•Š์Šต๋‹ˆ๋‹ค. ์Šคํฌ๋กค ๋ชฉ๋ก์ด ํฐ ๊ฒฝ์šฐ ์ผ ์ˆ˜ ์žˆ์Šต๋‹ˆ๋‹ค. ์˜ˆ์ƒ ํฌ๊ธฐ๊ฐ€ ์Šคํฌ๋กค ๋ง‰๋Œ€ ๊ธธ์ด์— ์˜ํ–ฅ์„์ฃผ์ง€ ์•Š๋„๋ก ๋ฒ„ํผ๋ฅผ ๋Š˜๋ฆฌ๊ฑฐ๋‚˜ ์ค„์ž„์œผ๋กœ์จ์ด๋ฅผ ์†์ผ ์ˆ˜ ์žˆ์Šต๋‹ˆ๋‹ค.

์ด๊ฒƒ์€ ์ด๋ฏธ react-virtualized ์—์„œ @bvaughn ์— ์˜ํ•ด ๊ตฌํ˜„๋˜์—ˆ์Šต๋‹ˆ๋‹ค. ์ด ์ ‘๊ทผ ๋ฐฉ์‹์˜ ์ฃผ์š” ๋‹จ์ ์€ ํŠน์ • ํ–‰์œผ๋กœ ์ ํ”„ํ•˜๋Š” ๊ฒƒ์ด ์ œ๋Œ€๋กœ ์ž‘๋™ํ•˜์ง€ ์•Š๊ณ  ์œ„๋กœ ์Šคํฌ๋กค ํ•  ๋•Œ ์‹œ๊ฐ์  ๋ฒ„๊ทธ๋ฅผ ์ƒ์„ฑํ•œ๋‹ค๋Š” ๊ฒƒ์ž…๋‹ˆ๋‹ค.

@ gnir-work ah .. ok ... ์•„๋งˆ๋„ ๋‚ด ์ž‘์—…์„ ์ค‘๋‹จํ•˜๊ณ  react-virtualized๋ฅผ ์‚ดํŽด๋ณผ ๊ฒƒ์ž…๋‹ˆ๋‹ค.

๋‚˜๋Š” ๋‹น์‹ ์ด ์Šคํฌ๋กค ์—… ๋ฌธ์ œ์— ๋งž๋‹ค๊ณ  ์ƒ๊ฐํ•˜์ง€๋งŒ '์˜ˆ์ƒ ํฌ๊ธฐ'๋ฅผ ๊ฐ€์ง€๊ณ  ์ด๊ฒƒ์„ ๊ณ ์น  ์ˆ˜ ์žˆ๋‹ค๊ณ  ์ƒ๊ฐํ•˜๊ณ  ๊ตฌ์„ฑ ์š”์†Œ๊ฐ€ ๋งˆ์šดํŠธ๋˜๋ฉด ์‹ค์ œ ํฌ๊ธฐ๋กœ ๋ณ€ํ™˜ ํ•  ์ˆ˜ ์žˆ์Šต๋‹ˆ๋‹ค.

... ๋ฌผ๋ก  ๋˜ ๋‹ค๋ฅธ ๋ฌธ์ œ๋Š” ๋™์  ์ฝ˜ํ…์ธ ๋ฅผ ์ฒ˜๋ฆฌํ•˜๋Š” ๊ฒƒ์ž…๋‹ˆ๋‹ค. ๋ฌด์–ธ๊ฐ€๊ฐ€ ์—…๋ฐ์ดํŠธ๋˜๋ฉด ๊ตฌ์„ฑ ์š”์†Œ ๋†’์ด๊ฐ€ ๋ณ€๊ฒฝ๋ฉ๋‹ˆ๋‹ค.

์˜ˆ์ƒ ํฌ๊ธฐ๊ฐ€ ์ž‘๋™ ํ•  ์ˆ˜์žˆ๋Š” ๊ฒƒ๋ณด๋‹ค ์ •ํ™•ํ•˜๋ฉด ์˜ˆ๋ฅผ ๋“ค์–ด ์–ผ๋งˆ ์ „์— react-virtualized๋กœ ๋™์  ๋†’์ด๊ฐ€์žˆ๋Š” ๊ฐ€์ƒํ™” ๋œ ๋ชฉ๋ก์„ ๊ตฌํ˜„ํ–ˆ์œผ๋ฉฐ ์˜ˆ์ƒ ํฌ๊ธฐ๊ฐ€ ์ •ํ™•ํ•˜๋ฉด ์ž˜ ์ž‘๋™ํ–ˆ์Šต๋‹ˆ๋‹ค. ๊ทธ๋ ‡์ง€ ์•Š์œผ๋ฉด ์Šคํฌ๋กค ๊ธฐ๋Šฅ์ด ๋‚ด ์•ฑ์„ ์†์ƒ์‹œํ‚ฌ ์ˆ˜ ์žˆ์Šต๋‹ˆ๋‹ค. โ˜น

Windows 10 ์šฉ ๋ฉ”์ผ์—์„œ ๋ณด๋ƒ„

๋ณด๋‚ธ ์‚ฌ๋žŒ : Kevin Burton
๋ณด๋‚ธ ๋‚ ์งœ : ํ™”์š”์ผ, 2020 ๋…„ 4 ์›” 14 ์ผ 23:07
๋ฐ›๋Š” ์‚ฌ๋žŒ : bvaughn / react-window
Cc : Nir Geller; ์–ธ๊ธ‰ํ•˜๋‹ค
์ œ๋ชฉ : Re : [bvaughn / react-window] Just-In-Time ์ธก์ • ์ฝ˜ํ…์ธ  ์ง€์› (# 6)

@ gnir-work ah .. ok ... ์•„๋งˆ๋„ ๋‚ด ์ž‘์—…์„ ์ค‘๋‹จํ•˜๊ณ  react-virtualized๋ฅผ ์‚ดํŽด๋ณผ ๊ฒƒ์ž…๋‹ˆ๋‹ค.
๋‚˜๋Š” ๋‹น์‹ ์ด ์Šคํฌ๋กค ์—… ๋ฌธ์ œ์— ๋งž๋‹ค๊ณ  ์ƒ๊ฐํ•˜์ง€๋งŒ '์˜ˆ์ƒ ํฌ๊ธฐ'๋ฅผ ๊ฐ€์ง€๊ณ  ์ด๊ฒƒ์„ ๊ณ ์น  ์ˆ˜ ์žˆ๋‹ค๊ณ  ์ƒ๊ฐํ•˜๊ณ  ๊ตฌ์„ฑ ์š”์†Œ๊ฐ€ ๋งˆ์šดํŠธ๋˜๋ฉด ์‹ค์ œ ํฌ๊ธฐ๋กœ ๋ณ€ํ™˜ ํ•  ์ˆ˜ ์žˆ์Šต๋‹ˆ๋‹ค.
... ๋ฌผ๋ก  ๋˜ ๋‹ค๋ฅธ ๋ฌธ์ œ๋Š” ๋™์  ์ฝ˜ํ…์ธ ๋ฅผ ์ฒ˜๋ฆฌํ•˜๋Š” ๊ฒƒ์ž…๋‹ˆ๋‹ค. ๋ฌด์–ธ๊ฐ€๊ฐ€ ์—…๋ฐ์ดํŠธ๋˜๋ฉด ๊ตฌ์„ฑ ์š”์†Œ ๋†’์ด๊ฐ€ ๋ณ€๊ฒฝ๋ฉ๋‹ˆ๋‹ค.
โ€”
๋‹น์‹ ์ด ์–ธ๊ธ‰ ๋˜์—ˆ๊ธฐ ๋•Œ๋ฌธ์— ์ด๊ฒƒ์„ ๋ฐ›๊ณ  ์žˆ์Šต๋‹ˆ๋‹ค.
์ด ์ด๋ฉ”์ผ์— ์ง์ ‘ ๋‹ต์žฅํ•˜๊ฑฐ๋‚˜ GitHub์—์„œ ํ™•์ธํ•˜๊ฑฐ๋‚˜ ๊ตฌ๋…์„ ์ทจ์†Œํ•˜์„ธ์š”.

-
์ด ์ด๋ฉ”์ผ์€ Avast ๋ฐ”์ด๋Ÿฌ์Šค ๋ฐฑ์‹  ์†Œํ”„ํŠธ์›จ์–ด์— ์˜ํ•ด ๋ฐ”์ด๋Ÿฌ์Šค ๊ฒ€์‚ฌ๋ฅผ ๋ฐ›์•˜์Šต๋‹ˆ๋‹ค.
https://www.avast.com/antivirus

@ gnir-work ์•„ ... ๋‚ด๊ฐ€ ์ƒ๊ฐํ•˜๊ธฐ์— '์Šคํฌ๋กค ํˆฌ ๋กœ์šฐ'๊ธฐ๋Šฅ์ด ํ•„์š”ํ•˜์ง€ ์•Š์Šต๋‹ˆ๋‹ค.

์ด๊ฒƒ์ด ๋‹น์‹ ์˜ ํ•„์š”์— ์ถฉ๋ถ„ํ•  ๊ฒƒ์ž…๋‹ˆ๋‹ค ๐Ÿ˜Š

Windows 10 ์šฉ ๋ฉ”์ผ์—์„œ ๋ณด๋ƒ„

๋ณด๋‚ธ ์‚ฌ๋žŒ : Kevin Burton
๋ณด๋‚ธ ๋‚ ์งœ : ํ™”์š”์ผ, 2020 ๋…„ 4 ์›” 14 ์ผ 23:13
๋ฐ›๋Š” ์‚ฌ๋žŒ : bvaughn / react-window
Cc : Nir Geller; ์–ธ๊ธ‰ํ•˜๋‹ค
์ œ๋ชฉ : Re : [bvaughn / react-window] Just-In-Time ์ธก์ • ์ฝ˜ํ…์ธ  ์ง€์› (# 6)

@ gnir-work ์•„ ... ๋‚ด๊ฐ€ ์ƒ๊ฐํ•˜๊ธฐ์— '์Šคํฌ๋กค ํˆฌ ๋กœ์šฐ'๊ธฐ๋Šฅ์ด ํ•„์š”ํ•˜์ง€ ์•Š์Šต๋‹ˆ๋‹ค.
โ€”
๋‹น์‹ ์ด ์–ธ๊ธ‰ ๋˜์—ˆ๊ธฐ ๋•Œ๋ฌธ์— ์ด๊ฒƒ์„ ๋ฐ›๊ณ  ์žˆ์Šต๋‹ˆ๋‹ค.
์ด ์ด๋ฉ”์ผ์— ์ง์ ‘ ๋‹ต์žฅํ•˜๊ฑฐ๋‚˜ GitHub์—์„œ ํ™•์ธํ•˜๊ฑฐ๋‚˜ ๊ตฌ๋…์„ ์ทจ์†Œํ•˜์„ธ์š”.

-
์ด ์ด๋ฉ”์ผ์€ Avast ๋ฐ”์ด๋Ÿฌ์Šค ๋ฐฑ์‹  ์†Œํ”„ํŠธ์›จ์–ด์— ์˜ํ•ด ๋ฐ”์ด๋Ÿฌ์Šค ๊ฒ€์‚ฌ๋ฅผ ๋ฐ›์•˜์Šต๋‹ˆ๋‹ค.
https://www.avast.com/antivirus

ํ•ด๊ฒฐ ๋ฐฉ๋ฒ• :

  • ๋ชฉ๋ก ํ–‰ ๋†’์ด๋Š” ๋‚ด๋ถ€ ํ…์ŠคํŠธ์—๋งŒ ์˜์กดํ•ฉ๋‹ˆ๋‹ค (๋ฐ ํฌ๊ธฐ๊ฐ€ ๊ฒฐ์ •๋œ ์ผ๋ถ€ ์š”์†Œ ํฌํ•จ).
  • ๋ชฉ๋ก์˜ ๋„ˆ๋น„๊ฐ€ ๊ณ ์ •๋˜์–ด ์žˆ์Šต๋‹ˆ๋‹ค.

์ „์ฒด ๊ตฌ์„ฑ ์š”์†Œ๋ฅผ ๋ Œ๋”๋งํ•˜๋Š” ๋Œ€์‹  CanvasRenderingContext2D.measureText ()๋ฅผ ์‚ฌ์šฉํ•˜์—ฌ ํ–‰ ๋†’์ด๋ฅผ ๊ณ„์‚ฐํ•  ์ˆ˜ ์žˆ์Šต๋‹ˆ๋‹ค.

CodeSandbox

@bvaughn npm์— ์ƒˆ ์•ŒํŒŒ ๋ฒ„์ „์„ ๊ฒŒ์‹œ ํ•  ๊ณ„ํš์ด ์žˆ์Šต๋‹ˆ๊นŒ? 1.6.0-alpha.1 ์ดํ›„ ์—…๋ฐ์ดํŠธ๊ฐ€ ์—†์Šต๋‹ˆ๋‹ค ๐Ÿ˜•

@bvaughn ์—…๋ฐ์ดํŠธ๊ฐ€ ์žˆ์Šต๋‹ˆ๊นŒ? ์ตœ์‹  ๋ฒ„์ „์—์„œ ์ˆ˜์ •๋ฉ๋‹ˆ๊นŒ?

DynamicSizeList ์™€ ํ•จ๊ป˜ Typescript๋ฅผ ์‚ฌ์šฉํ•˜๋ ค๋Š” ์‚ฌ๋žŒ๋“ค์„ ์œ„ํ•ด-๋ชจ๋“ˆ ํ™•์žฅ์€ DefinitelyTyped ์ •์˜์—์„œ ์ž‘๋™ํ•˜๋Š” DynamicSizeList ํ•„์š”ํ•œ ์œ ํ˜•์„ ์ œ๊ณต ํ•  ์ˆ˜ ์žˆ์Šต๋‹ˆ๋‹ค (์ž‘๋…„์—์ด ์Šค๋ ˆ๋“œ์— ๊ฒŒ์‹œ ๋œ ๋‚ด ์ฟผ๋ฆฌ์— ๋Œ€ํ•œ ํ•ด๊ฒฐ ๋ฐฉ๋ฒ•).

ํ”„๋กœ์ ํŠธ์— ๋‹ค์Œ์„ ์ถ”๊ฐ€ํ•˜์‹ญ์‹œ์˜ค.

import React, { Component } from 'react'

declare module 'react-window' {
  export type DynamicSizeListProps = Omit<FixedSizeListProps, 'itemSize' | 'scrollToItem'>
  export class DynamicSizeList extends Component<DynamicSizeListProps> {}
}

๊ทธ๋Ÿฐ ๋‹ค์Œ ํ‰์†Œ์™€ ๊ฐ™์ด ๊ฐ€์ ธ์˜ต๋‹ˆ๋‹ค.

import {
  DynamicSizeList,
  DynamicSizeListProps,
} from 'react-window'

// use as normal...

@types/react-window FixedSizeListProps ์ •์˜๋ฅผ ์œ„ํ•ด @types/react-window ๋จผ์ € ์„ค์น˜ํ•ด์•ผํ•ฉ๋‹ˆ๋‹ค.

typedefs์— ๊ฐ์‚ฌ๋“œ๋ฆฝ๋‹ˆ๋‹ค. ์ง€๊ธˆ ์ถ”๊ฐ€ํ•˜๊ฒ ์Šต๋‹ˆ๋‹ค! ์ €๋Š” 1 ๋…„ ๋„˜๊ฒŒ ์ œํ’ˆ์—์„œ DynamicSizeList๋ฅผ ์‚ฌ์šฉํ•˜๊ณ  ์žˆ์Šต๋‹ˆ๋‹ค. ํ˜„์žฌ์ด ํฌํฌ๋ฅผ ๊ธฐ๋ฐ˜์œผ๋กœํ•ฉ๋‹ˆ๋‹ค : "@john-osullivan/react-window-dynamic-fork": "^1.9.0-alpha.1" (์•„์ง ์ตœ์‹  ์ƒํƒœ์ž…๋‹ˆ๊นŒ?). ์ด๊ฒƒ์ด ์‹ค์ œ๋กœ ์ถœ์‹œ ๋ ์ง€ ์—ฌ๋ถ€์— ๋Œ€ํ•œ ๋ถˆํ™•์‹ค์„ฑ ๋•Œ๋ฌธ์— react-virtuoso ๋กœ ์ „ํ™˜ํ•˜๋ ค๊ณ ํ–ˆ์Šต๋‹ˆ๋‹ค. ๊ทธ๋Ÿฌ๋‚˜ ์„ฑ๋Šฅ์ด ๋–จ์–ด์ง€๊ณ  ์ด๊ฒƒ์— ๋ถ™์–ด ์žˆ์Šต๋‹ˆ๋‹ค.

@bvaughn ์•„์ง cowpath๋ฅผ ํฌ์žฅํ•˜๊ณ  npm์— ๋ฆด๋ฆฌ์Šค ํ•  ์‹œ๊ฐ„์ž…๋‹ˆ๊นŒ? ์•„์ง ์ค€๋น„๋˜์ง€ ์•Š์€ ๊ฒƒ์ด ๊ฑฑ์ •๋œ๋‹ค๋ฉด ExperimentalDynamicSizeList ๋กœ ์ด๋ฆ„์„ ๋ณ€๊ฒฝํ–ˆ์„ ์ˆ˜๋„ ์žˆ์Šต๋‹ˆ๋‹ค.

์•ˆ๋…•ํ•˜์„ธ์š” ์—ฌ๋Ÿฌ๋ถ„! ๊ท€ํ•˜์˜ ๋…ธ๋ ฅ๊ณผ์ด ํ›Œ๋ฅญํ•œ ๋„์„œ๊ด€์— ๊ฐ์‚ฌ๋“œ๋ฆฝ๋‹ˆ๋‹ค. ์ด ๊ธฐ๋Šฅ์ด ์ •๋ง ๊ธฐ๋Œ€๋ฉ๋‹ˆ๋‹ค! ๊ทธ๋Ÿฌ๋‚˜์ด ๋ฌธ์ œ์— ๊ด€ํ•œ ์ •๋ณด๋ฅผ README ๋ฐ ๋ฌธ์„œ / ์˜ˆ์ œ์— ์ถ”๊ฐ€ํ•˜๋Š” ๊ฒƒ์ด ์ข‹์Šต๋‹ˆ๋‹ค. ๋™์  ์ฝ˜ํ…์ธ ๊ฐ€ ์‹ค์ œ๋กœ ๋ผ์ด๋ธŒ๋Ÿฌ๋ฆฌ์—์„œ ์ง€์›๋˜์ง€ ์•Š๊ณ  ๊ณ ์ • / ์•Œ๋ ค์ง„ ํฌ๊ธฐ์˜ ํ•ญ๋ชฉ์—๋งŒ ์œ ์šฉํ•˜๋‹ค๋Š” ์‚ฌ์‹ค์„ ํŒŒ์•…ํ•˜๋Š” ๋ฐ ๊ฝค ์‹œ๊ฐ„์ด ๊ฑธ๋ ธ์Šต๋‹ˆ๋‹ค. README์— ์ถ”๊ฐ€ โ€‹โ€‹ํ•  ์ˆ˜์žˆ๋Š” ๋ฉ‹์ง„ FAQ ์„น์…˜์ด ์žˆ๋‹ค๊ณ  ์ƒ๊ฐํ•ฉ๋‹ˆ๋‹ค.

ํ…Œ์ด๋ธ” / ๊ทธ๋ฆฌ๋“œ / ํŠธ๋ฆฌ๋ฅผ ์ฐพ๊ณ  ์žˆ๋‹ค๋ฉด VariableSizeGrid ์— ๊ตฌ์ถ• ๋œ https://autodesk.github.io/react-base-table/examples/dynamic-row-heights ์ข‹์€ ์‹œ์ž‘์ด ๋  ๊ฒƒ์ž…๋‹ˆ๋‹ค.

@ tony-scio InfiniteLoader์™€ ํ•จ๊ป˜ 1.6.0-alpha.1์˜ DynamicSizeList๋ฅผ ์‚ฌ์šฉํ•˜๊ธฐ์œ„ํ•œ ์ž‘์—… ์ฝ”๋“œ ๋ฐ ์ƒ์ž๋ฅผ ๊ณต์œ ํ•ด ์ฃผ์‹œ๊ฒ ์Šต๋‹ˆ๊นŒ? ๊ฐ์‚ฌํ•ฉ๋‹ˆ๋‹ค. ์ •๋ง ๊ฐ์‚ฌํ•˜๊ฒ ์Šต๋‹ˆ๋‹ค.

๋ˆ„๊ตฌ๋“ ์ง€ react-beautiful-dnd์™€ ํ•จ๊ป˜ ์ผํ•˜๊ธฐ ์œ„ํ•ด ์ด๊ฒƒ์„ ์–ป์—ˆ์Šต๋‹ˆ๊นŒ? ๋“œ๋ž˜๊ทธํ•˜๋ฉด ํ•ญ๋ชฉ์ด ์„œ๋กœ ์œ„๋กœ ์ ํ”„ํ•˜๋Š” ๊ฒƒ์ฒ˜๋Ÿผ ๋ณด์ž…๋‹ˆ๋‹ค.

๋ˆ„๊ตฌ๋“ ์ง€ react-beautiful-dnd์™€ ํ•จ๊ป˜ ์ผํ•˜๊ธฐ ์œ„ํ•ด ์ด๊ฒƒ์„ ์–ป์—ˆ์Šต๋‹ˆ๊นŒ? ๋“œ๋ž˜๊ทธํ•˜๋ฉด ํ•ญ๋ชฉ์ด ์„œ๋กœ ์œ„๋กœ ์ ํ”„ํ•˜๋Š” ๊ฒƒ์ฒ˜๋Ÿผ ๋ณด์ž…๋‹ˆ๋‹ค.

๋‚˜๋Š” ๋˜ํ•œ์ด ๋Œ€๋‹ต์„ ๊ธฐ๋‹ค๋ฆด ๊ฒƒ์ž…๋‹ˆ๋‹ค : D

[๋„์›€]
์ด ๋งํฌ์—๋Š” ํ‘œ์‹œ ํ•  ์ฝ”๋“œ๊ฐ€ ์—†์Šต๋‹ˆ๋‹ค.
๋™์  ํฌ๊ธฐ ๋ชฉ๋ก ์ˆ˜์ง
์ด ๋Šฅ๋ ฅ์ด ํ•„์š”ํ•ฉ๋‹ˆ๋‹ค.
๊ฐ์‚ฌ

[๋„์›€]
์ด ๋งํฌ์—๋Š” ํ‘œ์‹œ ํ•  ์ฝ”๋“œ๊ฐ€ ์—†์Šต๋‹ˆ๋‹ค.
๋™์  ํฌ๊ธฐ ๋ชฉ๋ก ์ˆ˜์ง
์ด ๋Šฅ๋ ฅ์ด ํ•„์š”ํ•ฉ๋‹ˆ๋‹ค.
๊ฐ์‚ฌ

https://react-window-next.now.sh/#/examples/list/dynamic -size

์ด๊ฒƒ์— ๋Œ€ํ•œ ์—…๋ฐ์ดํŠธ๊ฐ€ ์žˆ์Šต๋‹ˆ๊นŒ? ์šฐ๋ฆฌ๊ฐ€ ํ•  ์ˆ˜์žˆ๋Š” ๊ฒƒ๊ณผ ๋น„์Šทํ•œ ๊ฒƒ์ด ํ•„์š”ํ•ฉ๋‹ˆ๋‹ค (์ผ๋ฐ˜์ ์œผ๋กœ ๋งค์šฐ ์ ์ง€ ๋งŒ ๊ฒฝ์šฐ์— ๋”ฐ๋ผ ๋งŽ์„ ์ˆ˜ ์žˆ์Œ). ๋Œ€ํ˜• ์‘๋‹ต ๊ทธ๋ฆฌ๋“œ ํ•ญ๋ชฉ ๋ชฉ๋ก์„ ๋ Œ๋”๋งํ•ฉ๋‹ˆ๋‹ค (๋†’์ด๋Š” ๋™์ ์ด๋ฉฐ ๋‹ค์–‘ํ•œ ํ…์ŠคํŠธ ๋žฉ ๋“ฑ์œผ๋กœ ๋ชจ๋ฐ”์ผ์—์„œ ๋ณ€๊ฒฝ๋จ). ์ด ์‚ฌ์šฉ ์‚ฌ๋ก€๋ฅผ ์ฒ˜๋ฆฌ ํ•  ์ˆ˜ โ€‹โ€‹์žˆ๋‹ค๋ฉด react-window ๊ฐ€ ๊ฒŒ์ž„ ์ฒด์ธ์ €๊ฐ€ ๋  ๊ฒƒ์ด๋ผ๊ณ  ์ƒ๊ฐํ•ฉ๋‹ˆ๋‹ค. ๊ทธ๋ ‡์ง€ ์•Š์€ ๊ฒฝ์šฐ ์‹ ๋ขฐํ•  ์ˆ˜์žˆ๋Š” ๋Œ€์•ˆ์ด ์žˆ์Šต๋‹ˆ๊นŒ?

์ด๊ฒƒ์— ๋Œ€ํ•œ ์—…๋ฐ์ดํŠธ๊ฐ€ ์žˆ์Šต๋‹ˆ๊นŒ? ์šฐ๋ฆฌ๊ฐ€ ํ•  ์ˆ˜์žˆ๋Š” ๊ฒƒ๊ณผ ๋น„์Šทํ•œ ๊ฒƒ์ด ํ•„์š”ํ•ฉ๋‹ˆ๋‹ค (์ผ๋ฐ˜์ ์œผ๋กœ ๋งค์šฐ ์ ์ง€ ๋งŒ ๊ฒฝ์šฐ์— ๋”ฐ๋ผ ๋งŽ์„ ์ˆ˜ ์žˆ์Œ). ๋Œ€ํ˜• ์‘๋‹ต ๊ทธ๋ฆฌ๋“œ ํ•ญ๋ชฉ ๋ชฉ๋ก์„ ๋ Œ๋”๋งํ•ฉ๋‹ˆ๋‹ค (๋†’์ด๋Š” ๋™์ ์ด๋ฉฐ ๋‹ค์–‘ํ•œ ํ…์ŠคํŠธ ๋žฉ ๋“ฑ์œผ๋กœ ๋ชจ๋ฐ”์ผ์—์„œ ๋ณ€๊ฒฝ๋จ). ์ด ์‚ฌ์šฉ ์‚ฌ๋ก€๋ฅผ ์ฒ˜๋ฆฌ ํ•  ์ˆ˜ โ€‹โ€‹์žˆ๋‹ค๋ฉด react-window ๊ฐ€ ๊ฒŒ์ž„ ์ฒด์ธ์ €๊ฐ€ ๋  ๊ฒƒ์ด๋ผ๊ณ  ์ƒ๊ฐํ•ฉ๋‹ˆ๋‹ค. ๊ทธ๋ ‡์ง€ ์•Š์€ ๊ฒฝ์šฐ ์‹ ๋ขฐํ•  ์ˆ˜์žˆ๋Š” ๋Œ€์•ˆ์ด ์žˆ์Šต๋‹ˆ๊นŒ?

@JavaJamie๋Š” ํŠน๋ณ„ํžˆ ๋Œ€์•ˆ์„ ์š”์ฒญ -react -virtuoso ๋ผ์ด๋ธŒ๋Ÿฌ๋ฆฌ ๋Š” ๋™์  ์ฝ˜ํ…์ธ  ์ธก์ •์„์œ„ํ•œ ๋‚ด์žฅ ์ง€์›์„ ์ œ๊ณตํ•ฉ๋‹ˆ๋‹ค. ๋ฉด์ฑ… ์กฐํ•ญ : ๋‚˜๋Š” ๊ทธ๊ฒƒ์˜ ์ €์ž์ž…๋‹ˆ๋‹ค.

@JavaJamie๋Š” ํŠน๋ณ„ํžˆ ๋Œ€์•ˆ์„ ์š”์ฒญ -react -virtuoso ๋ผ์ด๋ธŒ๋Ÿฌ๋ฆฌ ๋Š” ๋™์  ์ฝ˜ํ…์ธ  ์ธก์ •์„์œ„ํ•œ ๋‚ด์žฅ ์ง€์›์„ ์ œ๊ณตํ•ฉ๋‹ˆ๋‹ค. ๋ฉด์ฑ… ์กฐํ•ญ : ๋‚˜๋Š” ๊ทธ๊ฒƒ์˜ ์ €์ž์ž…๋‹ˆ๋‹ค.

react-virtuoso๋Š” ๋ฐ˜์‘ ์ฐฝ์˜ ํฌ๊ธฐ๋„ ๋‘ ๋ฐฐ์ž…๋‹ˆ๋‹ค. ํ•ญ์ƒ ์ข…์†์„ฑ ํฌ๊ธฐ๋ฅผ ์—ผ๋‘์— ๋‘์–ด์•ผํ•ฉ๋‹ˆ๋‹ค.

https://bundlephobia.com/[email protected]
https://bundlephobia.com/[email protected]

๋‚˜๋Š”์ด ๋…ธ๋ ฅ์„ ๋งˆ์น  ์‹œ๊ฐ„์ด๋‚˜ ์—๋„ˆ์ง€๊ฐ€ ์—†๋‹ค๋Š” ์‚ฌ์‹ค์„ ๋ฐ›์•„ ๋“ค์˜€๋‹ค. ๋ˆ„๊ตฌ๋“ ์ง€ ๋‚ด๊ฐ€ ์‹œ์ž‘ํ•œ ์ง€์ ์— ๋“ค์–ด๊ฐ€์„œ ๋๋‚ด๊ณ  ์‹ถ๋‹ค๋ฉด ๋‹น์‹ ์˜ ๋„์›€์„ ํ™˜์˜ํ•ฉ๋‹ˆ๋‹ค. (์ƒˆ๋กœ์šด List ๋ฐ Grid ๊ตฌ์„ฑ ์š”์†Œ๋กœ์„œ ๋ฒ„์ „ 2 ๋ฆด๋ฆฌ์Šค์— ์–ด๋–ป๊ฒŒ ์ ์šฉ๋˜๋Š”์ง€์— ๋Œ€ํ•ด์„œ๋Š” ๋ฌธ์ œ # 302๋ฅผ ์ฐธ์กฐํ•˜์‹ญ์‹œ์˜ค.)

์šฐ๋ฆฌ๋Š” ์‹ค์ œ๋กœ ์ž˜ ์ž‘๋™ํ•˜๋Š” ๊ฐ€์‹œ์„ฑ ์„ผ์„œ๋ฅผ ์‚ฌ์šฉํ•˜๋„๋ก ์ฒ˜์Œ๋ถ€ํ„ฐ ๋ฌด์–ธ๊ฐ€๋ฅผ ๊ตฌํ˜„ํ–ˆ์Šต๋‹ˆ๋‹ค.

๋‚˜๋Š” ๊ทธ๊ฒƒ์„ OSS ๋˜๋Š” ๋‹น์‹ ์ด ๊ทธ๊ฒƒ์„ ๋œฏ์–ด ๋‚ด๊ณ  ์ƒˆ ํ”„๋กœ์ ํŠธ๋ฅผ ๋งŒ๋“ค๊ฑฐ๋‚˜ ์—ฌ๊ธฐ๋กœ ์˜ฎ๊ธฐ๊ณ  ์‹ถ๋‹ค๋ฉด ๋‹น์‹ ๋“ค์—๊ฒŒ ์˜ฌ๋ฐ”๋ฅธ ์œ„์น˜๋ฅผ ๊ฐ€๋ฆฌํ‚ฌ ์ˆ˜ ์žˆ์Šต๋‹ˆ๋‹ค.

ํ•œ ๊ฐ€์ง€ ํŠธ๋ฆญ์€ '๋ธ”๋ก'์„ ์‚ฌ์šฉํ•˜์—ฌ ์„ฑ๋Šฅ์„ ๋†’์ผ ์ˆ˜ ์žˆ๋‹ค๋Š” ๊ฒƒ์ž…๋‹ˆ๋‹ค. ๊ธฐ๋ณธ์ ์œผ๋กœ ๊ฐ ํ–‰์„ ๊ฐ€์ ธ ์™€์„œ ์‹ค์ œ๋กœ 25 ๊ฐœ ํ•ญ๋ชฉ์˜ ์ƒ์œ„ ๋ธ”๋ก์— ๋„ฃ์€ ๋‹ค์Œ ํ•„์š”ํ•  ๋•Œ ๊ต์ฒดํ•ฉ๋‹ˆ๋‹ค.

@burtonator ์ •๋ง ๋„์›€์ด ๋  ๊ฒƒ์ž…๋‹ˆ๋‹ค

๋ˆ„๊ตฌ๋‚˜ DynamicSizeList๋ฅผ ์‚ฌ์šฉํ•˜์—ฌ ๋ฒ„๊ทธ์—†๋Š” react-select ๊ตฌํ˜„์„ ์ œ๊ณต ํ•  ์ˆ˜ ์žˆ์Šต๋‹ˆ๊นŒ?
ํ•จ๊ป˜ ์ž˜ ์ž‘๋™ํ•˜์ง€ ์•Š์Šต๋‹ˆ๋‹ค.
ํ˜„์žฌ ๋‘ ๊ฐ€์ง€ ๋ฌธ์ œ์— ์ง๋ฉด ํ•ด ์žˆ์Šต๋‹ˆ๋‹ค (์Šคํฌ๋ฆฐ ์ƒท์ด ์—†์–ด์„œ ์ฃ„์†กํ•ฉ๋‹ˆ๋‹ค).

  1. ๋ชจ๋“  ํ•ญ๋ชฉ์—๋Š” style={position: absolute, left: 0, top: 0} ๊ฐ€ ์žˆ์Šต๋‹ˆ๋‹ค. ๋ชจ๋“  ์˜ต์…˜์ด ์„œ๋กœ ์œ„์— ์žˆ๊ธฐ ๋•Œ๋ฌธ์—์ด ์Šคํƒ€์ผ์„ ์‚ฌ์šฉํ•  ์ˆ˜ ์—†์Šต๋‹ˆ๋‹ค.
  2. ์Šคํƒ€์ผ ์†Œํ’ˆ์„ ์‚ฌ์šฉํ•˜์ง€ ์•Š์œผ๋ฉด ๋ชฉ๋ก์ด ์ž˜ ํ‘œ์‹œ๋˜์ง€๋งŒ ์กฐ๊ธˆ ์Šคํฌ๋กคํ•˜๋ฉด ์˜ต์…˜์ด์žˆ๋Š” ๋ชฉ๋ก์˜ ์ผ๋ถ€๊ฐ€ ์ค„์–ด๋“ค๊ณ  ์ „์ฒด ๋†’์ด๋Š” ๋ณ€๊ฒฝ๋˜์ง€ ์•Š์Šต๋‹ˆ๋‹ค. ๋”ฐ๋ผ์„œ ์Šคํฌ๋กคํ•˜๋ฉด ์‹ค์ œ ์˜ต์…˜ x ํ”ฝ์…€๊ณผ ๊ธธ์ด x ํ”ฝ์…€ ๊ณต๋ฐฑ์ด ๋‚˜ํƒ€๋‚ฉ๋‹ˆ๋‹ค.

๋‘ ๊ฐ€์ง€์˜ ์ž‘๋™ ์˜ˆ๋ฅผ ์ฐพ์„ ์ˆ˜ ์—†์Šต๋‹ˆ๋‹ค.
Chrome์—์„œ 1.9.0 ํฌํฌ๋ฅผ ์‚ฌ์šฉํ•œ๋‹ค๋Š” ์ ์— ์œ ์˜ํ•˜๊ฒ ์Šต๋‹ˆ๋‹ค.

ํŽธ์ง‘ํ•˜๋‹ค. ์œ„์˜ ์ˆจ๊ฒจ์ง„ ๋Œ“๊ธ€ ์„น์…˜์—์„œ ๋‹ต์„ ์ฐพ์•˜์Šต๋‹ˆ๋‹ค. https://github.com/bvaughn/react-window/issues/6#issuecomment -509016422

์Šคํฌ๋กค ๋ฌธ์ œ์— ๋Œ€ํ•œ ํ•œ ๊ฐ€์ง€ ๋‹จ์ˆœํ™”๋Š” ์Šคํฌ๋กค์ด ๋ทฐํฌํŠธ ๋†’์ด๊ฐ€ ๋Œ€๋žต ํ•œ ๊ฐœ ์ด์ƒ ๋–จ์–ด์ ธ์žˆ๋Š” ๊ฒฝ์šฐ ์Šคํฌ๋กค ๋ง‰๋Œ€๋ฅผ ์‚ฌ์šฉํ•˜์—ฌ ํ”ฝ์…€ ์œ„์น˜ ๋Œ€์‹  ๋ชฉ๋ก์—์žˆ๋Š” ํ•ญ๋ชฉ์˜ ์ธ๋ฑ์Šค๋ฅผ ๋‚˜ํƒ€๋‚ด๋Š” ๊ฒƒ์ž…๋‹ˆ๋‹ค. ๊ตฌ์„ฑ ์š”์†Œ๋Š” X ํ”ฝ์…€์„ "์•„๋ž˜๋กœ ์Šคํฌ๋กค"ํ•˜๋Š” ๋Œ€์‹  ์›ํ•˜๋Š” ์ธ๋ฑ์Šค ์ฃผ๋ณ€์˜ ํ•ญ๋ชฉ์„ ๋ Œ๋”๋งํ•ฉ๋‹ˆ๋‹ค. ์ค‘๊ฐ„ ์•„๋ž˜๋กœ ํ•ญ๋ชฉ์„ ์ธ๋ฑ์Šค N / 2์— ๋ Œ๋”๋งํ•˜๊ณ  ๋งจ ์•„๋ž˜์— ํ•ญ๋ชฉ์„ ์ธ๋ฑ์Šค N-1์— ๋ Œ๋”๋งํ•ฉ๋‹ˆ๋‹ค.

๊ทธ๋Ÿฌ๋ฉด ๊ตฌ์„ฑ ์š”์†Œ๊ฐ€ ํฌ๊ธฐ๋ฅผ ๋ Œ๋”๋งํ•˜๊ณ  ๊ณ„์‚ฐํ•˜๋Š” ๋™์•ˆ ์Šคํฌ๋กค ์ธ์˜ ์ง€์—ฐ์—†์ด ๋ชฉ๋ก์˜ ์ค‘๊ฐ„ ๋˜๋Š” ๋์œผ๋กœ ์ง์ ‘ ์ธ ์Šคํฌ๋กค์ด ๊ฐ€๋Šฅํ•ฉ๋‹ˆ๋‹ค. ์ง€๊ธˆ์€ ๋งค์šฐ ๊ธด VariableSizeList ๊ตฌ์„ฑ ์š”์†Œ์˜ ๊ฒฝ์šฐ ์Šคํฌ๋กค ์ธ์ด ์›€์ง์ด๋Š” ๊ฒƒ๋ณด๋‹ค ์ปค์„œ๊ฐ€ ๋” ๋นจ๋ฆฌ ๋“œ๋ž˜๊ทธ๋˜๋ฏ€๋กœ ์•„๋ž˜์ชฝ์œผ๋กœ ์Šคํฌ๋กคํ•˜๋Š” ๊ฒƒ์ด ๊ฑฐ์˜ ๋ถˆ๊ฐ€๋Šฅํ•ฉ๋‹ˆ๋‹ค.

์ด ํŽ˜์ด์ง€๊ฐ€ ๋„์›€์ด ๋˜์—ˆ๋‚˜์š”?
0 / 5 - 0 ๋“ฑ๊ธ‰