ChatView

ChatView is a component (and a set of helpers) that provides a drop-in channel view + thread view switcher. It lets users toggle views without you building that logic yourself. It includes:

  • ChatView - provider that stores the current view
  • ChatView.Selector - switches the active view
  • ChatView.Channels - renders children when view is channels
  • ChatView.Threads - renders children when view is threads, and exposes ThreadsViewContext for active thread selection
  • ChatView.ThreadAdapter - reads the active thread from ThreadsViewContext and forwards it to ThreadProvider

Best Practices

  • Use ChatView when you need a clear channel/thread switcher without custom state.
  • Keep ChatView.Selector visible and accessible for quick context switching.
  • Use ThreadAdapter to avoid manual thread wiring when possible.
  • For custom threads views, use useActiveThread to manage lifecycle correctly.
  • Keep thread view rendering lightweight to avoid expensive toggles.

Basic Usage

import {
  Chat,
  ChatView,
  ChannelList,
  Channel,
  ThreadList,
  Thread,
  useCreateChatClient,
} from "stream-chat-react";

const App = () => {
  const chatClient = useCreateChatClient(/*...*/);

  if (!chatClient) return null;

  return (
    <Chat client={chatClient}>
      <ChatView>
        <ChatView.Selector />
        {/* Channel View */}
        <ChatView.Channels>
          <ChannelList />
          <Channel>{/*...*/}</Channel>
        </ChatView.Channels>
        {/* Thread View */}
        <ChatView.Threads>
          <ThreadList />
          <ChatView.ThreadAdapter>
            <Thread />
          </ChatView.ThreadAdapter>
        </ChatView.Threads>
      </ChatView>
    </Chat>
  );
};

Custom Threads View

This section shows how to build a custom threads view using the core components and hooks.

Required Components & Hooks

These components and hooks are required for your own implementation to work properly:

  • ThreadList
  • ThreadListItem - provider for ThreadListItemUi with thread data; use it to wire custom click handling
  • ThreadProvider - "adapter" for Thread component to work properly with Thread instance
  • Thread - renders the thread UI with MessageList and MessageInput configured for threads
  • useActiveThread - takes your selected thread instance and handles its activity state (Thread.activate() & Thread.deactivate()) based on document focus and visibility

Building Custom Threads View

import {
  ThreadList,
  ThreadListItem,
  ThreadProvider,
  Thread,
  WithComponents,
  useActiveThread,
} from "stream-chat-react";

export const CustomThreadsView = () => {
  const [activeThread, setActiveThread] = useState(undefined);

  useActiveThread({ activeThread });

  return (
    <div className="custom-threads-view">
      <ThreadList
        virtuosoProps={{
          itemContent: (_, thread) => (
            <ThreadListItem
              thread={thread}
              threadListItemUiProps={{
                "aria-selected": thread === activeThread,
                onClick: () => {
                  setActiveThread(thread);
                },
              }}
            />
          ),
        }}
      />

      {activeThread && (
        <ThreadProvider thread={activeThread}>
          <Thread />
        </ThreadProvider>
      )}
    </div>
  );
};