如何在React中不相关组件的切换样式?


在写React的时候发生了一个一个问题。

先说环境:react14.0 + Babel + gulp
显示的效果是这样的。

demo

流程:
响应式页面,左侧茶色在大屏幕显示,小屏幕隐藏
左边和右边的完全独立,不是父子组建的关系。
而我想要通过点击触发器来修改左侧的css样式,进而达成隐藏显示的效果。

我应该在代码里面怎么写呢?

我做过一些想法的验证,然而没有效果:
全局函数,通过 refs 获取然后调整 style
然而没办法生效,全局函数嘛, this.refs this 指向又是问题,因为两个组件没有任何联系。。。bind和call都试了,都是提示 undefined

后来我想可以通过 querySelector 来找到样式直接操作dom的样式,这样确实是达成了效果,然而并不优雅,react貌似也并不推荐这么做。

希望有大神能给一下解决方法

JavaScript react.js

青春划破流沙 9 years, 5 months ago

可以简单到一个组件做$(document).trigger('anevent', data),另一个组件$(document).on('anevent', fn); 思想是让不想关的组件和一个中间人打交道。你也可以实现自己的pubsub或则某种形式的message queue。

参考:

https://facebook.github.io/react/tips/communicate-between-components.html

For communication between two components that don't have a
parent-child relationship, you can set up your own global event
system. Subscribe to events in componentDidMount(), unsubscribe in
componentWillUnmount(), and call setState() when you receive an event.
Flux pattern is one of the possible ways to arrange this.

https://facebook.github.io/flux/docs/dispatcher.html
http://ctheu.com/2015/02/12/how-to-communicate-between-react-components/#comp_to_comp

多伦多奶酪 answered 9 years, 5 months ago

其实这个是涉及到不同组件之间的数据传递的一个问题,有两个方法:

  1. 使用共同父组件传递数据的方法将子组件的数据传递给共同父组件然后通过父组件将值通过属性传入另外的子组件中。

  2. 使用外部数据 Store 来存储这个切换状态,组件内通过读取这个状态来修改样式

这两个方法都能做到尽量在数据层做操作而不涉及到 DOM。如果实在是要用 refs 的方法的话也建议在共同父组件中做,这样会更清楚一点。

我去你妹的 answered 9 years, 5 months ago

HTML


 <!DOCTYPE html>
<html>
<head>
    <meta charset="UTF-8">
    <title>React</title>  
    <style>
        .left {
            background-color: darkslategray;
            float: left;
            width: 50%;
            height: 100px;
        }

        .left-other {
            background-color: green;
            float: left;
            width: 50%;
            height: 100px;
        }

        .right {
            background-color: deeppink;
            float: left;
            width: 50%;
            height: 100px;
        }
    </style>
</head>
<body>
<script src="js/lib/react.js"></script>
<script src="js/lib/JSXTransformer.js"></script>
<script src="js/my/app.js" type="text/jsx"></script>
</body>
</html>

Script


 var Left = React.createClass({
    render: function () {
        return (
            <div className={this.props.leftClass}>
                我是想要被隐藏的
            </div>
        )
    }
});

var Right = React.createClass({
    handleClick: function () {
        this.props.toggleLeftClass();
    },
    render: function () {
        return (
            <div className="right">
                <button onClick={this.handleClick}>事件触发器</button>
            </div>
        )
    }
});

var App = React.createClass({
    getInitialState: function () {
        return {
            leftClass: 'left'
        }
    },
    toggleLeftClass: function () {
        this.setState({
            leftClass: this.state.leftClass === 'left' ? 'left-other' : 'left'
        })
    },
    render: function () {
        return (
            <div className="container">
                <Left leftClass={this.state.leftClass}/>
                <Right toggleLeftClass={this.toggleLeftClass}/>
            </div>
        )
    }
});    

React.render(<App />, document.body);

Effect

图片描述

枫鸟院花月 answered 9 years, 5 months ago

Your Answer