Skip to content

ChatInput

Composite input component with auto-resizing textarea and send action bar, designed for chat scenarios.

Basic Usage

tsx
import { ChatInput } from '@airo-ui/react'
import { useState } from 'react'

function Demo() {
  const [message, setMessage] = useState('')

  return (
    <ChatInput
      value={message}
      onChange={setMessage}
      placeholder="Type a message..."
      sendLabel="Send"
      onSend={(value) => console.log('Send:', value)}
    />
  )
}

Action Bar

Use actionsLeft or actionsRight to insert custom action buttons.

tsx
<ChatInput
  value={value}
  onChange={setValue}
  placeholder="Reply..."
  actionsLeft={
    <>
      <button className="chat-input-btn" title="Attachment">
        {/* Attachment icon */}
      </button>
      <button className="chat-input-btn" title="Voice">
        {/* Voice icon */}
      </button>
    </>
  }
/>

Deep Thinking

Enable the deep thinking toggle with showThinking.

tsx
import { useState } from 'react'

function Demo() {
  const [message, setMessage] = useState('')
  const [thinking, setThinking] = useState(false)

  return (
    <div>
      <ChatInput
        value={message}
        onChange={setMessage}
        placeholder="Type a message..."
        showThinking
        thinking={thinking}
        onThinkingChange={setThinking}
        thinkingLabel="Deep thinking"
      />
      <p style={{ marginTop: 8, fontSize: 13 }}>
        Thinking mode: {thinking ? 'On' : 'Off'}
      </p>
    </div>
  )
}

Model Select

Enable model selection with showModelSelect.

tsx
import { useState } from 'react'

const models = [
  { label: 'GPT-4o', value: 'gpt4o' },
  { label: 'Claude 3.5 Sonnet', value: 'claude3' },
  { label: 'DeepSeek V3', value: 'deepseek' },
]

function Demo() {
  const [message, setMessage] = useState('')
  const [model, setModel] = useState('claude3')

  return (
    <div>
      <ChatInput
        value={message}
        onChange={setMessage}
        placeholder="Type a message..."
        showModelSelect
        model={model}
        models={models}
        modelPlaceholder="Select model"
        onModelChange={setModel}
      />
      <p style={{ marginTop: 8, fontSize: 13 }}>
        Current model: {model}
      </p>
    </div>
  )
}

Combined

Deep thinking and model select can be enabled together.

tsx
<ChatInput
  value={message}
  onChange={setMessage}
  placeholder="Type a message..."
  showThinking
  thinking={thinking}
  onThinkingChange={setThinking}
  showModelSelect
  model={model}
  models={models}
  modelPlaceholder="Model"
  onModelChange={setModel}
/>

API

Props

NameTypeDefaultDescription
valuestring''Controlled value
placeholderstring'Type a message...'Input placeholder
disabledbooleanfalseDisabled
maxRowsnumber6Auto-resize max rows
sendLabelstring'Send'Send button text
showThinkingbooleanfalseShow deep thinking toggle
thinkingbooleanfalseDeep thinking state
thinkingLabelstring'Deep thinking'Deep thinking label text
showModelSelectbooleanfalseShow model select
modelstring''Currently selected model value
modelsChatInputModelOption[][]Model options list
modelPlaceholderstring'Select model'Model select placeholder
actionsLeftReact.ReactNode--Left side of action bar
actionsRightReact.ReactNode--Right side of action bar
onChange(value: string) => void--Value change handler
onSend(value: string) => void--Send handler
onFocus(e: FocusEvent) => void--Focus handler
onBlur(e: FocusEvent) => void--Blur handler
onThinkingChange(value: boolean) => void--Thinking state change handler
onModelChange(value: string) => void--Model change handler

ChatInputModelOption

NameTypeDescription
labelstringDisplay text
valuestringOption value

MIT License