I'm pretty new to coding so I hope my question won't sound too ridiculous. I've spent days to figure something out but didn't find anything.
So I have a react page with the main component that is my "planning container".
In this component, I have a child component that represents a whole month. it's a table with a line for each people and my team, and a td
that represents each day of the month.
This child is stored in a variable array that is stored in the state.
When I click on a button, I create another child (for the next month), that I will push into the array stored in the state.
I have a variable called "refresh" that just setRefresh(!refresh)
. This variable is passed to the childs components and I put this variable in the useEffect [] that will trigger a re-render.
=> The problem is that it doesn't re-render at all.
So, just for you to know, I really need to be able to "append" a whole month at each click on the button. I really need this "view" to be able to work. I will paste some code to make you understand the main idea.
here is the parent :
import React, {useEffect, useState} from "react";
import PlanningMonthBuild from "./PlanningMonthBuild";
import './Planning.css';
import "react-datepicker/dist/react-datepicker.css";
const PlanningBuild = () => {
const [startForNextMonth, setStartForNextMonth] = useState(new Date());
const [inputList, setInputList] = useState([]);
const [refresh, setRefresh] = useState(false);
useEffect(() => {
initPlanning();
}, []);
const handleRefresh = () => {
setRefresh(!refresh);
}
const initPlanning = () => {
let date = new Date(startForNextMonth.getFullYear(), startForNextMonth.getMonth(), 1);
let newPlanning = [...inputList];
newPlanning.splice(0, 0,
<PlanningMonthBuild
key={'current' + new Date().toISOString()}
startDate={date}
refresh={refresh}
/>
);
let date2 = new Date(startForNextMonth.getFullYear(), startForNextMonth.getMonth() + 1, 1);
date2.setMonth(date.getMonth() + 1);
setStartForNextMonth(date2);
setInputList(newPlanning);
};
const addOneMonthNext = () => {
setInputList(inputList.concat(
<PlanningMonthBuild
key={new Date().toISOString()}
startDate={startForNextMonth}
refresh={refresh}
/>
));
let date = startForNextMonth;
date.setDate(1);
date.setMonth(date.getMonth() + 1);
setStartForNextMonth(date);
};
return (
<main>
<div className="refresh-div" onClick={handleRefresh}><i className="fa fa-refresh" aria-hidden="true"></i></div>
<button className="myButton" onClick={addOneMonthNext}>Add Next Month</button>
<div id="insideDiv">
{inputList}
</div>
</main>
);
};
export default PlanningBuild;
And here is the child (that build each month) :
import React, {useEffect, useState} from "react";
import useAxiosPrivate from "../hooks/useAxiosPrivate";
import {getFirstDayOfMonth} from "../utils/dates";
const PlanningMonthBuild = ({ startDate, refresh }) => {
const [dateDebut] = useState(startDate);
const [jsListe, setJsListe] = useState([]);
const axiosPrivate = useAxiosPrivate();
useEffect(() => {
let isMounted = true;
const controller = new AbortController();
try {
axiosPrivate.get('api/planning/team?start=' + getFirstDayOfMonth(dateDebut.getFullYear(), dateDebut.getMonth()), {
signal: controller.signal
}).then(response => {
if (isMounted) {
const newListeJS = response.data;
setJsListe(newListeJS);
}
});
} catch (err) {}
return () => {
isMounted = false;
controller.abort();
}
}, [refresh])
return (jsListe.map((day)=> {
///.... building a table(tr,td...)
}))
}
export default PlanningMonthBuild;
So, when I put my child component directly into the parent return, it works when I click on refresh button (if my workmate updates something for example...), it will update my table but if I store my child component in the array in "inputList" state it doesn't...
I hope you can understand what I mean.
Thanks in advance for any help.