简体   繁体   English

我需要帮助让 JS 事件循环等待函数执行

[英]I need help in making the JS event loop wait for a functions execution

I am working on a project in which I use fabric.js我正在做一个使用fabric.js的项目

  • I take image address from database.我从数据库中获取图像地址。
  • Replace a placeholder image on the canvas.替换画布上的占位符图像。
  • And then save the canvas as a PNG with ajax.然后将画布保存为带有 ajax 的 PNG。

When I run this code and console log index at different points I saw that the main loop runs through and after that Image replacement part logs index and even later ajax is done.当我在不同的点运行此代码和控制台日志索引时,我看到主循环贯穿整个图像替换部分日志索引,甚至后来的 ajax 完成。

pseudocode伪代码

    for loop
    {
        console.log("start");

        // To go through the image addresses array retrieved from database

        for loop
        {
            console.log("Inside Second loop");

            // To Go through placeholder images or layer of images 
            // There can be multiple images on canvas to replace
            
            // replace Image happens here

            console.log("BeforeImageChange");
            imgToChange.setSrc(imgAddressFromDB){
                console.log("AfterImageChange");
            }
        }
        
        function saveCanvas(){
            //function to save canvas as a Image done through ajax to php
            console.log("AfterSaving");
        }

        saveCanvas();
        console.log("End");
    }

console.log output is like console.log 输出就像

    "start"
    "Inside Second loop"
    "BeforeImageChange"
    "End"
    "AfterImageChange"
    "AfterSaving"

How can I make it so AfterImageChange happens right after BeforeImageChange and Saving happens before loop end?我怎样才能使它在 AfterImageChange 之后发生 AfterImageChange 并且在循环结束之前进行保存?

I am new to javascript, I tried learning about asynchronous methods but they aren't making sense to me that if they are useful in my case.我是 javascript 新手,我尝试学习异步方法,但如果它们对我有用的话,它们对我来说没有意义。 If you need more information comment below.如果您需要更多信息,请在下面评论。 Thanks谢谢

尝试在setSrc方法中调用saveCanvas() ,这样在调用 AfterSaving 控制台后会调用 saveCanvas。

You need to re-arrange your code.您需要重新安排您的代码。 You already know the answer because you know how the code behave but perhaps you're not familiar with the techniques.您已经知道答案,因为您知道代码的行为方式,但也许您不熟悉这些技术。 Firstly you need to do this:首先你需要这样做:

for loop
{
    console.log("start");

    // To go through the image address retrieved from database

    for loop
    {
        console.log("Inside Second loop");

        // To Go through placeholder images or layer of images
        // replace Image happens here

        console.log("BeforeImageChange");
        imgToChange.setSrc(imgAddressFromDB){
            console.log("AfterImageChange");

            // You already know that code inside here
            // gets executed last
    
            function saveCanvas(){
                //function to save canvas as a Image done through ajax to php
                console.log("AfterSaving");
            }

            saveCanvas();
            console.log("End");
        }
    }
}

But I presume you don't want to saveCanvas() on each iteration of the loop.但是我认为您不想在循环的每次迭代中都saveCanvas() Therefore you need to execute it only on the completion of the last setSrc() :因此,您只需要在最后一个setSrc()完成时执行它:

for loop
{
    console.log("start");

    // To go through the image address retrieved from database

    let setSrcCount = figureOutHowManyTimesTheForLoopBelowLoops();

    for loop
    {
        console.log("Inside Second loop");

        console.log("BeforeImageChange");
        imgToChange.setSrc(imgAddressFromDB){
            console.log("AfterImageChange");

            setSrcCount --;

            if (setSrcCount === 0) {
                function saveCanvas(){
                    //function to save canvas as a Image done through ajax to php
                    console.log("AfterSaving");
                }

                saveCanvas();
                console.log("End");
            }
        }
    }
}

The code can be made more readable if you use Promises :如果你使用Promises可以使代码更具可读性:

function setSrc(imgAddress) {
    return new Promise((ok,err) => {
        imgToChange.setSrc(imgAddress,function () {
            ok();
        });
    });
}

async function functionContainingLoops() {

  for loop
  {
    console.log("start");

    // To go through the image address retrieved from database

    for loop
    {
        console.log("Inside Second loop");

        // To Go through placeholder images or layer of images
        // replace Image happens here

        console.log("BeforeImageChange");

        await setSrc(imgAddressFromDB);

        console.log("AfterImageChange");
    }

    function saveCanvas(){
        //function to save canvas as a Image done through ajax to php
        console.log("AfterSaving");
    }

    saveCanvas();
    console.log("End");
  }
}

ContainingLoops()

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM