I'm trying to learn React Js and I've managed to get stuck on an issue that drives me insane. It's pretty specific so sorry for the long question. I'll try to explain it and then share the code.
- I have a component that contains a table with employees.
- On every row there is an edit button that triggers the rendering of a component that only has a React Bootstrap Modal.
- I'm sending all the employee's row data to the child component through props.
- The default values of all modal's fields are from the props.
Now, there are 2 scenarios:
- I got only one row in the table, I'll press the edit button and all data from the row is loaded in the modal, even the image is being set fine. When I try to change the image everything is fine, the photo instantly updates.
- I got more than one row in the table, I'll press the edit button from any of the rows and once again, the modal is loaded fine. The issue appears when I try to change the image from the modal... nothing happens. BUT there is a really awkward behaviour that I hardly noticed, when I close the modal, just for a frame, the image changes.
I have really hard time trying to figure out why would more rows in the table affect the image updating in the Modal. Or delaying it...
Now, I'll try to share the relevant bits of code and how I update the image and some other code from the component that holds the Modal. I'm sorry for the horrors that will follow.
constructor(props){
super(props);
this.handleSubmit=this.handleSubmit.bind(this);
this.handleFileSelected=this.handleFileSelected.bind(this);
}
photofilename = "anonymous.png";
imagesrc = process.env.REACT_APP_PHOTOPATH this.photofilename;
handleFileSelected(event){
event.preventDefault();
this.photofilename=event.target.files[0].name;
const formData = new FormData();
formData.append(
"myFile",
event.target.files[0],
event.target.files[0].name
);
fetch(process.env.REACT_APP_API 'Employee/SaveFile',{
method:'POST',
body:formData
})
.then(res=>res.json())
.then((result)=>{
this.imagesrc=process.env.REACT_APP_PHOTOPATH result;
document.getElementById("img").src = this.imagesrc;
},
(error)=>{
alert('Failed');
})
}
....
render() {
return (
<div className="container"
<Modal
.....
<Image width="220px" height="220px"
src={process.env.REACT_APP_PHOTOPATH this.props.photofilename} id="img"/>
<input onChange={this.handleFileSelected} type="File"/>
When the modal loads I first set the src for the image to be the photofilename sent from the table's row, everything is fine. When selecting another image I'll try to force the new src on the image. Again, when there is only one row in the table it works perfectly, but when there are more rows the image is not updating. I really can't correlate those things.
If needed I can share the github link to the repository.
If anyone can point out my dumb mistake or had a similar issue and share their experience I would highly appreciate it. Thanks and have a great day!
CodePudding user response:
Unfortunately, this is a bit difficult to debug just from your code above, but here are some suggestions. Can you try setting the image source (imagesrc
) as a state with useState / useEffect
instead of just changing the image source as a global variable. In case of class component just check: https://reactjs.org/docs/state-and-lifecycle.html
Maybe also check whats the result
of the response you are getting and if it does contain the correct value for the image url. You are doing a res.json()
which returns a json object/value I guess. Is it the correct url
for the image you are trying to set (maybe should be result.url
or so)? Please see below:
this.imagesrc=process.env.REACT_APP_PHOTOPATH result;
And I am not sure if you use this imagesrc elsewhere in your code, or only to change the image source in document.getElementById("img").src = this.imagesrc;
this.imagesrc = process.env.REACT_APP_PHOTOPATH result;
<Image width="220px" height="220px" src={process.env.REACT_APP_PHOTOPATH this.props.photofilename} id="img"/>
Try changing the src
of this image above to imagesrc
directly. So when you update the imagesrc
state it should also change the source directly.