Условный рендеринг

Учимся показывать или скрывать части интерфейса в зависимости от данных — без if внутри JSX.

Условный рендеринг — приём, при котором JSX выбирается на основе условия с помощью выражений: &&, тернарника или раннего return.

Тернарный оператор: одно из двух

Внутри JSX нельзя писать if (это инструкция). Зато можно тернарник — он возвращает значение, а значит, годится для { }:

function Status({ isOnline }) {
  return (
    <p>
      Пользователь {isOnline ? "в сети" : "не в сети"}
    </p>
  );
}

Тернарник выбирает одну из двух веток — удобно, когда нужно показать «или то, или это».

Оператор &&: показать или ничего

Когда нужно показать блок только если условие истинно (а иначе — ничего), используют &&:

function Cart({ items }) {
  return (
    <div>
      <h2>Корзина</h2>
      {items.length > 0 && <p>Товаров: {items.length}</p>}
    </div>
  );
}

Работает так: если левая часть true, выражение возвращает правую (JSX) и она рендерится; если false — возвращается false, а его React просто не рисует.

Опасная ловушка с нулём

Самая частая ошибка с &&: слева оказывается число 0. React рисует ноль (это валидное значение), и на экране появляется лишний «0». Посмотрим логику на чистом JS:

const count = 0;
console.log(count && "есть товары");   // вернёт 0, а не false
console.log(count > 0 && "есть товары"); // вернёт false — безопасно
const list = [];
console.log(list.length && "не пусто");        // 0 — отрисуется!
console.log(list.length > 0 && "не пусто");    // false — ничего

Вывод:

0
false
0
false

Вывод: слева от && ставьте булево условие (items.length > 0), а не само число (items.length). Иначе при пустом списке на странице вылезет «0».

Ранний return для крупных веток

Если в зависимости от условия меняется весь вывод, чище сделать ранний return до основного JSX:

function Profile({ user }) {
  if (!user) {
    return <p>Загрузка...</p>;
  }
  return (
    <div>
      <h1>{user.name}</h1>
      <p>{user.bio}</p>
    </div>
  );
}

Памятка

ЗадачаПриём
Одно из двух{cond ? A : B}
Показать или ничего{cond && A} (cond — булево!)
Совсем разный выводранний return

Итог

  • Тернарник {cond ? A : B} выбирает одну из двух веток; && — показывает блок или ничего.
  • Слева от && ставьте булево условие (length > 0), иначе React отрисует 0.
  • Для радикально разного вывода используйте ранний return.
Проверьте себя
1. Какой оператор удобен, чтобы показать блок ТОЛЬКО при истинном условии (иначе ничего)?
AТернарный оператор ?:
BЛогическое И &&
CОператор ||
DОператор ==
2. Почему {items.length && <p>...</p>} может вывести «0» на экран?
AReact всегда добавляет ноль
BПри пустом массиве length равен 0, а React рисует число 0
CЭто баг React
DПотому что length — это строка
3. Как безопаснее показать блок при непустом списке?
A{items.length && <p>...</p>}
B{items.length > 0 && <p>...</p>}
C{if (items.length) <p>...</p>}
D{items && <p>...</p> || 0}
Поддержать проект