Если вы новичок в React, вы, вероятно, слышали о JSX или JavaScript XML - это XML-подобный код для элементов и компонентов. В этой статье мы собираемся взглянуть на то, что такое JSX и почему мы должны использовать его в наших приложениях React. Мы также рассмотрим, что такое элементы, и как мы можем отобразить их в DOM.

🤓 Хотите быть в курсе новостей веб-разработчиков?
🚀 Хотите, чтобы последние новости доставлялись прямо на ваш почтовый ящик?
🎉 Присоединяйтесь к растущему сообществу дизайнеров и разработчиков!

Подпишитесь на мою рассылку здесь → https://easeout.eo.page

Что такое JSX?

Как уже упоминалось, JSX - это XML-подобный код, который мы можем использовать при кодировании с помощью React. Он был разработан командой Facebook и призван обеспечить более лаконичный синтаксис, помогающий упростить работу разработчика. Давайте посмотрим на наш первый пример:

const greeting = <h1>Hello, World!</h1>;

Все просто, правда?

У нас нет ни String, ни HTML. Это JSX! Мы можем использовать его, чтобы использовать всю мощь JavaScript при создании наших элементов пользовательского интерфейса. И хотя это не обязательно, это, безусловно, чрезвычайно полезный инструмент - он отлично помогает понять, когда мы работаем с пользовательским интерфейсом внутри нашего кода JavaScript.

Использование JSX

Давайте расширим наш приведенный выше пример, включив в него встроенное выражение.

const user = 'Bob Burger';
const greeting = <h1>Hello, {user}</h1>;

ReactDOM.render(
  greeting,
  document.getElementById('root')
);

Мы используем фигурные скобки {}, чтобы вставить переменную в наше JSX-выражение. И в эти фигурные скобки мы можем вставить любое допустимое выражение JavaScript. Например, user.firstName или printName(user).

Примечание. Подробнее о рендеринге мы поговорим позже в этой статье, но пока не беспокойтесь о вышеупомянутом методе рендеринга!

Давайте встроим результат вызванной функции JavaScript:

function printName(user) {
  return user.firstName + ' ' + user.lastName;
}

const user = {
  firstName: 'Bob',
  lastName: 'Burger'
};

const greeting = (
  <h1>
    Hello, {printName(user)}!
  </h1>
);

ReactDOM.render(
  greeting,
  document.getElementById('root')
);

JSX под капотом

Так что же на самом деле происходит с JSX, когда мы рендерим компоненты?

function Greeting() {
  return <h1>Hello, World!</h1>
}

Каждый элемент, отображаемый компонентом Greeting, преобразуется в React.createElement вызовы. Приведенный выше пример переносится на:

function Greeting() {
  return React.createElement("h1", {}, "Hello, World!")
}

React.createElement ()

Давайте посмотрим на другой пример:

const greeting = (
  <h1 className="speak">
    Hello, world!
  </h1>
);

При компиляции этот код выглядит следующим образом:

const greeting = React.createElement(
  'h1',
  {className: 'speak'},
  'Hello, world!'
);

Оба этих кодовых блока идентичны. А по сути объект создается так:

const greeting= {
  type: 'h1',
  props: {
    className: 'speak',
    children: 'Hello, world!'
  }
};

Этот объект известен как элемент React, и он во многом похож на описание того, что вы видите на экране. React использует эти объекты для построения модели DOM и поддержания ее в актуальном состоянии.

По сути, JSX просто делает функцию React.createElement(component, props, …children) более приятной для глаз. Другой пример:

<Navbar backgroundColor = "purple" opacity = {0.8}>
  Menu bar
</Navbar>

Будет переведено на:

React.createElement(Navbar, {
  backgroundColor: "purple",
  opacity: 0.8
}, "Menu bar");

Давайте теперь перейдем к рассмотрению еще нескольких концепций ...

Реквизит в JSX

Мы подробно рассмотрим реквизит в моей следующей статье! А пока хорошо помнить, что при построении компонентов они часто будут отображать дочерние элементы, которым требуются данные для правильного отображения. Параметры, которые мы передаем, мы называем реквизитами. В JSX это можно сделать несколькими способами, например:

// Defaults to "true" if no value is passed
<MyComponent connected />
// String literals passed as props
<MyComponent user= "Bob Burger" />
// Expressions (below example will evaluate to 10)
<MyComponent total = {1 + 2 + 3 + 4} />
// Spread attributes: passes the whole props object
<MyComponent selected = {...this.state} />

Примечание: операторы if и for циклы не являются выражениями в JavaScript, поэтому их нельзя использовать в JSX напрямую! Вместо этого вы можете закодировать это так:

function NumberType(props) {
  let answer;
  if (props.number % 2 == 0) {
    answer = <strong>even</strong>;
  } else {
    answer = <i>odd</i>;
  }
  return <div>{props.number} is an {answer} number</div>;
}

Мы можем видеть, как наши свойства передаются в условное выражение, оцениваются и затем возвращаются - все через JSX.

Дети в JSX

По мере того, как ваши приложения становятся больше, вы обнаружите, что некоторым компонентам потребуется отображать дочерние элементы. И затем эти дочерние компоненты также должны будут отображать дочерние элементы и т. Д.! С JSX мы можем довольно хорошо управлять этими древовидными структурами элементов. Практическое правило - любые элементы, возвращаемые компонентом, становятся его дочерними элементами.

Давайте быстро рассмотрим способы рендеринга дочерних элементов с помощью JSX:

Строковые литералы

<MyComponent>I'm a child!</MyComponent>

В этом очень простом примере строка I’m a child является дочерним элементом MyComponent. И он доступен через props.children из MyComponent.

Элементы JSX как дочерние элементы

Допустим, мы хотим вернуть HTML-дочерний элемент <header>, у которого есть два собственных дочерних элемента: <Nav /> и <SearchBox />. Мы могли бы сделать это так:

function Header(props) {
  return (
    <header>
      <Nav />
      <SearchBox />
    </header>
  )
}

Выражения

Мы также можем передавать выражения как дочерние элементы для отображения в нашем пользовательском интерфейсе. Это было бы очень полезно для приложения со списком дел, например:

function TodoItem(props) {
  return <li>{props.content}</li>;
}

function TodoList() {
  const todos = ['paint house', 'buy more chips', 'conquer world'];
  return (
    <ul>
      {todos.map((content) => <TodoItem key={content} content={content} />)}
    </ul>
  );
}

Функции

Функции могут быть полезны при обработке повторения, например при отрисовке повторяющихся элементов пользовательского интерфейса. Мы можем создавать структуры, которые React будет автоматически отображать для нас.

Давайте посмотрим на пример, в котором мы используем функцию .map() для создания новых страниц на веб-сайте:

// Array of current pages
const pages = [
  {
    id: 1,
    text: "Home",
    link: "/"
  },
  {
    id: 2,
    text: "About",
    link: "/about"
  },
  {
    id: 3,
    text: "Contact",
    link: "/contact"
  }
];
// Renders a <ul> which generates the <li> children
function Nav() {
  return (
    <ul>
      {pages.map(page => {
        return (
          <li key={page.id}>
            <a href={page.link}>{page.text}</a>
          </li>
        );
      })}
    </ul>
  );
}

Чтобы добавить новую страницу на наш веб-сайт, нам просто нужно добавить новый объект в массив pages, а все остальное сделать React!

Элементы рендеринга

Как я уверен, вы видели в этой статье, что при работе с JSX мы работаем с элементами, которые будут отображаться на нашей странице. Элемент описывает то, что вы видите на экране:

const element = <h1>Hello!</h1>;

Несколько таких элементов при объединении образуют компоненты. Мы подробно рассмотрим компоненты в моей следующей статье!

Рендеринг наших элементов в DOM

Как правило, в нашем HTML-коде используется такой <div>:

<div id="root"></div> 

Это известно как наш узел DOM. Все внутри него обрабатывается React DOM.

И чтобы отобразить элемент React в нашем корневом узле, мы передаем оба элемента ReactDOM.render(), следующим образом:

const element = <h1>Hello!</h1>;
ReactDOM.render(element, document.getElementById('root'));

Hello! будет отображаться на нашей странице.

Обновление визуализированных элементов

Обратите внимание, что элементы React неизменяемы! После создания элемента вы не можете изменять его дочерние элементы или его атрибуты. Если вы хотите обновить пользовательский интерфейс, вам нужно будет создать новый элемент и передать его ReactDOM.render().

Готовы ли вы поднять свои навыки CSS на новый уровень? Начните прямо сейчас с моей новой электронной книги: Руководство по CSS: Полное руководство по современному CSS. Будьте в курсе всего, от основных концепций, таких как Flexbox и Grid, до более сложных тем, таких как анимация, архитектура и многое другое !!

Заключение

И вот так! Мы рассмотрели основы JSX и рендеринга. И я надеюсь, вы начинаете понимать, насколько полезны эти концепции для нас, разработчиков, создающих приложения на React.

Используя возможности JSX для передачи элементов в JavaScript, мы создаем очень работоспособный код. Структура JSX невероятно хорошо сочетается с React, и, несмотря на то, что JSX не является обязательным, он дает фантастический опыт разработки.

Надеюсь, эта статья оказалась для вас полезной! Вы можете подписаться на меня на Medium. Я тоже в Твиттере. Не стесняйтесь оставлять любые вопросы в комментариях ниже. Буду рад помочь!