# @hiyve/rn-collaboration

React Native collaboration components and hooks for Hiyve video conferencing.

Provides `Chat`, `Polls`, and `QA` components with companion `usePolls` and `useQA` hooks for managing real-time collaboration state via data messages. All components are presentation-only and receive data via props.

## Installation

```bash
npm install @hiyve/rn-collaboration @hiyve/rn-react @hiyve/rn-core react-native-webrtc
```

## Quick Start

### Chat

```tsx
import { View, Text } from 'react-native';
import { Chat } from '@hiyve/rn-collaboration';
import { useChat, useParticipants, useConnection } from '@hiyve/rn-react';

function ChatPanel() {
  const { messages, unreadCount, sendMessage, clearUnread } = useChat();
  const { localUserId } = useParticipants();
  const { error } = useConnection();

  return (
    <View style={{ flex: 1 }}>
      {error && <Text style={{ color: '#FF3B30', padding: 8 }}>{error}</Text>}
      <Chat
        messages={messages}
        localUserId={localUserId}
        onSend={sendMessage}
        unreadCount={unreadCount}
        onClearUnread={clearUnread}
      />
    </View>
  );
}
```

### Polls

```tsx
import { Polls, usePolls } from '@hiyve/rn-collaboration';
import { useRoom, useParticipants } from '@hiyve/rn-react';

function PollsPanel({ onSendDataMessage }) {
  const { localUserId } = useParticipants();
  const { isOwner } = useRoom();

  const { polls, createPoll, vote, closePoll, handleDataMessage } = usePolls({
    localUserId,
    onSendDataMessage,
    isOwner,
  });

  return (
    <Polls
      polls={polls}
      localUserId={localUserId}
      isOwner={isOwner}
      onCreatePoll={createPoll}
      onVote={vote}
      onClosePoll={closePoll}
    />
  );
}
```

### Q&A

```tsx
import { QA, useQA } from '@hiyve/rn-collaboration';
import { useRoom, useParticipants } from '@hiyve/rn-react';

function QAPanel({ onSendDataMessage }) {
  const { localUserId } = useParticipants();
  const { isOwner } = useRoom();

  const { questions, askQuestion, upvote, answerQuestion, handleDataMessage } = useQA({
    localUserId,
    onSendDataMessage,
    isOwner,
  });

  return (
    <QA
      questions={questions}
      localUserId={localUserId}
      isOwner={isOwner}
      onAskQuestion={askQuestion}
      onUpvote={upvote}
      onAnswerQuestion={answerQuestion}
    />
  );
}
```

## Components

### Chat

Full-featured chat interface with message bubbles, avatars, timestamps, and an input bar.

```tsx
<Chat
  messages={messages}
  localUserId={localUserId}
  onSend={sendMessage}
  unreadCount={unreadCount}
  onClearUnread={clearUnread}
/>
```

| Prop | Type | Default | Description |
|------|------|---------|-------------|
| `messages` | `ChatMessage[]` | -- | Messages to display |
| `localUserId` | `string` | -- | Local user ID (right-aligns local messages) |
| `onSend` | `(content: string) => void` | -- | Send handler |
| `onClearUnread` | `() => void` | -- | Clear unread count when chat is visible |
| `unreadCount` | `number` | `0` | Unread badge count in header |
| `showHeader` | `boolean` | `true` | Show header with title and badge |
| `showTimestamps` | `boolean` | `true` | Show message timestamps |
| `showAvatars` | `boolean` | `true` | Show avatar circles for remote messages |
| `colors` | `Partial<ChatColors>` | -- | Color overrides |
| `labels` | `Partial<ChatLabels>` | -- | Label overrides |

### Polls

Poll creation, voting, and results display. Room owners can create and close polls.

```tsx
<Polls
  polls={polls}
  localUserId={localUserId}
  isOwner={isOwner}
  onCreatePoll={createPoll}
  onVote={vote}
  onClosePoll={closePoll}
/>
```

| Prop | Type | Default | Description |
|------|------|---------|-------------|
| `polls` | `Poll[]` | -- | Polls to display |
| `localUserId` | `string` | -- | Local user ID (highlights voted option) |
| `isOwner` | `boolean` | -- | Whether user can create/close polls |
| `onCreatePoll` | `(question, type, options?) => void` | -- | Create handler. Type: `'multiple-choice' \| 'yes-no'` |
| `onVote` | `(pollId, optionId) => void` | -- | Vote handler |
| `onClosePoll` | `(pollId) => void` | -- | Close poll handler (owner only) |
| `colors` | `Partial<PollsColors>` | -- | Color overrides |
| `labels` | `Partial<PollsLabels>` | -- | Label overrides |

### QA

Question submission, upvoting, and answer display. Room owners can answer questions.

```tsx
<QA
  questions={questions}
  localUserId={localUserId}
  isOwner={isOwner}
  onAskQuestion={askQuestion}
  onUpvote={upvote}
  onAnswerQuestion={answerQuestion}
/>
```

| Prop | Type | Default | Description |
|------|------|---------|-------------|
| `questions` | `Question[]` | -- | Questions to display (sorted by upvotes) |
| `localUserId` | `string` | -- | Local user ID (highlights upvoted questions) |
| `isOwner` | `boolean` | -- | Whether user can answer questions |
| `onAskQuestion` | `(text: string) => void` | -- | Submit question handler |
| `onUpvote` | `(questionId: string) => void` | -- | Toggle upvote handler |
| `onAnswerQuestion` | `(questionId, answer) => void` | -- | Answer handler (owner only) |
| `colors` | `Partial<QAColors>` | -- | Color overrides |
| `labels` | `Partial<QALabels>` | -- | Label overrides |

## Hooks

### usePolls

Manages poll state and broadcasts actions via data messages.

```tsx
const { polls, createPoll, vote, closePoll, handleDataMessage } = usePolls({
  localUserId,
  localUserName,
  onSendDataMessage,
  isOwner,
});
```

**Options:**

| Option | Type | Description |
|--------|------|-------------|
| `localUserId` | `string` | Local user ID |
| `localUserName` | `string` | Local user display name |
| `onSendDataMessage` | `(data) => void` | Callback to broadcast data to all participants |
| `isOwner` | `boolean` | Whether user is room owner |

**Returns (`PollState`):**

| Return | Type | Description |
|--------|------|-------------|
| `polls` | `Poll[]` | All polls (active and closed) |
| `createPoll` | `(question, type, options?) => void` | Create and broadcast a new poll |
| `vote` | `(pollId, optionId) => void` | Cast a vote and broadcast |
| `closePoll` | `(pollId) => void` | Close a poll and broadcast |
| `handleDataMessage` | `(data) => void` | Process incoming poll data from remote users |

### useQA

Manages Q&A state and broadcasts actions via data messages.

```tsx
const { questions, askQuestion, upvote, answerQuestion, handleDataMessage } = useQA({
  localUserId,
  localUserName,
  onSendDataMessage,
  isOwner,
});
```

**Options:**

| Option | Type | Description |
|--------|------|-------------|
| `localUserId` | `string` | Local user ID |
| `localUserName` | `string` | Local user display name |
| `onSendDataMessage` | `(data) => void` | Callback to broadcast data to all participants |
| `isOwner` | `boolean` | Whether user is room owner |

**Returns (`QAState`):**

| Return | Type | Description |
|--------|------|-------------|
| `questions` | `Question[]` | All questions (answered and unanswered) |
| `askQuestion` | `(text: string) => void` | Submit and broadcast a question |
| `upvote` | `(questionId: string) => void` | Toggle upvote and broadcast |
| `answerQuestion` | `(questionId, answer) => void` | Answer and broadcast |
| `handleDataMessage` | `(data) => void` | Process incoming Q&A data from remote users |

## Customization

All components accept `colors` and `labels` props. Pass partial objects to override only what you need:

```tsx
<Chat
  colors={{
    localBubble: '#6366F1',
    sendButton: '#6366F1',
    headerBackground: '#1e1e3f',
  }}
  labels={{
    title: 'Nachrichten',
    placeholder: 'Nachricht eingeben...',
    send: 'Senden',
  }}
  // ... other props
/>
```

## Requirements

- React 18+
- React Native 0.70+
- `@hiyve/rn-core`
- `@hiyve/rn-react`

## Related Packages

- [`@hiyve/rn-react`](../rn-react) -- Provider, hooks, and core UI components
- [`@hiyve/rn-capture`](../rn-capture) -- Recording, Streaming, and Transcription
- [`@hiyve/rn-meeting`](../rn-meeting) -- Alerts, Meeting Summary, and Join Token
