I have a panel with 3 buttons, i want to make onclick on every button, a different component will appear in the same place. How can this logic be done?
<AddNotification />
<EditNotification />
<DeleteNotification />
const AdminPanel = () => {
return (
<Card className={classes.input}>
<div><h1>Notification Panel</h1></div>
<form>
<div className="form-group">
<Button type="submit">Add Notification</Button>
</div>
<div className="form-group">
<Button type="submit">Edit Notification</Button>
</div>
<div className="form-group">
<Button type="submit">Delete Notification</Button>
</div>
</form>
</Card>
)
}
CodePudding user response:
Try this if you want to display one component at a time and hide the others when you click a button
const AdminPanel = () => {
const [componentToDisplay, setComponentToDisplay] = useState("")
return (
<>
<Card className={classes.input}>
<div><h1>Notification Panel</h1></div>
<form>
<div className="form-group">
{componentToDisplay !== "add ? (
<Button type="submit" onCLick={() => setComponentTodisplay("add")}>Add Notification</Button>)
:(<AddNotification />)}
</div>
<div className="form-group">
{componentToDisplay !== "edit ? (
<Button type="submit" onCLick={() => setComponentTodisplay("edit")}>Edit Notification</Button>)
:(<EditNotification />)}
</div>
<div className="form-group">
{componentToDisplay !== "delete ? (
<Button type="submit" onCLick={() => setComponentTodisplay("delete")}>Delete Notification</Button>)
:(<DeleteNotification />)}
</div>
</form>
</Card>
</>
)
}
Or if you want to be able to replace every buttons, use this logic with one state per button
const AdminPanel = () => {
const [addNotif, setAddNotif] = useState(false)
const [editNotif, setEditNotif] = useState(false)
const [deleteNotif, setDeleteNotif] = useState(false)
return (
<>
<Card className={classes.input}>
<div><h1>Notification Panel</h1></div>
<form>
<div className={`form-group ${editNotif || deleteNotif ? "display: none" : "display: flex"}`}>
{!addNotif ? (
<Button type="submit" onCLick={() => setAddNotif(true)}>Add Notification</Button>)
:(<AddNotification setAddNotif={setAddNotif} />)}
</div>
<div className={`form-group ${addNotif || deleteNotif ? "display: none" : "display: flex"}`}>
{!editNotif ? (
<Button type="submit" onCLick={() => setEditNotif(true)}>Edit Notification</Button>)
:(<EditNotification setEditNotif={setEditNotif} />)}
</div>
<div className={`form-group ${addNotif || editNotif ? "display: none" : "display: flex"}`}>
{!deleteNotif ? (
<Button type="submit" onCLick={() => setDeleteNotif(true)}>Delete Notification</Button>)
:(<DeleteNotification setDeleteNotif={setDeleteNotif} />)}
</div>
</form>
</Card>
</>
)
}
Then in your component
const AddNotification = ({setAddNotif}) => {
...
return (
...
<button onCLick={() => setAddNotif(false)}>back</button>
...
)
}
Same logic for the other components
CodePudding user response:
To achieve this logic you need to manage which component is displayed using a state.
This means:
- Attribute an arbitrary id to each component.
- Store the id of the active component in a
useState
hook. - Use conditional rendering to display the component that match the current state.
- Update the state to the corresponding Id when clicking on each button.
A small example
const [activePanel, setActivePanel] = React.useState(0)
let currentPanel = <Panel0 />
switch(activePanel){
case 0:
currentPanel = <PanelO />
case 1:
currentPanel = <Panel1 />
// Continue as needed
}
return (
<div>
<CurrentPanel/>
<button onClick={() => setActivePanel (0)}> Panel 0 </button>
<button onClick={() => setActivePanel (1)}> Panel 1 </button>
// And so on
</div>
)
You can further refine this by extracting the switch statement into its own component that takes the activePanel
as a prop.
CodePudding user response:
@MLDC No i don't have another divs, i want to replace the buttons with the crossponding component. For example: onclick on Add, then Add component will appears instead of the buttons.
In that case, create a boolean state for every Panel that you have (I created 3 so that you could open the panels simultaneously),
const [isAddPanelOpen, setIsAddPanelOpen] = useState(false);
const [isEditPanelOpen, setIsEditPanelOpen] = useState(false);
const [isDeletePanelOpen, setIsDeletePanelOpen] = useState(false);
Next, create an onclick function for every button
const openPanelHandler = (handler) => {
handler();
}
Then, apply this to every button
<Button onClick={setIsAddPanelOpen(prevState=>!prevState)}>Add Notification</Button>
<Button onClick={setIsEditPanelOpen(prevState=>!prevState)}>Edit Notification</Button>
<Button onClick={setIsDeletePanelOpen(prevState=>!prevState)}>Delete Notification</Button>
Lastly, Refactor your html to
<div className="form-group">
{isAddPanelOpen ? <AddNotification/> : <Button type="submit">Add Notification</Button>}
</div>
<div className="form-group">
{isEditPanelOpen ? <EditNotification/> : <Button type="submit">Edit Notification</Button>}
</div>
<div className="form-group">
{isDeletePanelOpen ? <DeleteNotification/> :<Button type="submit">Delete Notification</Button>}
</div>