Warning: file_get_contents(/data/phpspider/zhask/data//catemap/9/javascript/451.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Javascript React/Redux:将jQuery事件处理程序放在组件中等待异步数据的位置_Javascript_Jquery_Reactjs_Redux - Fatal编程技术网

Javascript React/Redux:将jQuery事件处理程序放在组件中等待异步数据的位置

Javascript React/Redux:将jQuery事件处理程序放在组件中等待异步数据的位置,javascript,jquery,reactjs,redux,Javascript,Jquery,Reactjs,Redux,当我阅读ReactJS文档时,我知道放置redux操作调用的最佳生命周期方法是componentDidMount,但我发现在该生命周期方法中很难执行任何jquery工作: class App extends React.Component { constructor(props) { super(props); this.state = { isAsyncLoaded: false } } stati

当我阅读ReactJS文档时,我知道放置redux操作调用的最佳生命周期方法是
componentDidMount
,但我发现在该生命周期方法中很难执行任何jquery工作:

class App extends React.Component {
    constructor(props) {
        super(props);
        this.state = {
            isAsyncLoaded: false
        }
    }
    static getDerivedStateFromProps(nextProps, prevState) {
        let {getData} = nextProps.someData;
        let {hasSuccess, isLoading} = getData;

        if (!isLoading && hasSuccess) {
            return {
                isAsyncLoaded: true
            }
        } else {
            return {
                isAsyncLoaded: false
            }
        }

        return null;
    }
    componentDidMount() {
        this.props.getSomeData();
        $('p').css('color', 'red');
    }
    render() {
        if (!this.state.isAsyncLoaded) return null;
        return (
            <p>{this.props.someData.data}</p>
        )
    }
}

function mapStateToProps(state) {
    return {
        someData: state.someData
    }
}

export default connect(mapStateToProps, {getSomeData})(App);
类应用程序扩展了React.Component{
建造师(道具){
超级(道具);
此.state={
isAsyncLoaded:错误
}
}
静态getDerivedStateFromProps(下一步,上一步){
让{getData}=nextrops.someData;
设{hassucces,isLoading}=getData;
如果(!isLoading&&Hassucces){
返回{
isAsyncLoaded:正确
}
}否则{
返回{
isAsyncLoaded:错误
}
}
返回null;
}
componentDidMount(){
this.props.getSomeData();
$('p').css('color','red');
}
render(){
如果(!this.state.isAsyncLoaded)返回null;
返回(
{this.props.someData.data}

) } } 函数MapStateTops(状态){ 返回{ someData:state.someData } } 导出默认连接(MapStateTops,{getSomeData})(应用程序);
这里是jquery
$('p').css('color','red')部分找不到
元素,因为
isAsyncLoaded
不为true,并且
render
函数返回
null


我的问题是,在不向我的应用程序引入容器视图(父子)组件关系的情况下,如何解决这个问题?

在我开始之前,请注意几点:使用jQuery之类的事件处理程序通常是React中的反模式。它可能会对DOM造成意外的副作用,理想情况下应该完全通过react中的受控组件来处理

如果您需要使用jQuery(对于快速/脏的插件或类似的东西),我建议使用单独的组件。当该组件挂载时,它会触发一个事件,您可以钩住该事件并触发jQuery代码:

class MyJqueryComponent extends React.Component {
    constructor(props) {
        super(props);
        this.mountPoint = React.createRef();
    }
    componentDidMount() {
        // Do your jQuery stuff here
        $(this.mountPoint).find(...);
    }
    render() {
        return (
            <p ref={this.mountPoint}>{this.props.data}</p>
        );
    }
}
class App extends React.Component {
    constructor(props) {
        super(props);
        this.state = {
            isAsyncLoaded: false
        }
    }
    static getDerivedStateFromProps(nextProps, prevState) {
        let {getData} = nextProps.someData;
        let {hasSuccess, isLoading} = getData;

        if (!isLoading && hasSuccess) {
            return {
                isAsyncLoaded: true
            }
        } else {
            return {
                isAsyncLoaded: false
            }
        }

        return null;
    }
    componentDidMount() {
        this.props.getSomeData();
        $('p').css('color', 'red');
    }
    render() {
        if (!this.state.isAsyncLoaded) return null;
        return (
            <p><MyJqueryComponent data={this.props.someData.data} /></p>
        )
    }
}

function mapStateToProps(state) {
    return {
        someData: state.someData
    }
}

export default connect(mapStateToProps, {getSomeData})(App);
类MyJqueryComponent扩展了React.Component{
建造师(道具){
超级(道具);
this.mountPoint=React.createRef();
}
componentDidMount(){
//在这里执行jQuery操作
$(this.mountPoint).find(…);
}
render(){
返回(

{this.props.data}

); } } 类应用程序扩展了React.Component{ 建造师(道具){ 超级(道具); 此.state={ isAsyncLoaded:错误 } } 静态getDerivedStateFromProps(下一步,上一步){ 让{getData}=nextrops.someData; 设{hassucces,isLoading}=getData; 如果(!isLoading&&Hassucces){ 返回{ isAsyncLoaded:正确 } }否则{ 返回{ isAsyncLoaded:错误 } } 返回null; } componentDidMount(){ this.props.getSomeData(); $('p').css('color','red'); } render(){ 如果(!this.state.isAsyncLoaded)返回null; 返回(

) } } 函数MapStateTops(状态){ 返回{ someData:state.someData } } 导出默认连接(MapStateTops,{getSomeData})(应用程序);
componentDidUpdate()中应用jquery代码

componentDidUpdate(prevProps,prevState){
//仅在首次呈现异步代码时执行代码
if(prevState.isAsyncLoaded==false&&this.state.isAsyncLoaded==true){
//在这里执行jQuery操作
$(this.mountPoint).find(…);
}
}

现场演示:

为什么一开始就要使用jQuery?jQuery不应该在react方式中占有一席之地。我理解你的意思,但是假设我有一个重要的插件,它依赖于jquery。我看不出这与创建容器-视图层次结构和只对子组件使用jquery有什么不同。它看起来更脏,而且设计过度。@BarışÜrüm欢迎来解释为什么这是一种反模式:虽然这是一个可行的替代方案,但我通常反对这些设计决策,因为这会使调试变得更加困难。当另一个程序员添加另一个fetch语句来更新数据时会发生什么
isAsyncLoaded
已经为true,因此它不会翻转,并且jQuery代码永远不会执行。新的事件处理程序无法绑定。添加此内容的理想位置应该是在呈现此异步组件时。@FrankerZ我们需要从使用jQuery和react是一种反模式这一点开始。这个解决方案只是一个逃生舱。我仍然坚持,如果我有一个我想要使用的强制jquery插件,我就必须进行这种集成。@Barışrüm这是一种务实的方法。使用jQ,直到找到/创建给定插件的替代品,因为原生react实现将更容易维护。