Программно изменить значение поля Redux-Form
Когда я использую redux-form
v7, я считаю, что невозможно установить значение поля. Теперь в моей form
, у меня есть два select
компонента. Второе значение будет ясно, когда первое select
значение компоненты изменяется.
В классе render:
<div className={classNames(style.line, style.largeLine)}>
<div className={style.lable}>site:</div>
<div className={style.content}>
<Field
name="site"
options={sites}
clearable={false}
component={this.renderSelectField}
validate={[required]}
/>
</div>
</div>
<div className={classNames(style.line, style.largeLine)}>
<div className={style.lable}>net:</div>
<div className={style.content}>
<Field
name="net"
options={nets}
clearable={false}
component={this.renderSelectField}
validate={[required]}
warning={warnings.net}
/>
</div>
</div>
Теперь я добавляю select
и как я могу изменить другое значение select
renderSelectField = props => {
const {
input,
type,
meta: { touched, error },
...others
} = props
const { onChange } = input
const _onChange = value => {
onChange(value)
this.handleSelectChange({ value, type: input.name })
}
return (
<CHSelect
error={touched && error}
{...input}
{...others}
onChange={_onChange}
onBlur={null}
/>
)
}
Ответы
Ответ 1
Вы можете иметь логику onChange в this.handleSelectChange({ value, type: input.name })
и использовать change
действие из редукционной формы
Согласно документам:
изменить (поле: строка, значение: любое): функция
Изменяет значение в магазине Redux. Это создатель связанного действия, поэтому он ничего не возвращает.
код:
handleSelectChange = (value, type) => {
if(type === "site") {
this.props.change('net', "newValue");
}
}
const mapDispatchToProps = (dispatch) => {
return bindActionCreators({change}, dispatch);
}
Ответ 2
Я бы предпочел использовать Normalization для обработки таких случаев. Смотрите здесь: https://redux-form.com/7.0.2/examples/normalizing/ Это наиболее рекомендуемый способ выполнения динамических манипуляций с полями. И это гораздо читательнее и проще реализовать, чем любое другое решение.
Умышленное изменение обычного кода just to get the work done by hook or crook
, сделает ваш код непоследовательным и нечитаемым. Поэтому, пожалуйста, избегайте использования функции change
редукции или использования любых других hacks
.
Кроме того, вот как сделать нормализацию еще более мощной с помощью закрытий. Предположим, вы хотите выполнить несколько нормализаций в одном поле. Мы можем сделать это, используя функцию normalizeAll
ниже:
function normalizeAll(normalizers){
return function(value , previousValue , allValues , previousAllValues){ //note that these arguments are passed by default from redux form
var i = 0;
var normalizersLength = normalizers.length;
var currentValue = value;
while(i < normalizersLength)
{
var currentNormalizer = normalizers[i];
if(typeof currentNormalizer == "function")
{
currentValue = currentNormalizer(currentValue ,previousValue , allValues , previousAllValues);
}
i++;
}
return currentValue;
}
}
//I am using only the 'value' argument in normalization functions just for the example, but you can use the rest of them if they are needed
var firstNormalization = function(value , previousValue , allValues , previousAllValues){
return value+1;
}
var secondNormalization = function(value, previousValue , allValues , previousAllValues){
return value+2;
}
var thirdNormalization = function(value, previousValue , allValues , previousAllValues){
return value+3;
}
//To test result: i will execute the function returned from normalizeAll and pass the first argument as 1.
var normalizedValue = normalizeAll([firstNormalization , secondNormalization , thirdNormalization])(1);
console.log(normalizedValue); // 7
Чтобы использовать normalizeAll теперь в вашей форме редукса, вы сделаете что-то вроде этого:
normalize={normalizeAll([firstNormalizationFunction , secondNormalizationFunction])}
Наслаждайтесь!