0
votes

I have created a function that "map" through array of objects and use that info to create material-ui TextField element. I am trying to output the error message when the user input characters more than maxLength. I would like to show error message only for the TextField that user is currently using through "onChange". However, it is being applied to all TextFields on the page. Could you please help me with this issue?

Below are my two functions:

This is displayCustomFields function that "maps" through the array of objects and use that info to TextField element.

displayCustomFields() {
    const { meteredConsumptionForm } = this.props.meteredConsumptionForm;
  
    if(Object.keys(meteredConsumptionForm).length > 0 ) {
      const customFields = meteredConsumptionForm.customfields;

      let customFieldPlaceholder = '';

      return (
        Object.keys(customFields).map((key, index) => {
          const customFieldItem = customFields[key];
          return (
            <div className="dd-form-text-field" key={index}>
             <TextField
                name="formTextField"
                className="metered-form-textfield"
                // id="first-textfield"
                id="metered-form-textfield-desc"
                // maxLength={10}
                margin="dense"
                fullWidth
                placeholder={customFieldPlaceholder}
                label={customFieldItem.label}
                onChange={this.handleTextChange.bind(this)}
                required={true}
                InputLabelProps={{
                  shrink: true
                }}
                inputProps={{
                  maxLength: 10,
                }}

                // error={false}
                error={this.state.textFieldError}
                helperText={this.state.textFieldErrorMsg}
             />
            </div>
          );
        })
      );
    }
  }

Here is my handleChange function for TextField:

handleTextChange = () => {
    const el = document.getElementById('metered-form-textfield-desc');
    
    this.setState({
      textFieldValueLength: el.value.length
    });
    
    if(this.state.textFieldValueLength === el.maxLength-1) {
      console.log('Exceeded number of characters');
      this.setState({
        textFieldError: true,
        textFieldErrorMsg: 'Exceeded maximum number of characters'
      });
    } else if(this.state.textFieldValueLength !== el.maxLength) {
      this.setState({
        textFieldError: false,
        textFieldErrorMsg: ''
      });
    }
  }
2

2 Answers

1
votes

You're checking against only one id which is 'metered-form-textfield-desc' so all the text fields have the same id

const el = document.getElementById('metered-form-textfield-desc');

you can try this just add the value of key which is index(I assume this will make all texfields unique). Thanks @Ted for correcting the value for id.

 id={"metered-form-textfield-desc "+index} 

and do same by passing index to handleTextChange(index) method and append it to

const el = document.getElementById('metered-form-textfield-desc '+index);
1
votes

You can change the handler to be: onChange={(e) => this.handleTextChange(e)}

and in the handler:

handleTextChange = (e) => {
    const el = e.target;

That'll get you the element that's currently being changed without looking it up by id

Regardless which route you go, you do need to be sure to give them unique id's.