I feel like there must be a simple, searchable answer to this, but try as I might, I am unable to find the solution to this simple problem. I am new to Promises and callbacks, so I am probably using the wrong search terms.
I have multiple DOM objects that have HTML loaded in via jquery's load function. The order the pieces are loaded in the page does not matter - however, I want to do some tasks only after ALL of them have completed loading.
Promise.all seemed like a great solution, something such as this:
// what I'd like to be able to do.
function init_page() {
var init_tasks = [];
init_tasks.push($("#divA").load("page1.html"));
init_tasks.push($("#divB").load("page2.html"));
init_tasks.push($("#divC").load("page3.html"));
await Promise.all(init_tasks);
// do stuff here
}
However, load() returns a callback function, not a Promise object, so this does not work.
I made a wrapper function (shown below), which wraps load's returned callback function in a Promise, so I can use the above approach. Unfortunately, with the way I've written it, the Promises never resolve. I figure I am probably doing something very obviously wrong, but I can not figure out what. (Do I need to be returning something other than the Promise? Do I need to define resolve and reject cases?)
// incorrect "Promise wrapper" attempt
function loadPromiseWrapper(dom_id, filename) {
return new Promise(function(resolve, reject) {
$(dom_id).load(filename);
// what am I missing here?
});
}
// revised init_page function that calls my incorrect "Promise wrapper"
function init_page() {
var init_tasks = [];
init_tasks.push(loadPromiseWrapper("divA", "page1.html"));
init_tasks.push(loadPromiseWrapper("divB", "page2.html"));
init_tasks.push(loadPromiseWrapper("divC", "page3.html"));
await Promise.all(init_tasks);
// never gets here because none of the Promises resolve
}
What am I missing? How do I properly wrap the returned callback of jquery's load function in to a Promise, so that I can use Promise.all and wait for all the individual pieces to complete?
CodePudding user response:
.load
can take more parameters and one of them is a complete
callback. That is where you should put the resolve
function loadPromiseWrapper(dom_id, filename) {
return new Promise(function(resolve, reject) {
$(dom_id).load(filename, resolve);
});
}