【问题标题】:Issue animating ui based on reducer state changes根据 reducer 状态变化发出动画 ui
【发布时间】:2019-10-07 15:24:49
【问题描述】:

我正在构建一个react 项目,用于使用redux 可视化insertion sort。我正在使用react-redux 创建和处理actions。然而,问题在于,在我的insertionSort 算法中,每次排序的array 发生变化时,我都会调度updateArray 操作。我将print 语句放在reducer 中,看到状态实际上正在发生变化,并且动作正在正确分派,但是,我的实际array 没有重新渲染。我将prints 放在相关UI 组件的render() 函数中,发现它只被调用一次或两次,而不是每次reducer 接收到动作时。我尝试多次重组我的代码并阅读人们遇到的类似问题,但他们的答案对我没有帮助。

我只是以错误的方式构建它吗?我不应该每秒钟左右使用一次调度来更新我的数组吗?

我有一个 main.js 文件,用于渲染 UI 组件,包括我的数组:

class Main extends React.Component {
     setArray = () => {
         this.props.setArray(50, window.innerHeight / 1.4)
     startSort = () => {
         this.props.startSorting(this.props.algorithm, this.props.array)
     }
     render() {
         let { array} = this.props
         return (
             <div>
                 <Navbar
                     startSort={this.startSort}
                     setArray={this.setArray}
                 />
                 <MainWrapper>
                     <Row />
                 </MainWrapper>
             </div>
              )
          }
      }
 const mapStateToProps = state => {
    return {
         array: state.array,
      }
  }

 const mapDispatchToProps = dispatch => {
     return {
         setArray: (length, height) => {
              let array = Array.from({ length: length }, () =>
              Math.floor(Math.random() * height))
              dispatch(setArray(array))
         },
         startSorting: (algorithm, array) => {
              var doSort
              if (algorithm == 'insertionSort') {
                  doSort = insertionSort
               }
              doSort(array, dispatch)
       }
     }
  }

我的实际数组是用Row.js生成的

class Row extends React.Component {
    generateNodes(array) {
        var elements = []
        array.forEach((value, index) => {
            elements.push(
                <CenteredColumn>
                    <ArrayNode idx={index} value={value} />
                </CenteredColumn>
            )
        })
        return elements
        }
    render() {
        let { array } = this.props
        console.log('UPDATED ARRAY: ' + array)
        var arrayElements = this.generateNodes(array)
        return <RowWrapper>{arrayElements}</RowWrapper>
    }
}

const mapStateToProps = state => {
    return {
        array: state.array
    }
}

最后,我的实际算法在insertionSort.js 中,我从他们的reducer 导入我的操作并从main.js 传入一个调度函数:

function delayedInsertion(array, dispatch) {
let n = array.length
var i = 0
function loop() {
    setTimeout(function() {
        var temp = array[i]
        var j = i - 1
        while (j >= 0 && array[j] > temp) {
            array[j + 1] = array[j]
            j--
        }
        array[j + 1] = temp
        // console.log('ARRAY: ' + array)
        dispatch(updateArray(array))
        i++
        if (i < n) {
            loop()
        }
    }, 200)
}
loop()
console.log('DONE')
}

【问题讨论】:

    标签: javascript reactjs redux react-redux


    【解决方案1】:

    看来你正在改变你的状态。

    您将this.props.array 传递给您的doSort 操作,并且我正确理解您的想法,您只是从该操作中调用delayedInsertion(您没有发布该操作的源代码)。 但是在delayedInsertion 中,当您更改项目的位置时,您正在改变传递的数组,这里:

    while (j >= 0 && array[j] > temp) {
       array[j + 1] = array[j]
       j--
    }
    array[j + 1] = temp
    

    您需要对数组执行不可变的更改。

    【讨论】:

      猜你喜欢
      • 2023-03-23
      • 1970-01-01
      • 1970-01-01
      • 2020-05-18
      • 1970-01-01
      • 2017-12-09
      • 1970-01-01
      • 2018-08-09
      • 2017-04-09
      相关资源
      最近更新 更多