【问题标题】:React - bubble up state to change className on childrenReact - 冒泡状态以更改孩子的 className
【发布时间】:2017-12-04 19:41:08
【问题描述】:

我有一个数据层次结构,每个层次结构分为 6 列。当用户点击他们的选择时,他们选择的位置通过动态 css 类名突出显示,并显示相应的数据列表。我想出了如何使每个选择的亮点移动。但是,如果用户从层次结构的开头重新开始,它将保持最后一个突出显示状态。

例如,如果我有一个国家、州、城市的层次结构,并且我选择了美国、加利福尼亚、洛杉矶。如果我选择一个不同的国家,然后单击返回美国,加利福尼亚仍然会突出显示。如何更改所有列的 className?

我意识到有几篇关于冒泡状态的类似帖子。我无法弄清楚如何将它们应用到我的场景中,因为我需要比通常的例子多生一个孩子。

代码结构: App.js、LocationList.js、Location.js

LocationList.js

class LocationList extends Component {
    constructor(props){
        super(props);
        this.state = {
            title: props.title,
            clicked: false,
         };
        this.handleClick = this.handleClick.bind(this);
    }

    handleClick(selectedItem) { 
       this.props.onListClick(selectedItem) 
       this.setState({clicked: selectedItem})
    }

    isSelected(location){ //current selected item is highlighted
        if(location.LocationId === this.state.clicked.LocationId){
            return 'highlight'
        }
        else {return 'no_highlight'}
    } 

    return( ..//other info.. 
                 <Location
                    location={location}
                    key={location.LocationId+location.LocationName}
                    tier={this.props.level}
                    handler={this.handleClick}
                    highlightClass={this.isSelected(location)}
                  />

Location.js

class Location extends Component {
    constructor(props) {
        super(props);
        this.state={
            locationsList: props.locationList
        }   
        this.onClick = this.onClick.bind(this);       
    }

    onClick(selectedItem) { 
        this.props.handler(this.props.location);
     };

  render() {
        let location = this.props.location;
        console.log(this.props)     

        return(
            <div 
                id="item"
                style={locationStyle}  
                key={location.LocationId} 
                value={location.Name} 
                level={location.Level}
                onClick={this.onClick}
                className={this.props.highlightClass}
            >
                {location.LocationName} 
            </div> 
        );
    }
  }

App.js - 这就是我卡住的地方

handleClick(selectedItem) {
// See value user clicked
console.log('Selected location: ', selectedItem) 
}

render() {
      return(
          <div className="row">
          <LocationList key="1" level="1" title="Country" lis={this.state.column Tier1} onListClick={this.handleClick}/>
          <LocationList key="2" level="2" title="State" lis={this.state.column Tier2} onListClick={this.handleClick}/>
          <LocationList key="3" level="3" title="City" lis={this.state.column Tier3} onListClick={this.handleClick}/>
  </div>
 );

}

App.css

.no_highlight {
  background-color: transparent
}
.highlight {
  background-color: #007dc34d
}

【问题讨论】:

  • 虽然可以将状态提升到多个级别,但更好的选择可能是转向更强大的状态管理解决方案,例如 Redux。
  • 布雷特,你叫它。下一步是实现 Redux。

标签: javascript reactjs state event-bubbling


【解决方案1】:

将整个选择存储在App 状态,然后将适当的选择传递给相应的LocationList。最后,为LocationList点击重置状态实现不同的处理程序

class App extends Component {
  constructor(props) {
    super(props);
    this.state = { 
      ...
      selection: {
        country: null,
        state: null,
        city: null
      }
    };

    this.handleClick = this.handleClick.bind(this);
  }

  handleClick(getSelection) {
    return location => {
      const selection = getSelection(location);
      this.setState({
        selection: Object.assign({}, this.state.selection, selection)
      };
    };
  }

  render() {
    return (
      <div>
        ...
        <LocationList title="Country"
                      selection={this.state.selection.country}
                      onClick={this.handleClick(country => ({ country, state: null, city: null }))}
                      // other props
        />
        <LocationList title="State"
                      selection={this.state.selection.state}
                      onClick={this.handleClick(state => ({ state, city: null }))}
                      // other props
        />
        <LocationList title="City"
                      selection={this.state.selection.city}
                      onClick={this.handleClick(city => ({ city }))}
        />
      </div>
    );
  }
}

【讨论】:

    猜你喜欢
    • 2017-01-21
    • 2015-06-26
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2019-10-20
    • 2010-12-21
    • 2014-05-14
    • 1970-01-01
    相关资源
    最近更新 更多