Files
LocalMind/docs/PLAN-chat-ux-improvements.md
T

169 lines
6.7 KiB
Markdown

# PLAN: Chat UX Improvements + Streaming Fix
> 🤖 **Agentes:** `@frontend-specialist` + `@mobile-developer`
> **Data:** 2026-03-04
---
## 🐛 Bug Crítico: ReadableStream not supported
**Causa raiz:** O `fetch` nativo do React Native (Hermes) não suporta `response.body.getReader()`. A implementação atual usa a Web Streams API que só funciona em navegadores.
**Solução:** Usar o pacote `react-native-sse` — cliente SSE leve feito para React Native, que usa `XMLHttpRequest` internamente (sem polyfills pesados).
```bash
pnpm add react-native-sse
```
Reescrever `chatCompletionStream()` em `services/lmStudioApi.ts` para usar `EventSource` do `react-native-sse` no mobile e manter `ReadableStream` no web via `Platform.OS`.
---
## 🧠 Brainstorm: Rendering de Markdown
### Contexto
Respostas de LLMs vêm em Markdown (code blocks, bold, listas, etc). Atualmente renderizamos como `<Text>` puro.
### Option A: `react-native-markdown-display`
- ✅ Leve, customizável por StyleSheet, suporta code blocks
- ❌ Manutenção irregular
- 📊 **Effort:** Low
### Option B: `@ronradtke/react-native-markdown-display` (fork mantido)
- ✅ Fork ativo e mantido, API idêntica, melhor suporte Expo
- ✅ Customização completa de estilos
- ❌ Sem syntax highlighting nativo (adicionável)
- 📊 **Effort:** Low
### Option C: Custom parser com regex
- ✅ Zero dependências, 100% controle
- ❌ Muito trabalho, bugs com edge cases
- 📊 **Effort:** High
### 💡 Recomendação
**Option B** (`@ronradtke/react-native-markdown-display`) — fork mantido, baixo esforço e cobre 95% dos casos.
---
## 📋 Plano de Implementação
### Fase 1: Bug Fix — Streaming (Prioridade Máxima)
#### [MODIFY] `services/lmStudioApi.ts`
- Instalar `react-native-sse`
- Reescrever `chatCompletionStream()` com dual strategy:
- **Web:** Manter `ReadableStream` (funciona nativamente)
- **Native (iOS/Android):** Usar SSE via `react-native-sse`
- Handling robusto de erros e abort
---
### Fase 2: Markdown Rendering
#### [ADD] Dependência
```bash
pnpm add @ronradtke/react-native-markdown-display
```
#### [MODIFY] `components/chat/MessageBubble.tsx`
- Substituir `<Text>` por `<Markdown>` nas mensagens do assistant
- Manter `<Text>` para mensagens do user (são texto simples)
- Estilizar code blocks com fundo escuro, fonte mono
- Estilizar bold, italic, listas, links
- Suporte a inline code com badge de destaque
---
### Fase 3: Message Actions (Copy, Edit, Resend)
#### [MODIFY] `components/chat/MessageBubble.tsx`
- Adicionar toolbar de ações abaixo de cada mensagem (aparece via long-press ou sempre visível para assistant)
- **Actions do Assistant:**
- 📋 Copy — copia conteúdo para clipboard (`Clipboard.setStringAsync`)
- 🔄 Regenerate — reenvia a última mensagem do user
- **Actions do User:**
- 📋 Copy — copia conteúdo
- ✏️ Edit — abre o texto no input para edição + reenvio
- 🗑️ Delete — remove mensagem
#### [MODIFY] `store/useAppStore.ts`
- Adicionar `deleteMessage(id)`
- Adicionar `editMessage(id, content)` — edita e reprocess
- Adicionar `regenerateLastResponse()` — remove última resposta + reenvia
#### [MODIFY] `components/chat/ChatInput.tsx`
- Suportar modo "edit" — pré-preencher input com texto da mensagem selecionada
- Mostrar indicador visual de que está editando (ex: badge "Editing" + botão cancelar)
#### [NEW] `components/chat/MessageActions.tsx`
- Componente de ações reutilizável
- Botões com ícones (Lucide): `Copy`, `Pencil`, `RefreshCw`, `Trash2`
- Touch targets 44px+ (Fitts' Law compliance)
- Haptic feedback nos botões (`expo-haptics`)
---
### Fase 4: UI/UX Polish
#### [MODIFY] `components/chat/MessageBubble.tsx`
- Avatar/ícone para assistant (Bot icon) e user
- Timestamp discreto abaixo da bolha
- Animação de entrada (fade in + slide up com `react-native-reanimated`)
#### [MODIFY] `app/chat/index.tsx`
- Empty state quando não há mensagens (ícone + texto de boas-vindas + sugestões de prompts clicáveis)
- Typing indicator animado (3 dots pulsando) enquanto `isStreaming` e conteúdo ainda vazio
#### [MODIFY] `components/chat/ChatInput.tsx`
- Auto-grow do input (já faz multiline, melhorar visual)
- Botão de "stop generation" (⏹️) visível durante streaming, substituindo o botão send
- Contador de caracteres sutil para mensagens longas
#### [MODIFY] `app/chat/_layout.tsx`
- Botão "New Chat" no header (limpa conversa)
---
## 💡 Sugestões Adicionais (Simples de Implementar)
1. **Sugestões de Prompts no Empty State** — 3-4 cards clicáveis com prompts exemplo ("Explique recursão", "Escreva um haiku") que preenchem o input ao tocar. Melhora onboarding e ajuda o user a começar.
2. **Persistência de Chat com AsyncStorage** — Salvar mensagens no dispositivo para não perder ao fechar o app. Usar `zustand/middleware` com `persist`.
3. **Haptic Feedback nas ações** — Vibração leve ao enviar mensagem, copiar, e deletar. Premium feel. (`expo-haptics` já está disponível no Expo).
4. **Scroll-to-bottom FAB** — Quando o user rola para cima e chega mensagem nova, mostrar um FAB "↓" no canto inferior para voltar ao final. Evita perder mensagens novas.
5. **Configuração de Temperature/Max Tokens no Chat** — Adicionar um menu de "Model Parameters" acessível pelo header (ícone de slider). Permite ajustar temperatura e max_tokens sem ir em Settings.
6. **Tema Dark Mode funcional** — O theme toggle existe mas as telas usam cores hardcoded (#FFFFFF, #F3F4F6). Conectar com o sistema `Colors` de `constants/theme.ts` para dark mode real.
7. **Indicador de tokens usados** — Mostrar contagem de tokens da resposta (retornado pelo `usage` da API) abaixo de cada mensagem assistant. Informativo para quem está testando modelos.
8. **System Prompt configurável** — Input nas Settings para definir o system prompt padrão que é enviado em toda conversa. Permite personalizar o "comportamento" do modelo.
---
## Verificação
1. Enviar mensagem → resposta deve aparecer via streaming (sem erro ReadableStream)
2. Resposta do assistant → renderizada com formatação markdown (code blocks, bold, listas)
3. Long-press em mensagem → botões de ação aparecem
4. Copiar → conteúdo no clipboard
5. Editar mensagem do user → input preenchido, reenvio funciona
6. Empty state → sugestões de prompt visíveis
7. Stop generation → streaming para imediatamente
8. Dark mode → todas as telas respeitam o tema
---
## Ordem de Execução Recomendada
| Fase | Prioridade | Esforço |
|------|-----------|---------|
| 1. Fix Streaming | 🔴 Crítico | Baixo |
| 2. Markdown | 🟠 Alto | Baixo |
| 3. Message Actions | 🟡 Médio | Médio |
| 4. UI/UX Polish | 🟢 Normal | Médio |
| 5+ Sugestões | 🔵 Nice-to-have | Baixo cada |