Привет, меня зовут Infanty, мой профиль в LinkedIn.
Я пишу how-to статьи на редкие темы или статьи обзоры - для себя и тех кто со мной работает.

3. Когда необходимо организовать единый контейнер состояния (state) для всего React.js приложения, то на помощь приходить Redux, прочитать об этом можно в статье: https://learn-reactjs.ru/basics/forms. Redux - организует однонаправленный поток данных в приложении. Случилось действие от пользователя -> полетел экшен, экшен был пойман редьюсером -> изменились пропсы у React-компонента -> компонент перерисовался. Когда мы подписываемся только на нужные редьюсеры в компоненте, перерисовка происходит только в случае изменения конкретно этих данных. Если же мы бы подписались просто на весь корневой редьюсер, то не важно в каком бы редьюсере изменились данные - все подписанные на корневой редьюсер компоненты обновились бы.

class Article extends React.Component {
  /* Стартовый значения набора переменных состояния. */
  state = {
    visible: false,
  }
 
  /* Обработка нажатия на ссылку. */
  handleReadMoreClck = (e) => { 
    /* Отменяем действия браузера по умолчанию при нажатию на ссылку. */
    e.preventDefault()
    /* Изменяем значение перемеренной состояния. */
    this.setState({ visible: true })
  }
 
  /* Обработка нажатия на ссылку. */
  handleReadMoreHide = (e) => { 
    /* Отменяем действия браузера по умолчанию при нажатию на ссылку. */
    e.preventDefault()
    /* Изменяем значение перемеренной состояния. */
    this.setState({ visible: false })
  }
 
  render() {
    /* Получаем значение перемеренной состояния. */
    const { visible } = this.state
 
    return (
{!visible && ( Показать )} {visible && ( Спрятать )}
) } }

При этом для Redux существуют расширения:

  • Redux Thunk и Redux Saga - это разные дизайн паттерны добавления асинхронности в Redux.
  • Redux Actions - позволяют писать более короткий код объявления екшенов (уменьшит код в 2 раза и повысит читаемость).
  • Reselect - не даст компоненту перерисовываться, если входные данные (props) не изменились.

Так как Redux это - единый контейнер состояния, с которым необходимо работать асинхронно. Рассмотрим общую суть работы асинхронности: функция 1 вызывает функцию 2 и передаёт ей какие-то параметры, а так же в виде одного из параметров - функцию 3 (колбек). В функции 2 производятся манипуляции с полученными параметрами, но результат не отправляется в функцию 1 (из которой произошёл вызов функции 2), а вместо этого - результат работы функции 2 отправляется в переданную ей в виде одного из параметров - функцию 3.

Таким образом это позволяет отойти от классической схемы работы программы: когда на какое-либо событие в программе - вызывается определённая (основная) функция ответственная за логику обработки данного события. В этой основной функции содержатся ВСЯ логика обработки данного события, в том числе: операции с поступившими данными и вызовы дочерних функции. При этом результаты работы дочерних функций будут использоваться как в логических блоках основной функции, так и в операциях с поступившими данными. Результатом работы основной функции - станет реакция программы на данное произошедшее событие.

В асинхронной схеме работы программы: функция ответственная за обработку логики данного события (основная функция) разделяется на более мелкие функции, каждая из которых содержит лишь один логический блок обработки данного события. После чего из этих мелких функций выстраивается логическая цепочка обработки данного события (на основании того - как выше объяснена суть асинхронности). Эта логическая цепочка может ветвиться. Например: в случае ошибки - вывести сообщение пользователю об ошибке и записать в лог-файл данные об ошибке. Вывод ошибки пользователю и запись в лог-файл не зависят друг от друга - поэтому они могут быть выполнены не последовательно (друг за другом), а параллельно - за счёт чего и достигается асинхронность. Кроме, того при внесении изменений в логику обработки данного события - достаточно внести изменение и протестировать лишь одну мелкую функцию, что позволяет сократить расходы на тестирование и поддержку приложения, а так же понижает "порог" понимания логики работы всей программы.

 

Нам нужен способ обратиться к тегу и вызвать либо его метод play(), либо pause(). Сделать это можно с помощью конструкции document.getElementById('audio').play(), но React предлагает кое-что получше.

https://dou.ua/lenta/articles/react-redux-approach/

http://react-learn.blogspot.com/2017/07/redux-saga.html

https://ru.redux-saga.js.org/

Мы назначаем элементу атрибут, называемый ref, который принимает функцию. Эта функция, в качестве первого аргумента, принимает элемент , и присваивает его this.audio.

https://habr.com/ru/company/ruvds/blog/345340/

https://habr.com/ru/company/ruvds/blog/419993/

https://habr.com/ru/company/ruvds/blog/344502/

https://alligator.io/react/typescript-with-react/

https://alligator.io/react/

 



Эта функция будет вызываться каждый раз, когда выводится Container, то есть, this.audio всегда будет в актуальном состоянии и будет указывать на тег .
Теперь мы можем запускать и приостанавливать воспроизведение музыки:

handleClick() {
  if (this.state.isMusicPlaying) {
    this.audio.pause();
  } else {
    this.audio.play();
  }
  this.setState(prevState => {
    return { 
      isMusicPlaying: !prevState.isMusicPlaying   
    };
  });
};