还原状态不变

时间:2018-08-24 06:51:25

标签: javascript reactjs react-native redux

我已经设置了redux存储,但是当我尝试使用mapStateToProps和mapDispatchToProps更改状态时,总是得到默认状态。因此,在account.js中,我想获取选定的语言,然后将其添加到redux存储中。我尝试在其他组件中调用它,但是我总是以reducers / Language.js defaultState结尾。我做错了什么?

Account.js

class Account extends React.Component {
        static navigationOptions = ({ navigation }) => {};

        constructor(props) {
            super(props);

            this.state = {
                language: {
                    sq: true,
                    en: false,
                    selected: '',
                },
            };
        }

        changeLanguage = (selected) => {
            if (this.state.sq) {
                this.setState({ selected: 'sq' });
            } else {
                this.setState({ selected: 'en' });
            }
        };


        render() {
            const navigation = this.props.navigation;
            return (
                <ScrollView>
                <View>
                        <ThemeProvider>
                            <TableView header={I18n.t('account.lang_label')}>
                                <CheckboxRow
                                    selected={this.state.language.sq}
                                    onPress={() => {
                                        this.setState(state => ({
                                            language: {
                                                sq: !state.language.sq,
                                                en: !state.language.en,
                                            },
                                        }));
                                        this.changeLanguage();
                                    }}
                                    title={I18n.t('account.albanian')}
                                />
                                <CheckboxRow
                                    selected={this.state.language.en}
                                    onPress={() =>
                                        this.setState(state => ({
                                            language: {
                                                en: !state.language.en,
                                                sq: !state.language.sq,
                                            },
                                        }))
                                    }
                                    title={I18n.t('account.english')}
                                />
                            </TableView>
                        </ThemeProvider>
                    </View>
                                </ScrollView>
            );
        }
    }

    const mapDispatchToProps = dispatch => {
        return {
            changeLanguage: (selected) => { dispatch(changeLanguageEn(selected))},
        };
    };

    const mapStateToProps = state => {
        return {
            language: state.language.selected,

        };
    };

    export default withNavigation(connect(
        mapStateToProps,
        mapDispatchToProps
    )(Account));

actions / Language.js

import {CHANGE_LANGUAGE_EN, CHANGE_LANGUAGE_AL} from "./types";

export const changeLanguageEn = (language) => {
    return {
        type: CHANGE_LANGUAGE_EN,
        lang: language,
    }
};

export const changeLanguageAl = (language) => {
    return {
        type: CHANGE_LANGUAGE_AL,
        lang: language,
    }
};

reducers / Language.js

const defaultState = {
    lang: '',
};

export default function reducer(state = defaultState, action) {
    switch (action.type) {
        case 'CHANGE_LANGUAGE_EN':
           return {...state, lang: 'en'};
        case 'CHANGE_LANGUAGE_AL':
            return Object.assign({}, state, {
                lang: 'sq',
            });
        default:
            return state;
    }
}

3 个答案:

答案 0 :(得分:2)

在您的mapStateToProps函数中,尝试直接使用state.lang

const mapStateToProps = state => {
    return {
        language: state.lang,
    };
};

希望这会起作用。

答案 1 :(得分:1)

您输入的语言不正确。 state.language.selected

在化简器中,您正在状态中添加lang属性,因此在mapStateToProps中使用相同的属性名称对其进行访问。

const mapStateToProps = state => {
    return {
        language: state.language.lang,
    };
};

答案 2 :(得分:1)

不能完全确定我理解您的问题,但是听起来您正在尝试使用Account的内部状态更新redux状态?您应该能够做到:

this.props.changeLanguage(this.state.language.selected)

您的组件上也有一个定义为changeLanguage的方法,也许您可​​以在更改内部状态之后在该方法中执行上述操作

另外,在Account类的changeLanguage方法中,我不认为this.state.sq存在,因为sq是language状态对象中的键。相反,它应该是this.state.language.sq。您也不需要将所选参数添加到此方法。尝试使您的changeLanguage方法看起来像这样

changeLanguage = () => {
    if (this.state.sq) {
        this.setState({ language.selected: 'sq' });
    } else {
        this.setState({ language.selected: 'en' });
    }
   // dispatch your action here after updating the state
  this.props.changeLanguage(this.state.language.selected)
};

现在调用this.changeLanguage();将更新您的内部状态,然后调度您的changeLanguage redux操作