Trying to switch between modal components using React

Viewed 1221

So I have a start page that gives options to open a login modal or sign up modal. However, once you are in the login modal I give an option so you can switch to sign up modal. However, I can't seem to get this to work. The one time I got it to work, the modal showed up in the wrong section of the screen since it was being opened in relation to the login modal and not the start page.

I am new to React so any insight would be appreciated. Should I use redux, since I can't pass props from child to parent. So that way when I return to start page I can rerender with info saying that I had clicked sign-up link on the login modal.

function LoginContent(props) {

    const [ open, setOpen ] = useState(false)
    const { show, closeModal } = props;

    function handleSubmit(e){
        e.preventDefault();
    }

    function handleSignUpButton(){
      closeModal();
      console.log(open)
      setOpen(!false)
      console.log(open)
    }


    //added so that the component doesn't get affected by parent css
    //and is being rendered from the "modal-root" DOM node from the index.html file
    return ReactDOM.createPortal(
      <>
      <div className={show ? "overlay" : "hide"} onClick={closeModal} />
        <div className={show ? "modal" : "hide"}>
          <button onClick={closeModal} id="close">X</button>
       
        <div className="login_form">
            <h1> Log in to Continue </h1>
            <form onSubmit={handleSubmit}>
                <input className="username" type='text' name='username' placeholder='Email Address' />
                <input className="password" type='password' name='password' placeholder='password' />
                <button className="login_button"> Sign In</button>
            </form>
        </div>
        <div className="login_demo">
            <h3 className="login_demo_pointer" type="submit">Demo Login</h3>
            </div>
        <hr />
        <div className="login_switch">Don't have an account. 
        <button className="signup_link" onClick={handleSignUpButton}>Sign Up</button>
        {open && <SignUpContent open={open} closeModal={closeModal} show={show} />} </div>
        </div>
      </>, document.getElementById("modal-root")
    );
}
function Start() {
    const history = useHistory();

    const [showLogin, setLogin ] = useState(false);
    const openModalLogin = () => setLogin(true);
    const closeModalLogin = () => setLogin(false);

    const [showSignUp, setShow ] = useState(false);
    const openModalSignUp = () => setShow(true);
    const closeModalSignUp = () => setShow(false);


    return (
        
        <div className="bodyStart">
            <img src="https://i.imgur.com/5gjRSmB.gif" alt="" id="bg" />
            <div className="start_logo">
                <img src={require("../styling/logo.png")} alt="" onClick={() => {
                history.push('/home')
                history.go(0)}} className="logo" />
            </div>
        <div className="start">
            
        <div className="start_heading">
            <h2>Mother Nature is Calling.</h2>
            <h4>Find a place to recharge and escape the day to day.</h4>
        </div>
        <div className="start_location">
        <p>Where?</p>
        <div className="start_input">
        <input type="text" placeholder="anywhere" />
        
            <ArrowForwardIcon onClick={() => {
                history.push('/search')
                history.go(0)}}
            className="arrow" fontSize="large"/>  
        
        </div>
        </div>
        <div className="start_authentication">
        <Button className="login" 
            variant="contained" 
            color="primary" 
            size="large"
            onClick={() => openModalLogin()}> Login </Button>
            {showLogin && <LoginContent closeModal={closeModalLogin} show={showLogin} />}

        <Button className="signup" 
            variant="contained" 
            size="large"
            onClick={()=> openModalSignUp()}> Sign-Up </Button>
            {showSignUp && <SignUpContent closeModal={closeModalSignUp} show={showSignUp} />}
        </div>
        </div>
        </div>
        
    )
}

1 Answers

I have made similar modals with Material-UI. You can change loginOpen state and signupOpen states in modals. See codepen below

Login Modal

Codepen

const { useState } = React;
const { Button, Dialog, DialogTitle, DialogContent, DialogActions } = MaterialUI;


function LoginDialog(props) {
  const { open, setLoginOpen, setSignupOpen } = props;

  const switchSignup = (event) => {
    setLoginOpen(false)
    setSignupOpen(true)
  }

  return (
    <Dialog aria-labelledby="simple-dialog-title" open={open}>
      <DialogTitle id="simple-dialog-title">LOGIN</DialogTitle>
      <DialogContent>If you don't have an account, press SIGNUP</DialogContent>
      <DialogActions>
        <Button onClick={(event) => {setLoginOpen(false)}}>CLOSE</Button>
        <Button>LOGIN</Button>
        <Button onClick={switchSignup}>SIGNUP</Button>
      </DialogActions>
    </Dialog>
  );
}

function SignupDialog(props) {
  const { open, setLoginOpen, setSignupOpen } = props;

  const switchLogin = (event) => {
    setSignupOpen(false)
    setLoginOpen(true)
  }

  return (
    <Dialog aria-labelledby="simple-dialog-title" open={open}>
      <DialogTitle id="simple-dialog-title">SIGNUP</DialogTitle>
      <DialogContent>If you have an account, press LOGIN</DialogContent>
      <DialogActions>
        <Button onClick={(event) => {setSignupOpen(false)}}>CLOSE</Button>
        <Button>SIGNUP</Button>
        <Button onClick={switchLogin}>LOGIN</Button>
      </DialogActions>
    </Dialog>
  );
}

const App = () => {
  const [loginOpen, setLoginOpen] = useState(false)
  const [signupOpen, setSignupOpen] = useState(false)
  
  const handleLogin = (event) => {
    setLoginOpen(true)
  }
  
  const handleSignup = (event) => {
    setSignupOpen(true)
  }
    
  return (
    <div>
      <Button variant='contained' color='primary' onClick={handleLogin} >
        LOGIN
      </Button>
      <Button variant='outlined' color='primary' onClick={handleSignup} >
        SIGNUP
      </Button>
      <LoginDialog open={loginOpen} setLoginOpen={setLoginOpen} setSignupOpen={setSignupOpen} />
      <SignupDialog open={signupOpen} setLoginOpen={setLoginOpen} setSignupOpen={setSignupOpen} />
    </div>
  )
}


ReactDOM.render(<App />, document.getElementById("root"));

Related