Вкладки, когда одна активна, превращают все в ложные алогритимы Meteor React

Я пытаюсь: сделать вкладку активной и отключить все остальные. В настоящее время у меня он работает только там, где он выключается и включается по одному.

Я пытаюсь понять, как я могу это сделать. Я подумал, есть ли способ передать родительский компонент функции, а затем получить доступ к свойству className всех его дочерних элементов?? В настоящее время у меня есть:

import React from 'react';
import ReactDOM from 'react-dom';


export default class TestContainer extends React.Component{


        setActive(event){
           event.preventDefault();

           //getting id from component
           let isActive = event.target.id;


           if(event.currentTarget.className === "list-group-item text-center active"){
                   event.currentTarget.className = "list-group-item text-center";
           } else if(event.currentTarget.className === "list-group-item text-center") {
                   event.currentTarget.className = "list-group-item text-center active";
           }

        }



        render(){   




         return (                               

                <div className="col-lg-6 col-md-6 col-sm-6 col-xs-6 bhoechie-tab-container    scroll-y">
                        <div className="col-lg-2 col-md-2 col-sm-2 col-xs-2 bhoechie-tab-menu">
                                <div className="list-group">
                                        <a href="#" onClick={this.setActive} id="eyes" className="list-group-item text-center active">
                                                <h4 className="glyphicon glyphicon-eye-close"></h4><br/>1
                                        </a>
                                        <a href="#" onClick={this.setActive} id="hair" className="list-group-item text-center">
                                                <h4 className="glyphicon glyphicon-tint"></h4><br/>2
                                        </a>
                                        <a href="#" onClick={this.setActive} id="mouth" className="list-group-item text-center">
                                                <h4 className="glyphicon glyphicon-minus"></h4><br/>3
                                        </a>
                                        <a href="#" onClick={this.setActive} id="clothing" className="list-group-item text-center">
                                                <h4 className="glyphicon glyphicon-user"></h4><br/>4
                                        </a>
                                        <a href="#" onClick={this.setActive} id="props" className="list-group-item text-center">
                                                <h4 className="glyphicon glyphicon-gift"></h4><br/>5
                                        </a>
                                </div>
                        </div>
)}

person sophia    schedule 16.06.2016    source источник


Ответы (1)


Пытаясь изменить состояние ваших элементов вне метода render(), вы боретесь с сильными сторонами механизма рендеринга React. Используйте состояние, либо внутреннее для компонента, либо предоставленное через реквизиты/контекст (предпочтительно реквизиты), чтобы определить, какая вкладка должна отображаться с active в ее className.

Когда вы отвечаете на щелчок, измените состояние и позвольте React повторно отобразить компонент на основе нового состояния.

Для приведенного здесь ограниченного примера я бы рекомендовал хранить идентификатор активного элемента внутри в состоянии компонента.

export default class TestContainer extends React.Component {
  constructor(props) {
    super(props);

    this.state = {
      activeTab: this.props.activeTab || 'eyes'
    };
  }

  setActive(event) {
    this.setState({ activeTab: event.target.id });
  }

  render() {
    const { activeTab } = this.state;
    const tabClassName = "list-group-item text-center";
    const eyesTabClassName = tabClassName + (activeTab === 'eyes' ? ' active' : '');

    ...

              <a href="#" onClick={this.setActive} id="eyes" className={eyesTabClassName}>

    ...

  }
}

Это грубое, неоптимизированное решение, но оно должно передать идею. Когда вы вызываете this.setState, React отвечает, помечая компонент как требующий повторного рендеринга. Метод render() будет вызван автоматически, и, таким образом, весь ваш JSX будет переоценен и перерендерен. Затем React рассмотрит разницу между тем, что он только что создал, и тем, что уже находится в виртуальной DOM, и объединит ваши изменения.

Это означает, что любая вкладка, которая ранее отображалась с «активным» в своем className, будет повторно отображаться. Если он больше не активен, ваш код рендеринга не объединит активный класс с className этой вкладки. Кроме того, какой бы класс ни был активен, теперь к его className будет добавлено слово «active».

TL;DR

Не манипулируйте DOM в обработчиках событий. Управляйте состоянием и позвольте React творить чудеса, выполняя повторный рендеринг с вашим новым состоянием.

person Ryan    schedule 17.06.2016