Почему мой оператор ReactRedux.connect не работает? - PullRequest
1 голос
/ 25 сентября 2019

Я пишу приложение для калькулятора как проект для FreeCodeCamp.Я решил написать это, используя React и Redux.Я написал часть приложения Redux и начал подключать Redux к React.

Когда я написал весь код для подключения Redux к моему приложению React, рендеринг перестал работать.Я использовал различные операторы console.log (), чтобы отследить, где JavaScript задыхался, и сузил его до оператора connect, найденного в строке 241 связанного Codepen.Если вы закомментируете строку 242 и замените строку 255 на ReactDOM.render(<Calculator/>, wrapper);, приложение отобразится.Однако тот же код, работающий на платформе FreeCodeCamp, похоже, работает.

Вот ссылка на мой CodePen: JavaScript Calculator .

Задача, которую я использовал для тестирования FreeCodeCampмой код может быть найден здесь: FCC Challenge

Точный код, который я адаптировал из FCC (чтобы редактор смог отрисовать мой компонент), приведен ниже.Вы можете видеть изменения, которые я сделал с помощью пера, только в части кода рендеринга.

const wrapper = document.querySelector("#wrapper");

// REDUX
const initialState = {
  operation: "",
  lastResult: "",
  operand: "",
  lastInput: "",
  display: "0"
}
const operators = ["+", "-", "*", "/"];
const ADD_DIGIT = "ADD_DIGIT";
const ADD_OPERATOR = "ADD_OPERATOR";
const ADD_DECIMAL = "ADD_DECIMAL";
const CLEAR = "CLEAR";
const EVALUATE = "EVALUATE";
const { createStore } = "Redux";

function reducer(state = initialState, action) {
  let newState;
  switch (action.type) {
    case ADD_DIGIT:
      // Number can't begin with multiple zeros, leave state the way it is
      if (state.lastInput === "0" && action.value === "0") {
        newState = state;
      // If last operation was =, start new operation
      } else if (state.lastInput === "=") {
        let newOperation = "" + action.value;
        newState = {
          operation: "",
          lastResult: state.lastResult,
          operand: newOperation,
          lastInput: action.value,
          display: newOperation
        }
      // If previous input was an operator, add operator to operation, reset display and start adding digits
      } else if (operators.indexOf(state.lastInput) > -1) {
        let newOperation = "" + action.value;
        newState = {
          operation: state.operation += state.lastInput,
          lastResult: state.lastResult,
          operand: newOperation,
          lastInput: action.value,
          display: newOperation
        }
      // Else, add digit to the current operand and display value
      } else {
        /* Append digit to operand, add to lastInput */
        /* Add digit to display */
        newState = {
          operation: state.operation,
          lastResult: state.lastResult,
          operand: state.operand + action.value,
          lastInput: action.value,
          display: state.display + action.value
        }
      }
      break;

    case ADD_OPERATOR:
      // Operation can't begin with operator unless previous operation was =
      if (state.operation === "") {
        if (state.lastInput === action.value) {
          newState = {
            operation: state.operation,
            lastResult: state.lastResult,
            operand: state.lastResult + "" + action.value,
            lastInput: action.value,
            display: state.lastResult + "" + action.value
          }
        } else {
          newState = state;
        }
      // If 2 or more operators are entered consecutively, use the most recently entered
      } else if (operators.indexOf(state.lastInput) > -1) {
        newState = {
          operation: state.operation,
          lastResult: state.lastResult,
          operand: "",
          lastInput: action.value,
          display: action.value
        }
      // Input should be handled normally for operator
      } else {
        /* Add current operand to operation */
        /* Set valid operator to lastInput */
        /* Add operator to display */
        newState = {
          operation: state.operation + state.operand,
          lastResult: state.lastResult,
          operand: "",
          lastInput: action.value,
          display: action.value
        }
      }
      break;

    case ADD_DECIMAL:
      // If used to begin a number, prepend a 0
      if (state.operand === "") {
        let newOperation = "0" + action.value;
        newState = {
          operation: state.operation,
          lastResult: state.lastResult,
          operand: newOperation,
          lastInput: action.value,
          display: newOperation
        }
      // No two decimals in one number
      } else if (state.operand.split("").indexOf(action.value) > -1 || state.lastInput === action.value) {
        newState = state;
      } else {
        /* Append decimal to lastInput, operand */
        /* Add decimal to display */
        newState = {
          operation: state.operation,
          lastResult: state.lastResult,
          operand: state.operand + action.value,
          lastInput: action.value,
          display: state.display + action.value
        }
      }
      break;   

    case EVALUATE:
      // Operation can't end with an operator
      // If input is only one operand, return that
      // Otherwise each operator must include two operands    
      if (operators.indexOf(state.lastInput) < 0) {
        /* Evalue the result of operand (Using eval() ) */
        /* Add result to display */
        /* Store result in lastResult, clear other state props */
        let result = eval(state.operation);
        newState = {
          operation: "",
          lastResult: result,
          operand: "",
          lastInput: action.value,
          display: result
        }
      }
      break;

    case CLEAR:
      /* Clear state, input, and display */
      newState = initialState;
      break;

    default:
      newState = state;
      break;
  }

  return newState;
}

function addDigit(digit) {
  let action = {
    type: ADD_DIGIT,
    value: digit
  }
  return action;
}
function addOperator(operator) {
  let action = {
    type: ADD_OPERATOR,
    value: operator
  }
  return action;
}
function addDecimal() {
  let action = {
    type: ADD_DECIMAL,
    value: "."
  }
  return action;
}
function evaluate() {
  let action = {
    type: EVALUATE,
    value: "="
  }
  return action;
}
function clear() {
  let action = {
    type: CLEAR,
    value: ""
  }
  return action;
}

const store = Redux.createStore(reducer);



// REACT-REDUX
const mapStateToProps = function(state) {
  console.log("map state to props");
  return {
    display: state.display
  }
}
const mapDispatchToProps = function(dispatch) {
  console.log("map dispatch to props");
  return {
    calcAddDigit: function(digit) {
      dispatch(addDigit(digit));
    },
    calcAddOperator: function(operator) {
      dispatch(addOperator(operator));
    },
    calcAddDecimal: function() {
      dispatch(addDecimal());
    },
    calcEvaluate: function() {
      dispatch(evaluate());
    },
    calcClear: function() {
      dispatch(clear());
    }
  }
}
const Provider = ReactRedux.Provider;
const connect = ReactRedux.connect;



// REACT
class Calculator extends React.Component {
  constructor(props) {
    super(props);
  }
  render() {
    return(
      <h1>Functioning</h1>
    )
  }
}

console.log("before connect statement - line 241");
Calculator = connect(mapStateToProps, mapDispatchToProps)(Calculator);
console.log("after connect statement");

class CalculatorApp extends React.Component {
  constructor(props) {
    super(props);
  }
  render() {
    return (
      <Provider store={store}>
        <Calculator/>
      </Provider>
    );
  }
}

class AppWrapper extends React.Component {
  render() {
    return (
      <Provider store={store}>
        <Calculator/>
      </Provider>
    );
  }
};

1 Ответ

1 голос
/ 25 сентября 2019

Потому что порядок, в котором вы импортируете внешние скрипты, имеет значение.Поместите redux ниже react, поскольку react-redux требует, чтобы React присутствовало в глобальной области видимости.

Правильный порядок:

  1. реагирует
  2. Реакт-Дом
  3. Рэдекс
  4. Реакт-Рэдекс
...