Solve Problem/React Native

[React Native] 채팅화면을 구성하는 2가지 방법 (FlatList)

안다희 2023. 3. 27. 09:20
728x90

채팅화면을 구성하는 2가지 방법에 대해 알아봅시다!

(FlatList의 inverted, onContentSizeChange)

 

1. FlatList의 inverted prop 사용

const data = [
	"안녕하세요! 채팅을 입력해주세요",
	"안녕",
	"반갑습니다!",
	"나는 보라야",
]

  <FlatList
    inverted
    data={data.reverse()}
    renderItem={renderItem}
  />

(공통) inverted 적용 / (좌) data.reverse() 적용 전 / (우) data.reverse() 적용 후

inverted prop을 사용하면

data는 위가 아닌 아래부터 배치가 됩니다. (좌)

이 상태라면, data가 추가될 때마다 위에 쌓이게 됩니다.

따라서 data.reverse()를 통해 data의 순서를 역으로 세팅해줍니다. (우)

 

아주 간단하죠!

 

그런데 data의 첫원소인 "안녕하세요! 채팅을 입력해주세요"가 빨간박스의 좌상단이 아닌, 파란박스의 좌상단부터 배치되게 할 수는 없을까요?

 

그렇다면 inverted는 포기해야..😶‍🌫️

(하는 줄 알았는데 현구님께서 댓글을 달아주셨어요! 항상 감사합니다🔥🔥🔥)

// contentContainerStyle 에 아래 스타일을 준다.
{
  justifyContent: 'flex-end',
  flexGrow: 1 // 혹은 minHeight: '100%'
}

이렇게 스타일을 주면 아이템이 꽉 차지 않았을때도 위에서부터 정렬 시킬 수 있다고 합니다!

 

 

두번째 방법도 볼까요?

2. onContentSizeChange 이용

우선 코드는 아래와 같이 수정합니다.

const flatListRef = useRef<FlatList>(null);

<FlatList
    ref={flatListRef}
    data={data}
    onContentSizeChange={(w: number, h: number) => {
    	console.log(`[onContentSizeChange] width:${w}, height: ${h}`); // FlatList의 size가 변할 때마다 실행됨
        setTimeout(() => {
          flatListRef.current?.scrollToEnd({ animated: false });
        }, 30); // 0이면 안먹히는 경우도 있어서 0.03초 시간차 두고 scrollToEnd 실행.
    }}
    renderItem={renderItem}
/>

 

onContentSize는 FlatList의 사이즈가 바뀔 때마다 실행되는 함수입니다.

아이템은 FlatList의 최상단부터 차곡차곡 쌓이면서, FlatList 사이즈에 변화가 생길 때마다 맨 아래로 스크롤하는 함수를 실행하는 방법입니다.

data를 추가하면 onContentSizeChange의 scrollToEnd가 실행됨

짠! data를 추가하면 onContentSizeChange의 scrollToEnd가 실행되어 FlatList 최하단에 포커싱이 되죠!

 

(하지만 가끔 scrollToEnd가 실행되지 않는 경우도 있어, 0.03초 뒤에 scrollToEnd를 실행하는 꼼수를 써봤습니다.)

 


이렇게 해서 채팅화면을 구성하는 2가지 방법에 대해 알아보았습니다😄

더 좋은 방법이 있다면 댓글을 남겨주세요~! 함께 배워가요!

출처: https://mingos-habitat.tistory.com/34 [밍고의서식지:티스토리]