ImgCache - 如何正确等待异步完成嵌套for循环

时间:2015-06-05 22:49:57

标签: android angularjs cordova

我正在构建适用于Android的Cordova应用。我必须解析一个由帖子组成的JSON。每个帖子都有文本(标题,描述,类别等)和图像(图像数组 - 可以是一个或多个)。我的目标是存储JSON数据以供离线使用(保存到SQLlite数据库)。现在,下面的示例代码可以工作,但序列不是我期望的那样:

  1. 请求JSON(ok)
  2. 等待所有承诺(ok)
  3. 解析JSON(在下载所有图像之前完成)
  4. 将信息存储到数据库,但图像仍在下载(在后台线程中 - 对用户界面无害)。
  5. 我想要的是在下载所有图像后存储到数据库。我'我试过很多东西,比如用递归函数替换第二个for循环(以处理所述here的async函数)和许多其他类似的方法,但我相信问题从第一个for循环开始,它没有&# 39;等待checkCache完成。你怎么看?我怎样才能克服这个问题?如果您需要任何进一步的解释,请问我。

    我的设置是: Cordova 4.0.0Angular 1.3.1ImgCache 1.0

    我的方法是:

    第一。请求JSON:

    promise1 = $http({method: 'GET', url: baseURL + options1};
    promise2 = $http({method: 'GET', url: baseURL + options2};
    //...
    

    第二。等待所有承诺

    return $q.all([promise1,promise2,...]).then(function(data){
       var promise1size = data[0].data.posts_number;//posts.length;
       parseJSON(data[0],promise1size,'category1');
       var promise2size = data[1].data.posts_number;//posts.length;
       parseJSON(data[1],promise1size,'category2');
    
      //similar for the rest promises
    });
    

    第三。解析JSON

    function parseJSON(respdata,size,category){            
            console.log("Parsing "+size+" "+category);
            for(i=0;i<size;i++){
                var item = {};
                item ["id"] = respdata.data.object[i].id;
                item ["title"] = respdata.data.object[i].title;
                item ["description"] = respdata.data.object[i].description;
    
                var jsarray = respdata.data.object[i].categories;
                item ["category"] = jsarray[0].title;
                item ["catid"] = jsarray[0].id; 
    
                //Other JSON keys here similar as above
    
                //Here it starts...                
                var jsattachement = respdata.data.object[i].attachments;
                var atsize = jsattachement.length;
                if(atsize>0){   
                    var images=[];
                    for(j=0;j<atsize;j++){
                        (function(j){checkCache(jsattachement[j].url)}(j));//here is the problem
                        multimedia.push({title:item["title"], src:ImgCache.returnCachedURL(jsattachement[j].url), w:400,h:300});               
                        images.push({title:item["title"],src:ImgCache.returnCachedURL(jsattachement[j].url),w:400,h:300});
                    }
                    item ["attachement"] = images;
                }else
                    item ["attachement"] = [];
    
                if(category=='category1')
                    response.category1.push(item);
                else if(category=='category2')
                    response.category2.push(item);
                //else if...
                //else if...
            }
        }
    };
    

    checkCache功能:

    function checkCache (imgsrc){
        ImgCache.isCached(imgsrc, function(src, success) {
            if(!success){
                ImgCache.cacheFile(src, function(){});
            }
        });
    };
    

    第四。存储到数据库

    这里我将解析后的信息保存到数据库中。在步骤3中,我对图像使用了returnCachedURL函数(这不是异步的),因此即使图像的本地路径可能尚未下载(但最终也会),也可以使图像的本地路径就绪。

1 个答案:

答案 0 :(得分:0)

我这样做了:

与您类似,但使用update sql存储每个下载图像的图像。然后,我发现我的一些用户想要和我一起玩,他们在图像下载过程中断开了互联网连接!所以我在sql中有不完整的记录!耶稣!

然后我改为:我创建一个临时的全局变量。例如tempvar = {},然后:tempvar.data1 =&#39; hello&#39;,tempvar.preparedatacompleted = true,tempvar.ImagesToBeDownload = 5,tempvar.ImagesDownloaded = 0,tempvar.imagearray = ......

然后,每次下载图像时,如果没有,则将数字加1。 =总数,调用将此tempvar中的所有数据和图像保存到sql的函数。