Autosize для textarea

Компонент текстовой области (textarea) предназначен для ввода многострочного текста. В классической HTML-реализации высота такого поля фиксирована и не изменяется автоматически при вводе. В пользовательских интерфейсах это нередко приводит к неудобствам: текст выходит за пределы видимой области и требует прокрутки.

В библиотеке Naive UI предусмотрен механизм автоматического изменения высоты текстовой областиautosize. Он позволяет динамически подстраивать высоту textarea в зависимости от объёма введённого текста.

Автоматическое масштабирование особенно актуально для:

  • форм комментариев
  • полей описания
  • сообщений в чатах
  • редакторов заметок
  • административных панелей

Текстовая область в Naive UI

В библиотеке Naive UI текстовая область реализуется через компонент NInput с типом textarea.

Базовый пример:

<template>
  <n-input
    type="textarea"
    placeholder="Введите текст"
  />
</template>

Компонент автоматически наследует стили и поведение всей системы ввода Naive UI: валидацию, состояния disabled, readonly, а также поддержку v-model.


Свойство autosize

Для включения автоматического изменения высоты используется свойство autosize.

Простейший вариант:

<n-input
  type="textarea"
  autosize
/>

При использовании такого варианта:

  • высота поля увеличивается по мере ввода текста
  • прокрутка внутри textarea исчезает
  • высота адаптируется к количеству строк

Механизм работает за счёт вычисления фактической высоты содержимого и динамического изменения CSS-свойства height.


Ограничение минимальной и максимальной высоты

В реальных интерфейсах полностью свободное изменение высоты может нарушать компоновку страницы. Поэтому Naive UI позволяет задавать минимальное и максимальное количество строк.

Для этого autosize принимает объект параметров.

<n-input
  type="textarea"
  :autosize="{
    minRows: 3,
    maxRows: 6
  }"
/>

Параметры

Параметр Назначение
minRows минимальное количество строк
maxRows максимальное количество строк

Поведение компонента:

  • начальная высота соответствует minRows
  • при вводе текста поле увеличивается
  • при достижении maxRows появляется прокрутка

Это позволяет сохранить компактность интерфейса.


Пример адаптивного поля комментария

<template>
  <n-input
    v-model:value="comment"
    type="textarea"
    placeholder="Комментарий"
    :autosize="{
      minRows: 2,
      maxRows: 8
    }"
  />
</template>

<script setup>
import { ref } from 'vue'

const comment = ref('')
</script>

Особенности такого поля:

  • компактный начальный размер
  • плавное увеличение при наборе текста
  • ограничение роста до восьми строк

Подобная конфигурация широко используется в системах комментариев.


Работа с v-model

Компонент полностью поддерживает двустороннее связывание данных через v-model:value.

<n-input
  v-model:value="text"
  type="textarea"
  autosize
/>
const text = ref('')

Каждое изменение текста:

  • обновляет реактивное состояние
  • может быть использовано для валидации
  • может отправляться в API

Autosize никак не влияет на реактивность данных — он управляет только визуальной частью компонента.


Управление высотой через состояние

Параметры autosize можно изменять динамически.

<n-input
  type="textarea"
  :autosize="autosizeConfig"
/>
const autosizeConfig = ref({
  minRows: 2,
  maxRows: 5
})

Позже конфигурацию можно изменить:

autosizeConfig.value.maxRows = 10

После обновления состояния компонент автоматически пересчитает размеры.


Использование вместе с ограничением длины

Autosize часто комбинируется со свойством maxlength.

<n-input
  type="textarea"
  autosize
  maxlength="200"
/>

Если требуется отображать счётчик символов:

<n-input
  type="textarea"
  autosize
  maxlength="200"
  show-count
/>

Интерфейс получает сразу два механизма контроля:

  • динамическую высоту
  • ограничение длины текста

Поведение при удалении текста

Autosize работает в обе стороны.

Когда текст удаляется:

  • высота пересчитывается
  • поле уменьшается до минимального значения

Если задано minRows, компонент никогда не станет меньше этого значения.


Программное управление значением

В случаях, когда текст изменяется программно (например, при загрузке данных из API), autosize также корректно пересчитывает высоту.

<n-button @click="loadText">
  Загрузить текст
</n-button>

<n-input
  v-model:value="content"
  type="textarea"
  autosize
/>
function loadText() {
  content.value = `
  Большой текст,
  загруженный из сервера,
  который автоматически
  увеличит высоту textarea.
  `
}

После обновления значения:

  • компонент пересчитает высоту
  • textarea расширится до нужного размера

Использование внутри форм

Autosize часто применяется в компонентах форм NForm.

<n-form-item label="Описание">
  <n-input
    v-model:value="description"
    type="textarea"
    :autosize="{
      minRows: 4,
      maxRows: 10
    }"
  />
</n-form-item>

Такой подход обеспечивает:

  • визуальную консистентность формы
  • удобный ввод длинных текстов
  • сохранение структуры layout

Стилизация autosize textarea

Naive UI использует CSS-переменные и внутренние стили компонента. Однако дополнительные стили могут быть добавлены вручную.

Пример:

<n-input
  class="custom-textarea"
  type="textarea"
  autosize
/>
.custom-textarea textarea {
  line-height: 1.6;
  font-size: 14px;
}

Изменение line-height может влиять на расчёт высоты, поскольку autosize ориентируется на реальную высоту строки.


Особенности работы алгоритма autosize

Механизм автоматического масштабирования работает следующим образом:

  1. содержимое копируется во временный элемент
  2. вычисляется фактическая высота текста
  3. вычисляется высота строки
  4. рассчитывается итоговая высота
  5. устанавливается CSS-свойство height

Это позволяет:

  • корректно учитывать переносы строк
  • учитывать padding
  • учитывать шрифт и line-height

Ограничения autosize

Несмотря на удобство механизма, существуют некоторые особенности.

Изменение шрифта

Если шрифт изменяется динамически, возможен пересчёт высоты.

Сложные CSS-стили

Некоторые стили могут нарушать точность расчёта:

  • нестандартный line-height
  • box-sizing
  • нестандартные padding

Вложенные контейнеры

При использовании внутри flex-контейнеров высота может пересчитываться при изменении размеров родительского элемента.


Использование в чат-интерфейсах

Autosize особенно полезен для текстовых полей отправки сообщений.

<n-input
  v-model:value="message"
  type="textarea"
  placeholder="Сообщение"
  :autosize="{
    minRows: 1,
    maxRows: 4
  }"
/>

Такое поведение характерно для:

  • мессенджеров
  • систем поддержки
  • корпоративных чатов

Поле растёт по мере ввода сообщения и остаётся компактным при коротких текстах.


Комбинация с отправкой по Enter

В чатах часто используется отправка по клавише Enter.

<n-input
  v-model:value="message"
  type="textarea"
  autosize
  @keydown.enter="sendMessage"
/>

Для предотвращения переноса строки можно перехватывать событие.

function sendMessage(event) {
  event.preventDefault()
  // отправка сообщения
}

Autosize при этом продолжает корректно работать.


Использование в административных панелях

В админ-интерфейсах autosize применяется для:

  • описаний товаров
  • текстов уведомлений
  • комментариев модераторов
  • системных заметок

Пример:

<n-input
  v-model:value="productDescription"
  type="textarea"
  :autosize="{
    minRows: 5,
    maxRows: 15
  }"
/>

Такой диапазон строк позволяет вводить длинные тексты без нарушения структуры страницы.


Производительность

Autosize в Naive UI оптимизирован для минимального влияния на производительность.

Основные особенности реализации:

  • пересчёт выполняется только при изменении текста
  • используется кеширование размеров строки
  • отсутствуют дорогостоящие перерисовки

Даже при большом количестве textarea на странице компонент работает стабильно.


Рекомендации по использованию

Оптимальные сценарии использования autosize:

  • формы обратной связи
  • поля комментариев
  • чат-интерфейсы
  • редакторы заметок
  • CMS-панели

Рекомендуемые значения:

Сценарий minRows maxRows
комментарий 2 6
чат 1 4
описание 4 10
заметки 5 15

Правильно выбранные ограничения предотвращают чрезмерное расширение интерфейса и сохраняют удобство ввода текста.