javascript - 关于一段 for 循环代码执行顺序的问题

查看:101
本文介绍了javascript - 关于一段 for 循环代码执行顺序的问题的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

问 题

在微信小程序里边实现点击 canvas 将其转换为图片再预览的功能,由于涉及异步方法在for循环里调用,参考网上建议,在for循环内部使用了一个立即执行函数,多次测试发现,有时候控制台会先打印出"loop index is 1", 再打印出"loop index is 0",(为方便起见,model长度为2),导致这样一种情况:你点击第一张canvas,结果预览的却是第二张,百思不得其解,望大神赐教。

<canvas wx:for="{{ model }}" bindtap="previewImg" canvas-id="{{ 'mycanvas' + index }}" data-index="{{ index }}"/>

 // 点击图片进行预览
  previewImg: function (e) {
    var tempFilePathList = [];
    var index = e.target.dataset.index;
    var self = this;
    var loopedModel = self.data.model;
    for (var i = 0; i < loopedModel.length; i++) {
      (function (a) {
        wx.canvasToTempFilePath({
          canvasId: 'mycanvas' + a,
          success: function (res) {
            console.log('loop index is ' + a);
            tempFilePathList.push(res.tempFilePath);
            if (a == loopedModel.length - 1) { // 循环到最后一个了
              console.log('current image is ' + tempFilePathList[index]);
              wx.previewImage({
                current: tempFilePathList[index], // 当前显示图片的http链接
                urls: tempFilePathList // 需要预览的图片http链接列表
              })
            }
          },
          fail: function (res) {
            console.log(res);
          }
        });
      }(i))
    }
  },

解决方案

首先申明,我不了解小程序,所以我以是纯 JS 前端程序的角度来分析,若有不对之处,请谅解并指正

按一般的逻辑,预览哪张图就加载哪张图,为什么会为了预览一张图循环加载一组图?

如果是按现在这个做法,我猜是在预览的时候可以左/右滑来显示其它邻近的预览图。

同时加载有两种常用的现成方法可以实现,一个是使用 ES6 的 Promise.all,另一种是用 jQuery 的$.when(),似乎这两种都不是微信小程序推荐的,我不清楚小程序里有没有类似的 API,所以只能以 Promise.all 来描述下过程:把每一个加载过程封装成 Promise,再通过 Promise.all() 来实现异步加载并等待全部完成,

const index = ....;

function load(a) {
    return new Promise((resolve, reject) => {
        wx.canvasToTempFilePath({
            canvasId: "mycanvas" + a,
            success: function(res) {
                resolve(res.tempFilePath);
            },
            fail: function(res) {
                console.log(res);
                reject(res);
            }
        });
    });
}

const loadings = loopedModel.map((m, i) => load(i));
Promise.all(loadings)
    .then(results => {
        wx.previewImage({
            current: results[index],
            urls: results
        });
    });


补充一下

刚才顺手上网查了一下,发现微信小程序不支持 Promise,不过可以通过第三方库来支持

这篇关于javascript - 关于一段 for 循环代码执行顺序的问题的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆