2017-01-23 9 views
8

Mam formę redux związaną z moim stanem aplikacji i wszystko wydaje się działać świetnie. Mogę pobrać dane i załadować je do mojego formularza, a następnie przesłać dane i uzyskać metadane, które chcę ...Redux-Form aktualizacja wartości pola z interakcji zewnętrznej

Mam jednak niestandardową interakcję (próbnik kolorów), który musi zmienić wartość zarządzanego pola na Mucha. Wszystko, co próbuję, zmieni ekran, ale nie stan formy redux, tzn. Kiedy przesyłam formularz, otrzymuję oryginalne dane pola, a nie nowe dane pokazane w formularzu.

Poniższa wersja przekazuje rekwizyty polowe do komponentu i próbuje użyć stanu składnika ColorSelect jako wartości pola. Próbowałem także stworzyć twórcę akcji, ale ten sam wynik i znacznie więcej kodu niż ten przykład ...

Uwaga: [email protected]Р15.4.2, [email protected]Р5.0.2, redux-form @^6.4.3

ES6: CollectionForm.js

... 
 
import ColorSelect from './ColorSelect'; 
 

 

 
class CollectionForm extends Component { 
 

 
    /** 
 
    * On form submit accepted 
 
    * @param values 
 
    */ 
 
    onSubmit(values){ 
 

 
     //See screenshot for evidence 
 
     log('Updating collection:', 'warn', values); 
 

 
     //values.color is grey and not yellow! 
 
     this.props.dispatch(updateCollection(values)); 
 
     return; 
 
    } 
 

 
    /** 
 
    * Form render 
 
    * @return {JSX} 
 
    */ 
 
    render() 
 
    { 
 
     const { handleSubmit, submitting } = this.props; 
 

 
     return (
 
      <form onSubmit={handleSubmit(this.onSubmit.bind(this))}> 
 
       <Field component={renderTextInput} name="name" type="text" label="Name"/> 
 
       <Field component={ColorSelect} name="color" /> 
 

 
       <div class="field-buttons right-align group"> 
 
        <Button type="submit" disabled={submitting} primary> 
 
         Save 
 
        </Button> 
 
       </div> 
 
      </form> 
 
     ); 
 
    } 
 
}; 
 

 
//Redux form decorator 
 
CollectionForm = reduxForm({ form: 'collectionForm' })(CollectionForm) 
 

 
// State connector 
 
CollectionForm = connect(
 
    state => ({ 
 
     initialValues: state.collections.activeCollection 
 

 
    }), //MapStatetoProps 
 
    { 
 
     onLoad: fetchCollection 
 
    } //mapActionToProps 
 
)(CollectionForm); 
 

 
export default CollectionForm;

ES6: CollectionForm.js

import React, { Component } from 'react' 
 
import { Field, reduxForm, SubmissionError } from 'redux-form'; 
 

 
const colors = [ 
 
    'grey', 'green', 'yellow', 'orange', 'red', 'purple', 'blue' 
 
]; 
 

 
export default class ColorSelect extends Component { 
 

 
    constructor(props){ 
 
     super(props); 
 

 
     this.state = { 
 
      selectedColor : this.props.input.value //Set to current <Field> input value 
 
     }; 
 

 
     this.onSelect = this.onSelect.bind(this); 
 
     this.renderColor = this.renderColor.bind(this); 
 
    } 
 

 
    /** 
 
    * Color picker selected 
 
    * @param color 
 
    */ 
 
    onSelect(color){ 
 
     this.setState({ selectedColor: color }); //Sets correct state here 
 
    } 
 

 
    /** 
 
    * Render a color list item 
 
    * @param color 
 
    * @return {JSX} 
 
    */ 
 
    renderColor(color){ 
 

 
     const select = this.state.selectedColor === color ? "active" : ""; 
 
     const klass = color + " " + select; 
 

 
     return <li key={color}> 
 
      <a class={klass} onClick={(event) => this.onSelect(color)}></a> 
 
     </li> 
 
    } 
 

 
    /** 
 
    * Render color list action 
 
    * @return {JSX} 
 
    */ 
 
    render(){ 
 

 
     //Override field value with colorSelected state 
 
     
 
     return (
 
      <div> 
 
       <input {...this.props.input} value={this.state.selectedColor} name="color" type="text" label="Color" /> 
 

 
       <div class="color-selector"> 
 
        <ul> 
 
         {colors.map((color) => this.renderColor(color))} 
 
        </ul> 
 
       </div> 
 
      </div> 
 
     ); 
 
    } 
 
}

Odpowiedz

10

Można użyć reagować-Redux na mapDispatchToProps wraz z change action creator, aby osiągnąć to, co chcesz:

import { Component } from "react"; 
import { change } from "redux-form"; 

class ColorSelect extends Component { 
    // ...other stuff in this class... 

    renderColor (color) { 
    const { selectColor } = this.props; 
    return <li key={color}><a onClick={() => selectColor(color)}></a></li>; 
    } 
} 

export default connect(null, { 
    selectColor: color => change("yourFormName", "yourFieldName", color) 
})(ColorSelect) 
+0

Perfect! Dziękuję bardzo - zadziałał urok. –

+1

@gustavohenke proszę dodać opakowanie wysyłki –

+0

To nie jest potrzebne: https://github.com/reactjs/react-redux/blob/master/docs/api.md#connectmapstatetoprops-mapdispatchtoprops-mergeprops-options – gustavohenke

Powiązane problemy