1

I am having a root component from which I am calling the Todo Component which is basically displaying details of already registered students along with edit and delete functions.

When clicking on the edit button a dialog box is opening with the fields.But the requirement is that the data should be pulled from Todo component to Dialog component.It should be auto populated from the Todo component to the dialog and it should flow back to the Todo. I am having this code initially where the fields are opening on the same page. But my requirement is that it should flow to dialog component .

Initially Todo.js

import React, { Component } from 'react';
import './Todo.css'
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(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});
  }


  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"}} >     
               {this.renderEditForm()}         

                  <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.onEditHandle.bind(this,abc.id,abc.name,abc.age,abc.email)}>Edit</button>
                    </tr>))}</table> </div>  
              }
            }

              export default Todo;

Modified 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;

And i have defined 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,fish:true,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]' }
         ]}
    }
  uponFormSubmit(event){
      alert("help")
      event.preventDefault();
    this.props.updDetails(
      event.target.id.value,
      event.target.item.value,
      event.target.xyz.value,
      event.target.email.value
    );

  }
    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>    }  }


         handleCloseForm(){
            this.setState({fish:!this.state.fish})
          }




    render()
    {
     return(
     <div> 


          <Dialog  open>
          <DialogTitle>Edit The Details</DialogTitle>
              <form onSubmit={this.uponFormSubmit}>
              <label >ID</label>
                   <input  type="number"  name="id" className="item" value={this.state.id} />
                 <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="update-add-item" >Update</button>              
                  </form>
                  <Button onClick={this.handleCloseForm.bind(this)} color="primary">
            Cancel
          </Button></Dialog>   


     </div> )

    }

}
export default EditDialog;

2 Answers 2

1

Right now it looks like your code is sending data back to Todo component. In order for the data to also flow into the Dialog, you would have to pass down the props, just like you passed down the callback function updDetails(). Then using this.props.email etc, instead of initializing them in the Dialog's state. Then your data would flow into the component, as well as out.

Set defaultValue={this.props.id} instead of this.state.id

You're also binding your function in render when passing them as props. I suggest using ES6 arrow functions instead, as it removes the need to bind them explicitly in either render or constructor.

You can do it this way: In Render, remove .bind(this) --> updDetails={this.onUpdateHandle}

Function itself transformed to arrow function onUpdateHandle = (id,name,age,email) => { // Your code }

This isn't necessary, but it makes the code a bit more clean.

Edit: I just realised that you are not using renderEditForm() in your render method. This is the function that uses defaultValue to auto-populate the dialog as you wanted. Instead it looks like you have another form in your render method, if you used the renderEditForm() function, it should auto-populate as expected.

Sign up to request clarification or add additional context in comments.

Comments

0

But the requirement is that the data should be pulled from Todo component to Dialog component.

If you want to use data from Todo component you should pass the data as props not declaring state in the EditDialog component.

PS:

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

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

Updating state that relies on previous state, you should use prevState in setState() function.

    signUpDialog() {
        this.setState(prevState => {
            return { view: !prevState.view }
        })
    }

1 Comment

it happens to be that i am neither able to send data to EditDialog nor from EditDialog to Todo.I want the data from the row which is selected to autopopulate on the dialog and once it is edited/Updated it should flow back to Todo

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.