aakriti priya
aakriti priya

Reputation: 119

how to auto populate data in the dialog box in react js?

I have a root component.From that I am calling the welcome page which is displaying the details of the students already registered along with edit and delete button in each row. The delete function is working fine which is used to delete a row,But my requirement is that when i click on the edit button,the details of the student selected, should auto populate in the dialog box and once updating is complete,the finalized result should be published back to the starting page. App-->Todo.js-->EditDialog.js

App.js


import React, { Component } from 'react';
import FormDialog from './FormDialog'
import Todo from './ToDo'
import EditDialog from './EditDialog'



import './App.css';



class App extends Component {

  constructor(props) {
    super(props);
    this.state = {
      mode: false
    };

  }

  showForm()
  {
    this.setState({mode:!this.state.mode})
  }

  render() {
    return (
      <div className="App">        
        <button onClick={this.showForm.bind(this)}>Welcome</button>
        {this.state.mode? <Todo/>:null}


        </div>

    );
  }
}

export default App;

Todo.js

import React, { Component } from 'react';
import './Todo.css'
import EditDialog from './EditDialog'
import FormDialog from './FormDialog'
import Dialog from '@material-ui/core/Dialog';
import { thisExpression } from '@babel/types';

class Todo extends Component {

  state = {    edit: false, id: null,view:false,editview:false,
    students: [
      { id: 1, name: 'Wasif', age: 21, email: '[email protected]' },
      { id: 2, name: 'Ali', age: 19, email: '[email protected]' },
      { id: 3, name: 'Saad', age: 16, email: '[email protected]' },
      { id: 4, name: 'Asad', age: 25, email: '[email protected]' },
      { id: 5, name: 'kiwi', age: 20, email: '[email protected]' }
   ], }



   onDeleteHandle() {let id = arguments[0];
    this.setState({students:this.state.students.filter(item => {if (item.id !== id)
       {return item;}})});}


  onUpdateHandle(id,name,age,email){

    this.setState({students: this.state.students.map(item => {
      if (item.id === this.state.id){
        item['id'] = id;        
        item['name']=name;
        item['age']=age;
        item['email']=email;
      }return item;})})
      this.setState({edit: false});
  }


  signUpDialog(){
    this.setState({view:!this.state.view})
  }   

  editFormDialog(){
    this.setState({editview:!this.state.editview})
  }


  renderEditForm() {
    if (this.state.edit) {
    return <form onSubmit={this.onUpdateHandle.bind(this)}>
    <input type="text" name="updatedItem" className="item" defaultValue={this.state.id} />
    <input type="text" name="updatedItem1" className="item" defaultValue={this.state.name} />
    <input type="text" name="updatedItem2" className="item" defaultValue={this.state.age} />
    <input type="text" name="updatedItem3" className="item" defaultValue={this.state.email} />
    <button className="update-add-item">Update</button> 
    </form>    }  }


    onEditHandle(event) {
    this.setState({edit: true,id: arguments[0],name:arguments[1],age:arguments[2],email:arguments[3]});}


    onSubmitHandle(id,name,age,email) { 

      this.setState({students: [...this.state.students, {
        id:id,
        name:name,
        age:age,
        email:email
      }]})
    }; 



     render() 

          {    
           return<div style={{width: "500px",background : "beige"}} >     


                  <button onClick={this.signUpDialog.bind(this)}>Sign-UP</button>
                 {this.state.view? <FormDialog details={this.onSubmitHandle.bind(this)}/> :null}

                   <table>{this.state.students.map(abc => (<tr><td>{abc.id}</td><td>{abc.name}</td><td>{abc.age}</td><td>{abc.email}</td><td>
                    <button onClick={this.onDeleteHandle.bind(this, abc.id)}>Delete</button></td>
                    <button onClick={this.editFormDialog.bind(this)}>Edit</button>
                    {this.state.editview? <EditDialog updDetails={this.onUpdateHandle.bind(this)}/>:null}

                    </tr>))}</table> </div>  
              }
            }

              export default Todo;

EditDialog.js

import React, {Component} from 'react';
import Todo from './ToDo'
import Button from '@material-ui/core/Button';
import TextField from '@material-ui/core/TextField';
import Dialog from '@material-ui/core/Dialog';
import DialogActions from '@material-ui/core/DialogActions';
import DialogContent from '@material-ui/core/DialogContent';
import DialogContentText from '@material-ui/core/DialogContentText';
import DialogTitle from '@material-ui/core/DialogTitle';


class EditDialog extends Component{
    constructor(props){

        super(props);
        this.state={editDetails: true,view:false}
    }
    onUpdateHandle(event){
        event.preventDefault();
        this.setState({students: this.state.students.map(item => {
          if (item.id === this.state.id){
            item['id'] = event.target.updatedItem.value;        
            item['name']=event.target.updatedItem1.value;
            item['age']=event.target.updatedItem2.value;
            item['email']=event.target.updatedItem3.value;
          }return item;})})
          this.setState({edit: false});
      }
    renderEditForm() {
        if (this.state.editDetails) {
        return <form onSubmit={this.onUpdateHandle.bind(this)}>
        <input type="text" name="updatedItem" className="item" defaultValue={this.state.id} />
        <input type="text" name="updatedItem1" className="item" defaultValue={this.state.name} />
        <input type="text" name="updatedItem2" className="item" defaultValue={this.state.age} />
        <input type="text" name="updatedItem3" className="item" defaultValue={this.state.email} />
        <button className="update-add-item">Update</button> 
        </form>    }  }
         handleClose(){
            this.setState({view:!this.state.view})
          }




    render()
    {
     return(
     <div> 


          <Dialog  open>
          <DialogTitle>Edit The Details</DialogTitle>
              <form>
              <label >ID</label>
                   <input type="number"  name="id" className="item"  />
                 <label>Name</label>
                   <input type="text" name="item" className="item"  />
                   <label>age</label>
                   <input type="number" name="xyz" className="item"  />
                   <label>email</label>
                   <input type="text" name="email" className="item"  />  
                   <button className="btn-add-item" >Add</button> 

                  </form>
                  <Button onClick={this.handleClose.bind(this)} color="primary">
            Cancel
          </Button></Dialog>   


     </div> )

    }

}
export default EditDialog;

I have used Callback function and passing the updating function. But for the EditDialog box,the details arent autopopulating and also i need to perform the update in dialog box and publish the result back.

Upvotes: 1

Views: 2715

Answers (1)

Vahid
Vahid

Reputation: 3442

A Problem:

You put your <EditDialog /> into your Array loop (students.map) in the file ToDo.js, so when your state (state.editview) becomes true you have 5 dialogs that are shown together, so you cannot see the first one.

So lets put it outside of your loop (map):

// FROM HERE
</tr>))
}
</table>
// TO HERE
{this.state.editview? <EditDialog updDetails={this.onUpdateHandle.bind(this)}/>:null}
</div>

Your Answer:

You should pass the current student as a props to your dialog, so you can view the one that is clicked. Something similar to your onDeleteHandle function. Do the steps below:

1) Add a state of your currentStudent to your ToDo state:

state = {
        edit: false, id: null, view: false, editview: false,
        students: [
            {id: 1, name: 'Wasif', age: 21, email: '[email protected]'},
            {id: 2, name: 'Ali', age: 19, email: '[email protected]'},
            {id: 3, name: 'Saad', age: 16, email: '[email protected]'},
            {id: 4, name: 'Asad', age: 25, email: '[email protected]'},
            {id: 5, name: 'kiwi', age: 20, email: '[email protected]'}
        ],
        currentStudent: {} // ADD THIS ONE
    }

2) Pass your student ID to your function editFormDialog just like your delete one: (abc.id)

<button onClick={this.editFormDialog.bind(this, abc.id)}>Edit</button>

3) In your editFormDialog function find your student just like the one you did in onUpdateHandle but this time you have to find the equal ID and update your currentStudent state:

editFormDialog() {

        let id = arguments[0]; // Or better to pass it as a parameter: editFormDialog(id) { ... }
        this.setState({
            currentStudent: this.state.students.filter(item => {
                if (item.id === id) { // IDs should be Equal
                    return item;
                }
            })
        });

        this.setState({editview: !this.state.editview})
    }

4) Now you have your currentStudent in your state. So you have to have it in your <EditDialog />, and so you can access it into your EditDialog class (EditDialog.js). Add a property to your <EditDialog />, I named it currentStudent like this:

{
    this.state.editview
        ? <EditDialog
            currentStudent={this.state.currentStudent} // THIS PROPERTY
            updDetails={this.onUpdateHandle.bind(this)}
        />
        : null
}

5) Now you can access your currentStudent in the EditDialog class like this:

// Add a State to EditDialog
this.state = {
      editDetails: true,
      view: false,
      updatedValues: {
           id: null,
           email: null
      }
}

// We use this to Mount it for the first time (Prevent Loop Renders)    
componentDidMount() {
    this.setState({
        updatedValues: {
            id: this.props.currentStudent[0].id,
            email: this.props.currentStudent[0].email
        }
    });
}

// We should do this to update the input value to the state
<input type="text" name="email" className="item" onInput={this.updateStateHandler} value={this.state.updatedValues.email}/>

// And we of course need the updateHandler method
updateStateHandler = (e) => {
    this.setState({
        updatedValues: {
            ...this.state.updatedValues,
            email: e.target.value
        }
    });
};

I've just filled the email input in the render() method. You could fill the other ones too.

6) Now for passing the data back to the your ToDo and update the table with the new values, you have to add handleUpdate method in your dialog like this:

handleUpdate(e) {
    e.preventDefault();
    this.props.closeModal();
    this.props.updateStudentHandler(this.state.updatedValues);
}

7) So you need to pass closeModal and updateStudentHandler from your ToDo class. Your EditDialog should be something like this:

<EditDialog
      currentStudent={this.state.currentStudent}
      updDetails={this.onUpdateHandle.bind(this)}
      updateStudentHandler={this.updateStudent}
      closeModal={this.closeModal}
/>

And the handlers:

updateStudent = (updatedValues) => {

    let newStudents = [...this.state.students];
    newStudents.map(
        student => {
            if (student.id === updatedValues.id) {
                student.email = updatedValues.email;
            }
        }
    );

    this.setState({
        students: newStudents
    });
}

closeModal = () => {
    this.setState({
        editview: false
    });
}

NOTE 1: To closing the dialog, I saw that you change the state of the EditDialog class which was wrong. You should handle that in your ToDo state like the closeModal method at the top.

NOTE 2: To access this in the methods above, you should use ES6 arrow functions.

At last your ToDo and EditDialog classes should look like this:

ToDo.js

import React, {Component} from 'react';
import './Todo.css'
import EditDialog from './EditDialog'
import FormDialog from './FormDialog'
import Dialog from '@material-ui/core/Dialog';
import {thisExpression} from '@babel/types';

class Todo extends Component {

    state = {
        edit: false, id: null, view: false, editview: false,
        students: [
            {id: 1, name: 'Wasif', age: 21, email: '[email protected]'},
            {id: 2, name: 'Ali', age: 19, email: '[email protected]'},
            {id: 3, name: 'Saad', age: 16, email: '[email protected]'},
            {id: 4, name: 'Asad', age: 25, email: '[email protected]'},
            {id: 5, name: 'kiwi', age: 20, email: '[email protected]'}
        ],
        currentStudent: {}
    }

    onDeleteHandle() {
        let id = arguments[0];
        this.setState({
            students: this.state.students.filter(item => {
                if (item.id !== id) {
                    return item;
                }
            })
        });
    }

    onUpdateHandle(id, name, age, email) {

        this.setState({
            students: this.state.students.map(item => {
                if (item.id === this.state.id) {
                    item['id'] = id;
                    item['name'] = name;
                    item['age'] = age;
                    item['email'] = email;
                }
                return item;
            })
        })
        this.setState({edit: false});
    }

    signUpDialog() {
        this.setState({view: !this.state.view})
    }

    editFormDialog(id) {

        // let id = arguments[0];
        this.setState({
            currentStudent: this.state.students.filter(item => {
                if (item.id === id) {
                    return item;
                }
            })
        });

        this.setState({editview: !this.state.editview})
    }

    updateStudent = (updatedValues) => {

        let newStudents = [...this.state.students];
        newStudents.map(
            student => {
                if (student.id === updatedValues.id) {
                    student.name = updatedValues.name;
                    student.age = updatedValues.age;
                    student.email = updatedValues.email;
                }
            }
        );

        this.setState({
            students: newStudents
        });
    }

    closeModal = () => {
        this.setState({
            editview: false
        });
    }

    renderEditForm() {
        if (this.state.edit) {
            return <form onSubmit={this.onUpdateHandle.bind(this)}>
                <input type="text" name="updatedItem" className="item" defaultValue={this.state.id}/>
                <input type="text" name="updatedItem1" className="item" defaultValue={this.state.name}/>
                <input type="text" name="updatedItem2" className="item" defaultValue={this.state.age}/>
                <input type="text" name="updatedItem3" className="item" defaultValue={this.state.email}/>
                <button className="update-add-item">Update</button>
            </form>
        }
    }

    onEditHandle(event) {
        this.setState({edit: true, id: arguments[0], name: arguments[1], age: arguments[2], email: arguments[3]});
    }

    onSubmitHandle(id, name, age, email) {

        this.setState({
            students: [...this.state.students, {
                id: id,
                name: name,
                age: age,
                email: email
            }]
        })
    };

    render() {
        return <div style={{width: "500px", background: "beige"}}>
            <table>
                <tbody>
                {
                    this.state.students.map(abc => (<tr key={abc.id}>
                        <td>{abc.id}</td>
                        <td>{abc.name}</td>
                        <td>{abc.age}</td>
                        <td>{abc.email}</td>
                        <td>
                            <button onClick={this.onDeleteHandle.bind(this, abc.id)}>Delete</button>
                        </td>
                        <td>
                            <button onClick={this.editFormDialog.bind(this, abc.id)}>Edit</button>
                        </td>
                    </tr>))
                }
                </tbody>
            </table>

            {
                this.state.editview
                    ? <EditDialog
                        currentStudent={this.state.currentStudent}
                        updDetails={this.onUpdateHandle.bind(this)}
                        updateStudentHandler={this.updateStudent}
                        closeModal={this.closeModal}
                    />
                    : null
            }

        </div>
    }
}

export default Todo;

EditDialog.js

import React, {Component} from 'react';
import Button from '@material-ui/core/Button';
import TextField from '@material-ui/core/TextField';
import Dialog from '@material-ui/core/Dialog';
import DialogActions from '@material-ui/core/DialogActions';
import DialogContent from '@material-ui/core/DialogContent';
import DialogContentText from '@material-ui/core/DialogContentText';
import DialogTitle from '@material-ui/core/DialogTitle';

class EditDialog extends Component {
    constructor(props) {
        super(props);
        this.state = {
            editDetails: true,
            view: false,
            updatedValues: {
                id: null,
                name: null,
                age: null,
                email: null
            }
        }
    }

    onUpdateHandle(event) {
        event.preventDefault();
        this.setState({
            students: this.state.students.map(item => {
                if (item.id === this.state.id) {
                    item['id'] = event.target.updatedItem.value;
                    item['name'] = event.target.updatedItem1.value;
                    item['age'] = event.target.updatedItem2.value;
                    item['email'] = event.target.updatedItem3.value;
                }
                return item;
            })
        })
        this.setState({edit: false});
    }

    renderEditForm() {
        if (this.state.editDetails) {
            return <form onSubmit={this.onUpdateHandle.bind(this)}>
                <input type="text" name="updatedItem" className="item" defaultValue={this.state.id}/>
                <input type="text" name="updatedItem1" className="item" defaultValue={this.state.name}/>
                <input type="text" name="updatedItem2" className="item" defaultValue={this.state.age}/>
                <input type="text" name="updatedItem3" className="item" defaultValue={this.state.email}/>
                <button className="update-add-item">Update</button>
            </form>
        }
    }

    handleClose() {
        this.setState({view: !this.state.view})
    }

    handleUpdate(e) {
        e.preventDefault();
        this.props.closeModal();
        this.props.updateStudentHandler(this.state.updatedValues);
    }

    updateStateHandler = (e) => {
        let newUpdatedValues = {};
        switch (e.target.name) {
            case 'name':
                newUpdatedValues = {
                    ...this.state.updatedValues,
                    name: e.target.value
                };
                break;
            case 'age':
                newUpdatedValues = {
                    ...this.state.updatedValues,
                    age: e.target.value
                };
                break;
            case 'email':
                newUpdatedValues = {
                    ...this.state.updatedValues,
                    email: e.target.value
                };
                break;
            default:
                break;
        }

        this.setState({
            updatedValues: newUpdatedValues
        });
    };

    componentDidMount() {
        this.setState({
            updatedValues: {
                id: this.props.currentStudent[0].id,
                name: this.props.currentStudent[0].name,
                age: this.props.currentStudent[0].age,
                email: this.props.currentStudent[0].email
            }
        });
    }

    render() {
        return (
            <div>
                <Dialog open>
                    <DialogTitle>Edit The Details</DialogTitle>
                    <form>
                        <label>ID</label>
                        <input type="number" name="id" className="item"
                               value={this.state.updatedValues.id} />
                        <label>Name</label>
                        <input type="text" name="name" className="item"
                               onInput={this.updateStateHandler}
                               value={this.state.updatedValues.name} />
                        <label>age</label>
                        <input type="number" name="age" className="item"
                               onInput={this.updateStateHandler}
                               value={this.state.updatedValues.age} />
                        <label>email</label>
                        <input type="text" name="email" className="item"
                               onInput={this.updateStateHandler}
                               value={this.state.updatedValues.email} />
                        <button className="btn-add-item" onClick={this.handleUpdate.bind(this)}>Add</button>

                    </form>
                    <Button onClick={this.handleClose.bind(this)} color="primary">
                        Cancel
                    </Button></Dialog>
            </div>)
    }

}

export default EditDialog;

Upvotes: 1

Related Questions