[React] Reflow와 Repaint

은승균·2022년 8월 14일
1

Reflow와 Repaint

브라우저 렌더링 과정

우리가 사용하는 브라우저는 우리에게 시각적으로 화면에 여러 컨텐츠를 보여주기위해 일련의 과정을 거치게 된다. 컨텐츠를 다운로드 하는 것 부터 DOM트리와 CSSOM트리를 만든 후 Reflow와 Repaint라는 과정을 거치면서 화면에 여러 텍스트, 사진, 동영상 등을 보여준다.

Critical Rendering Path

브라우저 렌더링 과정 중 아래의 과정을 Critical Rendering Path라고 한다. 또는 PixelPipeline이라고도 한다.

DOM + CSSOM 구성

Render Tree

  • DOM tree + CSS tree를 조합
  • 요소에 컨텐츠와 스타일 포함

Layout

  • 요소에 대한 위치, 크기를 계산

Paint

  • 색 채워넣기

Composite

  • 각 레이어를 합성, 앞의 단계까 각 레이어로 쪼개져 진행되는데, 이것들을 합성한다

브라우저에서 어떤 이벤트가 발생하여 요소에 변화가 생긴다면 변화된 내용을 반영하기 위해 위의 단계를 다시 거치게 된다.

Reflow와 Repaint

브라우저에서 애니메이션을 다룰 때 주로 성능 문제가 발생하는데, Reflow와 Repaint는 렌더링 성능과 연관이 있다.

애니메이션의 원리

초당 수 십장의 사진을 보여줌으로써 자연스러운 움직임 처럼 보이게 한다.
초당 60프레임을 보여주어야 우리 눈에 자연스럽게 보인다.

애니메이션을 브라우저에서 보여준다는 것은 위의 Critical Render Path를 다시 거쳐야한다는 것을 의미한다. 하지만 너무 단시간에 많은 것을 보여주어야 한다면 브라우저는 재시간에 일을 끝내지 못해 사용자에게 보여주어야 할 시점에 보여주지 못하여 사용자는 이전 프레임 보게된다. 이런 현상이 우리가 흔히 말하는 *랙이 걸린다 라고 표현하는 현상이다.
이러한 현상은 브라우저 뿐만 아니라 CPU와 I/O 장치간에도 적용이 된다.

어쨌든! 랙이 걸리지 않고 부드럽게 사용자에게 보여주기 위해서는 Critical Render Path를 전부 거치는게 아니라 일부 과정만 거치면 더 부드럽게 보여줄 수 있을 것이다.

Reflow

width, height, position(위치나 크기)등이 변경된다면 Critical Render Path에서 요소의 위치와 크기를 결정하는 과정인 Layout과정을 거치지 않으면 안된다.
즉, 위치나 크기를 변경하게 된다면 전 과정을 모두 거쳐야 한다는 것을 의미한다.
이러한 동작(위치나 크기 변경)에 대해 Critical Render Path를 재실행하여 거치는 과정을 Reflow라고 한다.

Repaint

Reflow과정을 거쳐야 하는 때는 요소의 위치나 크기를 변경 했을 때이다. 그렇다면 위치나 크기를 변경하지 않고 색깔을 변경한다면 굳이 Layout 과정을 실행하지 않아도 된다.
즉, color, background-color, outline 등을 변경한다면 Critical Render Path에서 Layout 과정을 생략하고 바로 Paint과정을 거치는데 이러한 과정을 Repaint라고 한다

Reflow와 Repaint 모두 피하기

위치나 크기를 변경하면 Reflow 과정을, 색깔을 변경하면 Repaint 과정을 거친다. 그렇다면 Layout과 Paint과정을 모두 생략할 수 는 없을까?

GPU 도움 받기

GPU의 도움을 받으면 위의 두 과정을 모두 생략할 수 있다. 그 방법은 GPU가 관여할 수 있는 속성인 transform과 opacity 속성 등을 이용하는 것이다.

각 속성에 대한 영향

Reflow 발생 속성

Repaint 발생 속성

Reflow, Repaint 생략 가능 속성

  • transform
  • opacity

GPU 오버헤드?

GPU에 위임하여 처리하고 다시 처리된 것을 받아 적용한다고 했을 때 GPU와 CPU간의 통신에 대한 비용은 크지 않을까? 라는 고민을 할 수 있다.
분명히 전공 수업때도 CPU와 GPU간에 데이터를 공유할 때 주고 받는데에 오래 걸린다고 하였었으니...
인프런 강의에서 강사님의 답변을 받을 수 있었다.

브라우저가 GPU에 작업을 위임할 때, 흔히 우리가 생각하는 네트워크 통신처럼 시간이 걸는게 아니라 굉장히 빠른 프로세스 간의 통신이 이뤄집니다. 또한, 크롬 브라우저에서는 이미 GPU 프로세스를 포함한 여러 역할을 담당하는 프로세스들이 동작하고 있기 때문에 별도의 오버헤드 없이 해당 프로세스들 끼리 데이터를 주고 받을 수 있게 됩니다.
즉, CPU에서 처리함으로써 떨어지는 성능에 비하면 거의 무의미한 수준의 비용이기 때문에 오히려 빨라지는 것입니다.

즉, 프로세스 레벨에서의 시간은 네트워크 통신과 같은 애플리케이션 레벨에서보다 훨씬 빠르며, 브라우저에서 이미 GPU 프로세스가 동작하고 있기 때문에 따로 준비하는 오버헤드가 없다는 것으로 이해할 수 있었다.

profile
3대 500을 향해서

0개의 댓글