为什么画布上的多个图片无法加载到Google Chrome中?

时间:2014-02-08 20:23:46

标签: javascript google-chrome html5-canvas

我无法弄清楚我应该如何处理这个严格的WebKit。 所以我在画布中加载了多个图像,但问题出现在谷歌的Chrome浏览器中是因为基于我的研究严格的WebKit而无法加载,并且使其工作的唯一方法是使用逻辑“< em>预加载“图像。你能给我一些关于我应该如何处理这个问题或aybe一些代码片段的想法吗?

我的代码中包含我在网上找到并实现的解决方案:

var vCanvas, vContext;
// Chap02 Backgrounds
//var officeBG;
// GUIs
var episode, logo, name, dialogue, nextBTN, backBTN, menuBTN, epiBTN, audioBTN, quitBTN;

// Solution 1 = Not Working
/*var episode = new Image();
var logo = new Image();
var name = new Image();
var dialogue = new Image();
var nextBTN = new Image();
var backBTN = new Image();
var menuBTN = new Image();
var epiBTN = new Image();
var audioBTN = new Image();
var quitBTN = new Image();*/

// Solution 2 = Not Working
/*var test = new Array();
test[0] = new Image();
test[0].src = './gameGUI/Episode.png';
test[1] = new Image();
test[1].src = './gameGUI/Logo.png';
test[2] = new Image();
test[2].src = './gameGUI/Name.png';
test[3] = new Image();
test[3].src = './gameGUI/Dialogue.png';
test[4] = new Image();
test[4].src = './gameGUI/NextBtn.png';
test[5] = new Image();
test[5].src = './gameGUI/BackBtn.png';
test[6] = new Image();
test[6].src = './gameGUI/MenuBtn.png';
test[7] = new Image();
test[7].src = './gameGUI/EpisodesBtn.png';
test[8] = new Image();
test[8].src = './gameGUI/AudioBtn.png';
test[9] = new Image();
test[9].src = './gameGUI/QuitBtn.png';*/


// First Function to load all the magic stuff
function load() {
    vCanvas = document.getElementById("canvas");
    vContext = vCanvas.getContext("2d");
    officeBG = document.getElementById("officeBG");
    vContext.drawImage(officeBG, 0, 0);

    InGameGUI();
}

// Function to clear the canvas
function clearCanvas() {
    vContext.clearRect(0, 0, 800, 480);
}

function InGameGUI() {
    // Default that shows up properly on Firefox
    episode = document.getElementById("episode");
    logo = document.getElementById("logo");
    name = document.getElementById("name");
    dialogue = document.getElementById("dialogue");
    nextBTN = document.getElementById("nextBTN");
    backBTN = document.getElementById("backBTN");
    menuBTN = document.getElementById("menuBTN");
    epiBTN = document.getElementById("epiBTN");
    audioBTN = document.getElementById("audioBTN");
    quitBTN = document.getElementById("quitBTN");

    vContext.drawImage(episode, 0, 0, 216, 39, 15, 13, 216, 39);
    vContext.drawImage(logo, 0, 0, 143, 86, 647, 10, 143, 86);
    vContext.drawImage(name, 0, 0, 484, 33, 0, 293, 484, 33);
    vContext.drawImage(dialogue, 0, 0, 800, 154, 0, 326, 800, 154);
    vContext.drawImage(nextBTN, 0, 0, 83, 39, 685, 355, 83, 39);
    vContext.drawImage(backBTN, 0, 0, 56, 27, 697, 403, 56, 27);
    vContext.drawImage(menuBTN, 0, 0, 54, 27, 473, 452, 54, 27);
    vContext.drawImage(epiBTN, 0, 0, 77, 25, 540, 452, 77, 25);
    vContext.drawImage(audioBTN, 0, 0, 54, 27, 636, 452, 54, 27);
    vContext.drawImage(quitBTN, 0, 0, 54, 27, 733, 452, 54, 27);

    // Solution 1
    /*episode.onload = vContext.drawImage(episode, 0, 0, 216, 39, 15, 13, 216, 39);
    logo.onload = vContext.drawImage(logo, 0, 0, 143, 86, 647, 10, 143, 86);
    name.onload = vContext.drawImage(name, 0, 0, 484, 33, 0, 293, 484, 33);
    dialogue.onload = vContext.drawImage(dialogue, 0, 0, 800, 154, 0, 326, 800, 154);
    nextBTN.onload = vContext.drawImage(nextBTN, 0, 0, 83, 39, 685, 355, 83, 39);
    backBTN.onload = vContext.drawImage(backBTN, 0, 0, 56, 27, 697, 403, 56, 27);
    menuBTN.onload = vContext.drawImage(menuBTN, 0, 0, 54, 27, 473, 452, 54, 27);
    epiBTN.onload = vContext.drawImage(epiBTN, 0, 0, 77, 25, 540, 452, 77, 25);
    audioBTN.onload = vContext.drawImage(audioBTN, 0, 0, 54, 27, 636, 452, 54, 27);
    quitBTN.onload = vContext.drawImage(quitBTN, 0, 0, 54, 27, 733, 452, 54, 27);*/

    // Solution 2
    /*test[0].onload = function(){ vContext.drawImage(episode, 0, 0, 216, 39, 15, 13, 216, 39); };
    test[1].onload = function(){ vContext.drawImage(logo, 0, 0, 143, 86, 647, 10, 143, 86); };*/
}

// Solution 3 = Not Working
/*function loadImages(sources, callback) {
  var images = {};
  var loadedImages = 0;
  var numImages = 0;
  // get num of sources
  for(var src in sources) {
    numImages++;
  }
  for(var src in sources) {
    images[src] = new Image();
    images[src].onload = function() {
      if(++loadedImages >= numImages) {
        callback(images);
      }
    };
    images[src].src = sources[src];
  }
}
var vCanvas = document.getElementById('canvas');
var vContext = vCanvas.getContext('2d');

var sources = {
        episode: './gameGUI/Episode.png',
        logo: './gameGUI/Logo.png',
        name: './gameGUI/Name.png',
        dialogue: './gameGUI/Dialogue.png',
        nextBTN: './gameGUI/NextBtn.png',
        backBTN: './gameGUI/BackBtn.png',
        menuBTN: './gameGUI/MenuBtn.png',
        epiBTN: './gameGUI/EpisodesBtn.png',
        audioBTN: './gameGUI/AudiBtn.png',
        quitBTN: './gameGUI/QuitBtn.png'
};

loadImages(sources, function(images) {
    vContext.drawImage(images.logo, 0, 0, 143, 86, 647, 10, 143, 86);
    vContext.drawImage(images.name, 0, 0, 484, 33, 0, 293, 484, 33);
    vContext.drawImage(images.dialogue, 0, 0, 800, 154, 0, 326, 800, 154);
    vContext.drawImage(images.nextBTN, 0, 0, 83, 39, 685, 355, 83, 39);
    vContext.drawImage(images.backBTN, 0, 0, 56, 27, 697, 403, 56, 27);
    vContext.drawImage(images.menuBTN, 0, 0, 54, 27, 473, 452, 54, 27);
    vContext.drawImage(images.epiBTN, 0, 0, 77, 25, 540, 452, 77, 25);
    vContext.drawImage(images.audioBTN, 0, 0, 54, 27, 636, 452, 54, 27);
    vContext.drawImage(images.quitBTN, 0, 0, 54, 27, 733, 452, 54, 27);
});*/

addEventListener("load", load, false);

有没有办法可以在没有JQuery的情况下使用javascript来解决这个问题,或者我真的需要使用JQuery来预加载图像。

2 个答案:

答案 0 :(得分:1)

以下是您可以使用的仅限javascript的图片加载程序。

加载所有图像后,将调用start()函数。

你可以在start()

中开始drawImage等
// image loader

var imageURLs=[]; 
var imagesOK=0;
var imgs=[];

// put the paths to your images here
imageURLs.push("./gameGUI/Episode.png");
imageURLs.push("./gameGUI/Logo.png");
// ... same with all your other images

loadAllImages(start);

function loadAllImages(callback){
    for (var i=0; i<imageURLs.length; i++) {
        var img = new Image();
        imgs.push(img);
        img.onload = function(){ 
            imagesOK++; 
            if (imagesOK>=imageURLs.length ) {
                callback();
            }
        };
        img.onerror=function(){alert("image load failed");} 
        img.crossOrigin="anonymous";
        img.src = imageURLs[i];
    }      
}

var episode,logo; //以及所有其他图像对象的var

function start(){

    // At this point...
    // the imgs[] array holds fully loaded images
    // the imgs[] are in the same order as imageURLs[]

    // drawImage the episode
    vContext.drawImage(imgs[0], 0, 0, 216, 39, 15, 13, 216, 39);

    // drawImage the logo
    vContext.drawImage(imgs[1], 0, 0, 143, 86, 647, 10, 143, 86);


}

答案 1 :(得分:0)

我的方法:

// flag showing whether a loop through the image list is finished, 
//needed because loading will be finished in a time after looping 
var _loop_finished = false;

/* number of loaded images */
var _loadedNum = 0;
var _images = {};

function Load(list, callback) {
  var createdNum = 0;
  for ( var i in list ) {
      _createdNum++;
  }

  for ( var key in list ) {
      if ( list.hasOwnProperty(key) ) {
          var image = new Image();
          image.key = key;
          image.src = list[key];

          _images[key] = image;

          image.onload = function () {
              _loadedNum++;

              console.log("Cached image '" + this.key + "'");

              if ( _loop_finished == true && createdNum == _loadedNum ) {
                  if ( callback != null ) {
                      callback();
                  }
              }
          };
      }
  }

  _loop_finished = true;
  return this;
};
 Load({a: './images/a.png', b: './images/b.png'}, function() {

    //will be executed after images are loaded
    // console.log(_images.a);
    //
});