2016-04-28 67 views
6

Attualmente sto cercando di aggiungere la convalida a un modulo che viene creato utilizzando i componenti del materiale-ui. Ho funzionato, ma il problema è che attualmente sto facendo la funzione di convalida è attualmente chiamata a ogni cambiamento di stato nell'input (cioè ogni lettera che viene digitata). Tuttavia, desidero solo che la convalida si verifichi una volta interrotta la digitazione.Convalida modulo con reagente e materiale-

dato il mio codice corrente:

class Form extends React.Component { 

    state = {open: false, email: '', password: '', email_error_text: null, password_error_text: null, disabled: true}; 

    handleTouchTap() { 
     this.setState({ 
      open: true, 
     }); 
    } 

    isDisabled() { 
     let emailIsValid = false; 
     let passwordIsValid = false; 

     if (this.state.email === "") { 
      this.setState({ 
       email_error_text: null 
      }); 
     } else { 
      if (validateEmail(this.state.email)) { 
       emailIsValid = true 
       this.setState({ 
        email_error_text: null 
       }); 
      } else { 
       this.setState({ 
        email_error_text: "Sorry, this is not a valid email" 
       }); 
      } 
     } 

     if (this.state.password === "" || !this.state.password) { 
      this.setState({ 
       password_error_text: null 
      }); 
     } else { 
      if (this.state.password.length >= 6) { 
       passwordIsValid = true; 
       this.setState({ 
        password_error_text: null 
       }); 
      } else { 
       this.setState({ 
        password_error_text: "Your password must be at least 6 characters" 
       }); 
      } 
     } 

     if (emailIsValid && passwordIsValid) { 
      this.setState({ 
       disabled: false 
      }); 
     } 
    } 

    changeValue(e, type) { 
     const value = e.target.value; 
     const nextState = {}; 
     nextState[type] = value; 
     this.setState(nextState,() => { 
      this.isDisabled() 
     }); 
    } 

    login() { 
     createUser(this.state.email, this.state.password); 
     this.setState({ 
      open: false 
     }); 
    } 

    render() { 

     let {open, email, password, email_error_text, password_error_text, disabled} = this.state; 

     const standardActions = (
      <FlatButton 
       containerElement={<Link to="/portal" />} 
       disabled={this.state.disabled} 
       label="Submit" 
       onClick={this.login.bind(this)} 
      /> 
     ); 

     return (
      <div style={styles.container}> 
       <Dialog 
        open={this.state.open} 
        title="Enter Your Details to Login" 
        actions={standardActions} 
       > 
        <span className="hint--right hint--bounce" data-hint="Enter in your email address"> 
         <TextField 
          hintText="Email" 
          floatingLabelText="Email" 
          type="email" 
          errorText={this.state.email_error_text} 
          onChange={e => this.changeValue(e, 'email')} 
         /> 
        </span> 
        <br /> 
        <span className="hint--right hint--bounce" data-hint="Enter your password"> 
         <TextField 
          hintText="Password" 
          floatingLabelText="Password" 
          type="password" 
          errorText={this.state.password_error_text} 
          onChange={e => this.changeValue(e, 'password')} 
         /> 
        </span> 
       </Dialog> 
       <h1>VPT</h1> 
       <h2>Project DALI</h2> 
       <RaisedButton 
        label="Login" 
        primary={true} 
        onTouchTap={this.handleTouchTap.bind(this)} 
       /> 
      </div> 
     ); 
    } 
} 

export default Form; 

C'è un modo che io possa raggiungere il mio funzionalità desiderate, senza fare un grande cambiamento al codice, o ha bisogno di essere completamente riscritta?

Qualsiasi aiuto sarebbe molto apprezzato

Grazie per il vostro tempo

+0

Vorrei davvero raccomandare di consultare http://redux-form.com per questo. ecco un esempio: http://redux-form.com/5.2.1/#/examples/synchronous-validation – kromit

risposta

6

Il controllo deve avvenire dopo un certo ritardo? Una soluzione che ritengo sarebbe sufficiente nella maggior parte delle situazioni sarebbe quella di dividere un po 'il codice. Non attivare la funzione isDisabled() in changedValue(). Invece farlo funzionare sull'evento onBlur invece.

Prova questo:

<TextField 
    hintText="Password" 
    floatingLabelText="Password" 
    type="password" 
    errorText={this.state.password_error_text} 
    onChange={e => this.changeValue(e, 'password')} 
    onBlur={this.isDisabled} 
/> 

e quindi la funzione diventa:

changeValue(e, type) { 
    const value = e.target.value; 
    const nextState = {}; 
    nextState[type] = value; 
    this.setState(nextState); 
} 
+0

Al momento non c'è nessun ritardo, quindi il messaggio di errore verrà mostrato fino a quando i parametri di validazione non saranno soddisfatti, ma voglio fare il controllo in seguito. – BeeNag

+0

In seguito quando esattamente? La mia risposta sopra controllerà quando l'utente "lascia" la casella di testo. Non è quello che stai cercando? – Chris

+0

onBlur non lo sta facendo isDisabled non viene mai chiamato per qualche motivo che presumo significa che l'evento onBlur non sta sparando ?? – BeeNag

0

È possibile utilizzare onblur evento campo di testo. Viene attivato quando l'input perde la messa a fuoco.

+0

Mentre il tuo suggerimento funzionava, probabilmente è meglio aggiornare il valore con ogni tasto premuto, ma invece eseguire la convalida onblur . – Chris

2

Questo library che avevo creato, si prende cura di tutto ciò che riguarda i campi di convalida e supporta componenti materiali-ui come beh ...

Per convalidare i tuoi campi, devi solo avvolgere il componente del campo e hai finito ... risparmiando un sacco di sforzi nella gestione dello stato tuo elfo manualmente.

<Validation group="myGroup1" 
    validators={[ 
      { 
      validator: (val) => !validator.isEmpty(val), 
      errorMessage: "Cannot be left empty" 
      }, ... 
     }]}> 
      <TextField value={this.state.value} 
         className={styles.inputStyles} 
         style={{width: "100%"}} 
         onChange={ 
         (evt)=>{ 
          console.log("you have typed: ", evt.target.value); 
         } 


    }/> 

+0

Se si intende promuovere le proprie librerie, è necessario dichiararlo: vedere [Comportamento di overflow dello stack] (http: // stackoverflow.com/help/behavior) – icc97

+1

Ho modificato la risposta, grazie per la moderazione e l'attenzione. –

0

ho appena pubblicato npm package per la convalida forme. L'esempio di lavoro può essere trovato sul mio github profile

+0

https://node-react-redux.herokuapp.com/login –