Как правильно установить значения по умолчанию с помощью redux-forms?

используя React with redux-forms, я получил следующий компонент, это форма, в которой 3 поля ввода могут получить значения, если строка запроса включает значения.

Я использую initialize способ установки:

initialize({
  firstname: query.firstname,
  lastname: query.lastname,
  birthday: query.dob
});

и это заполняет заливки, однако у меня есть два основных вопроса:

  • кнопка Отправить сохраняет отключенным
  • поля не редактируются.

Я попытался установить исправление для кнопки отправки, Протестировав invalid prop, но не сработало.

как я могу исправить и справиться с этими проблемами?

это весь код компонента:

import React, { Component, PropTypes } from 'react';
import { connect } from 'react-redux';
import { browserHistory } from 'react-router';
import { reduxForm, Field, SubmissionError } from 'redux-form'
import { RaisedButton, Paper, TextField } from 'material-ui';

import * as actionsAuth from '../redux/modules/auth';
import { createValidator, required, email } from '../utils/validation';
import FieldTextField from '../components-form/FieldTextField';


const styles = {
    root: {
        display: 'flex',
        flexWrap: 'wrap',
        justifyContent: 'space-around',
        paddingTop: 50
    },
    paper: {
        padding: 20,
        maxWidth: 500
    },
    field: {
        width: '100%'
    },
    button: {
        width: '100%',
        marginTop: 10
    }
};

const validate = createValidator({
    firstname: [],
    lastname: [],
    birthday: []
});

class LoginPage extends Component {

    constructor(props) {
        super();
        this.submit = this.submit.bind(this);
    }

    static propTypes = {
        patientChatLogin: PropTypes.func.isRequired
    };

    submit(values) {
        const { user } = this.props;
        let dob = values.birthday.split('-');
        let data = {
            _id: user.id,
            firstname: values.firstname,
            lastname: values.lastname,
            dob: {
                year: dob[0],
                month: dob[1],
                day: dob[2]
            }
        }
        const { patientChatLogin } = this.props;

        return patientChatLogin(data)
            .then(this.onSubmitSuccess, this.onSubmitError);
    }

    onSubmitSuccess(patient) {
        browserHistory.push(`/chat/${patient.id}`);
    }

    onSubmitError(rejection) {
        throw new SubmissionError({ auth: rejection.error, _error: 'Login failed!' });
    }

    ///////////////////
    // render

    render() {
        return (
            <div style={styles.root}>
                {this.renderForm()}
            </div>
        );
    }

    renderForm() {
        const { handleSubmit, initialize, location: {query} } = this.props;
        if (query.firstname && query.firstname !== 'undefined' &&
            query.lastname && query.lastname !== 'undefined' &&
            query.dob && query.dob !== 'undefined') {
            initialize({
              firstname: query.firstname,
              lastname: query.lastname,
              birthday: query.dob
            });
        }
        return (
            <form
                onSubmit={handleSubmit(values => this.submit(values))}
            >
                <Paper style={styles.paper} zDepth={1}>
                    {this.renderFieldFirstName()}
                    {this.renderFieldLastName()}
                    {this.renderFieldBirthday()}
                    {this.renderSubmitButton()}
                </Paper>
            </form>
        );
    }

    renderFieldFirstName() {
        // TODO:
        // Set default as redux-form requires it
        return (
            <Field
                autoFocus
                style={styles.field}
                name="firstname"
                floatingLabelText="First Name"
                component={FieldTextField}
                required
            />
        );
    }

    renderFieldLastName() {
        return (
            <Field
                style={styles.field}
                name="lastname"
                floatingLabelText="Last Name"
                component={FieldTextField}
                required
            />
        );
    }

    renderFieldBirthday() {
        return (
            <Field
                style={styles.field}
                type="date"
                name="birthday"
                floatingLabelText = "Date of Birth"
                floatingLabelFixed={true}
                component={FieldTextField}
                required
            />
        );
    }

    renderSubmitButton() {
        const { pristine, submitting, invalid } = this.props;
        return (
            <RaisedButton
                style={styles.button}
                type="submit"
                label="Enter secure chat"
                secondary
                disabled={ pristine || submitting ||  invalid }
            />
        );
    }
}

export default connect(state => ({
        user: state.auth.user,
}), {
        ...actionsAuth,
    })
    (reduxForm({
        form: 'AuthenticatePatientForm',
        validate,
    })(LoginPage));

1 ответов


вы не можете редактировать поля, потому что вы инициализируете каждый рендер, если эти реквизиты присутствуют. Использовать initialize, вы хотели бы сделать, что в componentDidMount, а не в методе render.

альтернативным подходом было бы обернуть компонент формы и поставить initialValues на основе этих реквизита.

const Wrapper = ({ location: { query }, ...props }) => {
  class LoginPage extends Component {
    ...
  }
  const WrappedForm = reduxForm({
    form: 'the-form',
    validate,
    initialValues: {
      firstname: query.firstname,
      lastname: query.lastname,
      birthday: query.dob
    }
   })(LoginPage);
   return <WrappedForm {...props} />;
 }