Chat Board

8358 단어 React후크
마지막 4일간은, 어플리케이션다운 UI 의 샘플을 소개해 갑니다. 오늘은 메시지 앱에서 자주 보는 chat board입니다.

아쉽게도 본작은 현재 iOS safari 등으로 하부 고정 입력 영역의 거동 의심이 해결되지 않았습니다. 메시지가 추가될 때마다 스크롤 위치를 이동해 말풍선을 표시하는 처리는 어딘가에서 이용할 수 있다고 생각합니다.
code: github/$ yarn 1222






메시지 입력


Input 구성 요소는 내부적으로 입력 텍스트를 보유합니다. onCommitMessage 의 callback 에서 items 를 업데이트합니다.

components/index.tsx
export default (props: Props) => {
  const [items, updateItems] = useState<Item[]>([])
  return (
    <div className={props.className}>
      <List items={items} />
      <Input
        onCommitMessage={message => {
          const newItem: Item = {
            createdAt: new Date(),
            message
          }
          updateItems(_items => [...items, newItem])
        }}
      />
    </div>
  )
}

메시지 삽입


props.items 로 받는 메세지 배열이 변화했을 때, 풍선 컴퍼넌트를 생성, 컴퍼넌트용 배열에 보관 유지합니다. 이렇게하면 마운트 된 구성 요소의 rerender를 억제 할 수 있습니다.

components/list.tsx
const View = (props: Props) => {
  const nodeRef = useRef({} as HTMLDivElement)
  const [items, updateItems] = useState<JSX.Element[]>([])
  useEffect(() => {
    if (nodeRef.current === null) return
    const {
      height
    } = nodeRef.current.getBoundingClientRect()
    window.scrollTo(0, height)
  })
  useEffect(
    () => {
      if (props.items.length === 0) return
      updateItems(_items => {
        const newItem = props.items[props.items.length - 1]
        _items.push(
          <ItemComponent
            key={newItem.createdAt.getTime()}
            createdAtLabel={getTimeLabel(newItem.createdAt)}
            message={newItem.message}
          />
        )
        return _items
      })
    },
    [props.items]
  )
  return (
    <div className={props.className} ref={nodeRef}>
      {items}
    </div>
  )
}

좋은 웹페이지 즐겨찾기