React Pass the value input in the other Pages - reactjs

I have a homepage where they can click the modal button. after the button click the modal will show. then in the modal they will input a text and when they click submit the text they input should be display in the homepage. Currently the one i did is not displaying in homepage when click the submit button. Please help. Thank you
This is the code:
https://codesandbox.io/s/competent-rgb-lk4ws

Modal
In your Modal component you can create a event when the Submit button is clicked:
import React from "react";
import "./modal.css";
// Create new event: onSubmitClick
function Modal({ setOpenModal, onSubmitClick }) {
// It`s function get name value and pass to onSubmitClick
function getData() {
const nameValue = document.getElementById("name").value;
onSubmitClick(nameValue);
setOpenModal(false);
}
return (
<div className="modalBackground">
<div className="modalContainer">
<div className="titleCloseBtn">
<button
onClick={() => {
setOpenModal(false);
}}
>
X
</button>
</div>
<div className="title">Forms</div>
<div className="body">
<input id="name" placeholder="Enter Your Name" />
</div>
<div className="footer">
<button
onClick={() => {
setOpenModal(false);
}}
id="cancelBtn"
>
Cancel
</button>
{/* The onclick should be onClick */}
<button onClick={getData}>Submit</button>
</div>
</div>
</div>
);
}
export default Modal;
Home
In home page you can get the event and use the new name value
import React, { useState } from "react";
import Modal from "../../src/components/Modal/modal.js";
const Home = () => {
const [modalOpen, setModalOpen] = useState(false);
const [name, setName] = useState("");
function handleModalSubmitClick(nameValue) {
// Receive new value, and set in a state
setName(nameValue);
}
return (
<div class="hello">
<h1>Hey, click on the button to open the modal.</h1>
<span>name: {name}</span>
<button
onClick={() => {
setModalOpen(true);
}}
class="button is-pulled-right"
>
Button
</button>
{modalOpen && (
<Modal
setOpenModal={setModalOpen}
onSubmitClick={handleModalSubmitClick} // Bind a function to handle a event
/>
)}
</div>
);
};
export default Home;

Related

How can I close my modal by clicking the close button in reactjs?

How can I close my modal by clicking the close button in reactjs ? My closeModal function is not working. Help me please !!! When I click the close button, the modal does not close.
When, I click on open the modal button then it is working, but when i click on close button then close button is not working. I am using the hooks in my project. Below, I have mentioned my code :
Gallery.jsx
import React, { useState } from 'react'
import "./gallery.css"
import { FaChevronLeft, FaChevronRight } from "react-icons/fa";
const Gallery = ({ pictures, source1, source2, source3, source4, source5, source6, title }) => {
const [clickedImg, setClickedImg] = useState(null);
const [currentPictureIndex, setCurrentPictureIndex] = useState(0);
const handleClick = (e, pictures, title ) => {
setClickedImg({e, pictures, title })
console.log("showmodal state before any click")
};
const closeModal = (e) => {
try {
if (e.target.classList.contains("dismiss")) {
setClickedImg(null);
console.log(e.target.classList.contains("dismiss"))
}
} catch (error) {
console.log(error);
}
};
const handleNextClick = () => {
const nextIndex = currentPictureIndex === pictures.length - 1 ? 0 : currentPictureIndex + 1;
setCurrentPictureIndex(nextIndex);
};
const handlePrevClick = () => {
const prevIndex = currentPictureIndex === 0 ? pictures.length - 1 : currentPictureIndex - 1;
setCurrentPictureIndex(prevIndex);
};
return (
<div className="gallery" onClick={handleClick}>
<div className="galleryBox1">
<img src={source1} alt={title} className="galleryCard"/>
</div>
<div className="galleryBox2">
<div className="galleryBox3">
<div className="galleryBoxa">
<img src={source2} alt={title} className="galleryCardTwo"/>
</div>
<div className="galleryBoxb">
<img src={source3} alt={title} className="galleryCardTwo"/>
</div>
</div>
<div className="galleryBox5">
<div className="galleryBoxc">
<img src={source4} alt={title} className="galleryCardTwo"/>
</div>
<div className="galleryBoxd">
<img src={source5} alt={title} className="galleryCardTwo"/>
</div>
</div>
</div>
{
clickedImg && (
<div className="galleryModal dismiss" onClick={closeModal}>
<img
src={pictures[currentPictureIndex]}
alt={title}
className="galleryModalImg"
/>
<button className="galleryModalButton dismiss" onClick={closeModal}>
Fermer
</button>
{pictures.length !== 1 && (
<div className="galleryModalArrows" onClick={handleNextClick}>
<FaChevronRight className="galleryModalNext" />
</div>
)}
{pictures.length !== 1 && (
<div className="galleryModalArrows" onClick={handlePrevClick}>
<FaChevronLeft className="galleryModalPrev" />
</div>
)}
</div>
)}
</div>
)
}
export default Gallery
How can I close my modal by clicking the close button in reactjs ?
I have figured out the reason. As you have added onClick in the parent div (className="gallery"), That's why, whenever you are clicking on any button in the div it is triggering a click on the main div's handleClick method.
If you console on the handleClick and closeModal function. You will see that if you click on the close button you will see the console that is written in the handleClick() function.
So I tried to move the onClick={handleClick} from that parent div. And put it in a children div. You can put it on className="galleryBox1" this div or any other div. Then it will work fine.

React: Child don't update parent's state

I'm new to React and I was trying to create a Modal using mui that opens and closes based on parent's state.
The problem is that the modal opens well based on state but upon closing, the modal onClose function works well, but when I click on Button that has the same with the same update state function it doesn't work.
Here's my parent component
const TableIcon = props => {
const {title,icon}=props;
// handling modal functionality
const [modalOpen, setModalOpen] = useState(false);
const handleModalOpen = () => {
setModalOpen(true);
};
const handleModalClose = () => {
setModalOpen(false);
};
console.log('modal', modalOpen)
return (
<button className={styles.button} title={title} onClick={()=>handleModalOpen()}>
{icon}
<ActionModal
open={modalOpen}
handleClose={handleModalClose}
handleOpen={handleModalOpen}
/>
</button>
)
}
and here is the modal component
const ActionModal=(props)=> {
const {open,handleOpen,handleClose}=props;
console.log(props,'modal')
return (
<div>
<Modal
open={open}
onClose={handleClose}
aria-labelledby="modal-modal-title"
aria-describedby="modal-modal-description"
>
<Box className={styles.box}>
<div className={styles.header}>
<div className={styles.icon}>
<BsFillTrashFill/>
</div>
</div>
<div className={styles.content}>
<h2>You are about to delete a school</h2>
<h3>School Name/Tuituion</h3>
<p>This will delete the school from the database
Are you sure?</p>
</div>
<div className={styles.footer}>
<Button color='var(--unnamed-color-ffffff)' name='Cancel' onClick={handleClose}/>
<Button color='var(--unnamed-color-f53748)' name='Confirm'/>
</div>
</Box>
</Modal>
</div>
);
}
and here is the button component
const Button=(props)=>{
const {color,onClick,icon,name}=props;
return <div className={styles.container} style={{background:color}} onClick={()=>onClick()}>
{icon}
<span>{name}</span>
</div>
}
and the Button onClick works just fine
The problem is that your <ActionModal> component is inside the <button> tag. So when clicking the Cancel button in the modal you first get the call to handleModalClose, immediately followed by the call to handleModalOpen, because the "click" is getting passed to the button that opens the modal.
You need to change the code in <TableIcon> to something like:
return (
<>
<button title={title} onClick={() => handleModalOpen()}>
{icon}
</button>
<ActionModal open={modalOpen} handleClose={handleModalClose} />
</>
);
You can use this Stackblitz example.

How to open dynamic modal with react js

I am trying to convert the HTML/Javascript modal to React js.
In Reactjs, I just want to open the modal whenever the user clicks the View Project button.
I have created a parent component (Portfolio Screen) and a child component (Portfolio Modal). The data I have given to the child component is working fine but the modal opens the first time only and then does not open. Another problem is that the data does not load even when the modal is opened the first time.
Codesandbox link is here.
https://codesandbox.io/s/reverent-leftpad-lh7dl?file=/src/App.js&resolutionWidth=683&resolutionHeight=675
I have also shared the React code below.
For HTML/JavaScript code, here is the question I have asked before.
How to populate data in a modal Popup using react js. Maybe with hooks
Parent Component
import React, { useState } from 'react';
import '../assets/css/portfolio.scss';
import PortfolioModal from '../components/PortfolioModal';
import portfolioItems from '../data/portfolio';
const PortfolioScreen = () => {
const [portfolio, setportfolio] = useState({ data: null, show: false });
const Item = (portfolioItem) => {
setportfolio({
data: portfolioItem,
show: true,
});
};
return (
<>
<section className='portfolio-section sec-padding'>
<div className='container'>
<div className='row'>
<div className='section-title'>
<h2>Recent Work</h2>
</div>
</div>
<div className='row'>
{portfolioItems.map((portfolioItem) => (
<div className='portfolio-item' key={portfolioItem._id}>
<div className='portfolio-item-thumbnail'>
<img src={portfolioItem.image} alt='portfolio item thumb' />
<h3 className='portfolio-item-title'>
{portfolioItem.title}
</h3>
<button
onClick={() => Item(portfolioItem)}
type='button'
className='btn view-project-btn'>
View Project
</button>
</div>
</div>
))}
<PortfolioModal portfolioData={portfolio} show={portfolio.show} />
</div>
</div>
</section>
</>
);
};
export default PortfolioScreen;
Child Component
import React, { useState, useEffect } from 'react';
import { NavLink } from 'react-router-dom';
const PortfolioModal = ({ portfolioData, show }) => {
const portfolioItem = portfolioData;
const [openModal, setopenModal] = useState({ showState: false });
useEffect(() => {
setopenModal({
showState: show,
});
}, [show]);
return (
<>
<div
className={`portfolio-popup ${
openModal.showState === true ? 'open' : ''
}`}>
<div className='pp-inner'>
<div className='pp-content'>
<div className='pp-header'>
<button
className='btn pp-close'
onClick={() =>
setopenModal({
showState: false,
})
}>
<i className='fas fa-times pp-close'></i>
</button>
<div className='pp-thumbnail'>
<img src={portfolioItem.image} alt={`${portfolioItem.title}`} />
</div>
<h3 className='portfolio-item-title'>{portfolioItem.title}</h3>
</div>
<div className='pp-body'>
<div className='portfolio-item-details'>
<div className='description'>
<p>{portfolioItem.description}</p>
</div>
<div className='general-info'>
<ul>
<li>
Created - <span>{portfolioItem.creatDate}</span>
</li>
<li>
Technology Used -
<span>{portfolioItem.technologyUsed}</span>
</li>
<li>
Role - <span>{portfolioItem.Role}</span>
</li>
<li>
View Live -
<span>
<NavLink to='#' target='_blank'>
{portfolioItem.domain}
</NavLink>
</span>
</li>
</ul>
</div>
</div>
</div>
</div>
</div>
</div>
</>
);
};
export default PortfolioModal;
You don't have to use one useState hook to hold all your states. You can and I think you should break them up. In the PortfolioScreen component
const [data, setData] = useState(null);
const [show, setShow] = useState(false);
I changed the function Item that is used to set the active portfolio item to toggleItem and changed it's implementation
const toggleItem = (portfolioItem) => {
setData(portfolioItem);
setVisible(portfolioItem !== null);
};
You should use conditional rendering on the PortfolioModal, so you won't need to pass a show prop to it, and you'll pass a closeModal prop to close the PortfolioModal when clicked
{visible === true && data !== null && (
<PortfolioModal
data={data}
closeModal={() => toggleItem()} // Pass nothing here so the default value will be null and the modal reset
/>
)}
Then in the PortfolioModal component, you expect two props, data and a closeModal function
const PortfolioModal = ({ data, closeModal }) => {
And the close button can be like
<button className="btn pp-close" onClick={closeModal}>
...

button onclick refresh page instead of set state to false

I am developing an ecommerce application and I am working on the login.
I want the login to be a pop up box such that when the user click on login button the dialog box will appear and when the user click on the x button the dialog box disappears.
Other things work well except the close(x) button.
When it is clicked it refreshes the page instead of setting setOpenLoginModal to false.
I created a reusable modal then imported it to LoginModal.js which is passed to App.js.
Modal.js
const Modal = ({open, children, handleSubmit}) => {
if(!open) return null
return ReactDom.createPortal(
<>
<form action="" onSubmit={handleSubmit}>
<div style={OVERLAY_STYLE}>
<div style={MODAL_STYLES}>
{children}
</div>
</div>
</form>
</>,
document.getElementById('portal')
)
}
export default Modal
LoginModal.js
import Modal from './Modal'
const LoginModal = ({openLoginModal, setOpenLoginModal}) => {
return (
<div>
<Modal open={openLoginModal} handleSubmit={handleSubmit}>
<div className="d-flex justify-content-center">
<div>
<h4 className="head">eTranzact eCommerce</h4>
<h6 className="sub-heading">Create an account to list your own product</h6>
</div>
<div>
<h2 style={{position: 'absolute', right: '2em'}}>
<button className="close" type="button" onClick={() => setOpenLoginModal(false)}>x</button>
</h2>
</div>
</div>
<hr />
</div>
)
}
export default LoginModal
App.js
import LoginModal from '../Components/LoginModal';
const App = () => {
const [openLoginModal, setOpenLoginModal] = useState(false)
return (
<div>
{
openLoginModal && (
<LoginModal openLoginModal={openLoginModal} setOpenRegisterModal={ () => setOpenRegisterModal(false) } />
)
}
<div className="right-navs">
<button onClick={() => setOpenLoginModal(true)} className="btn btn-primary">
LOGIN
</button>
</div>
</div>
)
}
export default App
This issue is probably with your form, I don't think you are preventing the default. Even though you are saying action="" it will still try and process it like a get action which would be causing it to refresh the page.
const Modal = ({ open, children, handleSubmit }) => {
if (!open) return null
const submit = (e) => {
e.preventDefault()
handleSubmit()
}
return ReactDom.createPortal(
<>
<form action="" onSubmit={submit}>
<div style={OVERLAY_STYLE}>
<div style={MODAL_STYLES}>{children}</div>
</div>
</form>
</>,
document.getElementById('portal')
)
}
export default Modal
I can see you're passing the wrong setState handler to the child component. You have to change setOpenRegisterModal to setOpenLoginModal in your App.js file

onScroll when at the bottom of the div then disable button

Trying to achieve something similar to popular T&C's actions, when you scroll down to the very bottom of the div 'accept' button becomes enabled so you can click on it.
For this example, I am using material-UI components & button becomes disabled when I add 'disabled' within the component, that's all.
Here's the code:
import React from 'react';
import PropTypes from 'prop-types';
import Modal from '#material-ui/core/Modal';
import Button from '#material-ui/core/Button';
import './terms-popup.scss';
const handleScroll = (e) => {
const bottom = e.target.scrollHeight - e.target.scrollTop === e.target.clientHeight;
if (bottom) { console.log('bottom is reached'); }
};
const TermsPopup= ({
isModalOpen,
isOpen,
title,
closeLabel,
showCloseButton,
}) => {
return (
<Modal
aria-labelledby="simple-modal-title"
aria-describedby="simple-modal-description"
open={isOpen}
onClose={() => isModalOpen(false)}
>
<div className="terms-container">
<div className="terms-header">
<h2>{title}</h2>
</div>
<div
className="terms-body"
onScroll={handleScroll}
>
<h3>Sample title</h3>
<p>Sample description would go here</p>
<div className="terms-footer">
{(showCloseButton) ? (
<Button
variant="contained"
type="button"
onClick={() => isModalOpen(false)}
>
{closeLabel}
</Button>
) : null}
</div>
</div>
</Modal>
);
};
TermsPopup.propTypes = {
isModalOpen: PropTypes.func.isRequired,
isOpen: PropTypes.bool.isRequired,
title: PropTypes.string.isRequired,
closeLabel: PropTypes.string,
showCloseButton: PropTypes.bool,
};
TermsPopup.defaultProps = {
closeLabel: 'accept',
showCloseButton: true,
};
export default TermsPopup;
And what I'd like to achieve is when the bottom is reached then Button should change to:
<Button
variant="contained"
type="button"
onClick={() => isModalOpen(false)}
disabled
/>
Move your onScroll event handler into the component itself, and use React state to update your component when the bottom is reached. You can use the state variable to then set the 'disabled' prop on your Button component.
import React, { useState } from 'react';
import PropTypes from 'prop-types';
import Modal from '#material-ui/core/Modal';
import Button from '#material-ui/core/Button';
import './terms-popup.scss';
const TermsPopup= ({
isModalOpen,
isOpen,
title,
closeLabel,
showCloseButton,
}) => {
const [bottom, setBottom] = useState(false);
const handleScroll = (e) => {
const bottom = e.target.scrollHeight - e.target.scrollTop === e.target.clientHeight;
setBottom(bottom)
};
return (
<Modal
aria-labelledby="simple-modal-title"
aria-describedby="simple-modal-description"
open={isOpen}
onClose={() => isModalOpen(false)}
>
<div className="terms-container">
<div className="terms-header">
<h2>{title}</h2>
</div>
<div
className="terms-body"
onScroll={handleScroll}
>
<h3>Sample title</h3>
<p>Sample description would go here</p>
<div className="terms-footer">
{(showCloseButton) ? (
<Button
variant="contained"
type="button"
onClick={() => isModalOpen(false)}
disabled={bottom}
>
{closeLabel}
</Button>
) : null}
</div>
</div>
</Modal>
);
};

Resources