Reputation: 11
Just trying to understand the flow of a promise. Have only been learning js for a few weeks, so any help is greatly appreciated. Trying to display a random image from an API with the measurements from the input in the form. However the width and height don't adjust. Im assuming it is because I don't understand the flow of the promise. Thanks!
let width = 600
let height = 300
function imgSize() {
width = parseInt(document.getElementById('width').value)
height = parseInt(document.getElementById('height').value)
loadElement()
}
function loadElement() {
return new Promise((resolve) => {
const element = new Image()
element.src = `https://picsum.photos/${width}/${height}`
element.onload = () => {
resolve(element)
}
})
}
loadElement().then((element) => {
document.getElementById('img-container').innerHTML = `<img src=${element.src}/>`
})
body {
text-align: center;
}
<form id='form' action='VanZalk_ES6_Promises.html'>
<label for='width'>Enter width of property:</label><br>
<input type='number' id='width' name="width"><br><br>
<label for='height'>Enter height of property:</label><br>
<input type="number" id='height' name="height"><br><br>
<label for='grey'>Greyscale</label>
<input type="checkbox" id="grey" name="grey"><br><br>
<button onclick='imgSize()' id='btn'>Show photo</button><br><br>
<div id='img-container'>
</div>
</form>
Update thanks, I think the main problem was retrieving the image. The image is displayed fine on loading the page. However when I submit values for changing the size and hit the button, it goes back to it's previous size. I tried it without using a promise. I tried it using just some text instead of an image. callImg runs fine the first time, but when call it again and it reaches the line of code to change the img.src it jumps the rest of the code. This is what it looks like now:
let width
let height
let img = new Image()
let node = document.getElementById('img-container')
function callImg() {
if (width === undefined) {
width = 200
height = 200
} else {
width = parseInt(document.getElementById('width').value)
height = parseInt(document.getElementById('height').value)
}
img.src = `https://picsum.photos/${width}/${height}`
node.appendChild(img)
}
// just to try to change the width after clicking the button
function imgSize() {
width = 800
callImg()
}
//calling function on loading the page, so that there will be an image to //start with
callImg()
Upvotes: 0
Views: 1090
Reputation: 136114
There is no need for the Promise
here*. Also the service you're using supports just putting the width/height into the src
directly so just use that in the appended img
tag.
function imgSize() {
width = parseInt(document.getElementById('width').value)
height = parseInt(document.getElementById('height').value)
document.getElementById('img-container').innerHTML = `<img src="https://picsum.photos/${width}/${height}">`;
}
<label for='width'>Enter width of property:</label><br>
<input type='number' id='width' name="width"><br><br>
<label for='height'>Enter height of property:</label><br>
<input type="number" id='height' name="height"><br><br>
<label for='grey'>Greyscale</label>
<input type="checkbox" id="grey" name="grey"><br><br>
<button onclick='imgSize()' id='btn'>Show photo</button><br><br>
<div id='img-container'>
</div>
* Not strictly true, the advantage of the code you wrote originally was that by setting the src
of an Image
instance you're really preloading the image in the background. When then setting the src of the image element, the image is already loaded. You could indeed do this with a promise:
function imgSize() {
width = parseInt(document.getElementById('width').value)
height = parseInt(document.getElementById('height').value)
loadElement().then(img => {
document.getElementById('img-container').innerHTML = `<img src="${img.src}">`;
})
}
function loadElement() {
return new Promise((resolve) => {
const element = new Image()
element.src = `https://picsum.photos/${width}/${height}`
element.onload = () => {
resolve(element)
}
})
}
<label for='width'>Enter width of property:</label><br>
<input type='number' id='width' name="width"><br><br>
<label for='height'>Enter height of property:</label><br>
<input type="number" id='height' name="height"><br><br>
<label for='grey'>Greyscale</label>
<input type="checkbox" id="grey" name="grey"><br><br>
<button onclick='imgSize()' id='btn'>Show photo</button><br><br>
<div id='img-container'>
</div>
Upvotes: 1