简体   繁体   English

JavaScript-未捕获的TypeError:类型错误

[英]JavaScript - Uncaught TypeError: Type error

I am trying to break a spritesheet and well, it's not putting it into a 2D array like it should. 我正在尝试破坏一个Spritesheet,但是,它并没有像应该的那样将其放入2D数组中。 At the end of my code, near the console.log, it spits out ImageData...but when it tries to putImageData... I get Uncaught TypeError: Type error 在我的代码结尾处,在console.log附近,它吐出了ImageData ...但是当它尝试放置putImageData ...时,我得到了Uncaught TypeError: Type error

Help? 救命?

and here's my code: 这是我的代码:

$(document).ready(function () {
    console.log("Client setup...");
    canvas = document.getElementById("canvas");
    context = canvas.getContext("2d");
    canvas.tabIndex = 0;
    canvas.focus();
    console.log("Client focused.");

    var imageObj = new Image();
    imageObj.src = "./images/all_tiles.png";
    imageObj.onload = function() {
    context.drawImage(imageObj, imageWidth, imageHeight);
    };

    var allLoaded = 0;
    var tilesX = ImageWidth / tileWidth;
    var tilesY = ImageHeight / tileHeight;
    var totalTiles = tilesX * tilesY;        
    var tileData = [totalTiles]; // Array with reserved size
    for(var i=0; i<tilesY; i++)
    {
      for(var j=0; j<tilesX; j++)
      {           
        // Store the image data of each tile in the array.
        tileData.push(context.getImageData(j*tileWidth, i*tileHeight, tileWidth, tileHeight));
        allLoaded++;
      }
    }

    if (allLoaded == totalTiles) {
    console.log("All done: " + allLoaded);
    console.log(tileData[1]);
    context.putImageData(tileData[0], 0 ,0); // Sample paint
    }


});

error happens at context.putImageData(tileData[0], 0 ,0); // Sample paint 错误发生在context.putImageData(tileData[0], 0 ,0); // Sample paint context.putImageData(tileData[0], 0 ,0); // Sample paint

Here is example fiddle of code above http://jsfiddle.net/47XUA/ 这是http://jsfiddle.net/47XUA/上方的代码示例

Your problem is that the first element of tileData is not an ImageData object, it's a plain number ! 您的问题是tileData的第一个元素不是ImageData对象, 而是一个纯数字 When you initialized your array you used: 初始化数组时,您使用了:

var tileData = [totalTiles];

This means that tileData[0] is equal to the value of totalTiles , which is the number 483 . 这意味着tileData[0]等于totalTiles的值,即数字483 You are providing a number instead of an ImageData object to putImageData , and the browser is throwing an error in confusion. 您向putImageData提供了一个数字而不是ImageData对象,浏览器在混乱中抛出错误。 If you look at any other element in the rest of your array, you'll see it is successfully being populated with ImageData objects as you expect; 如果您查看数组其余部分中的任何其他元素,就会发现它已成功按预期填充ImageData对象; only the first element in the array is a number. 只有数组中的第一个元素是数字。

You probably meant to do: 你可能打算这样做:

var tileData = new Array(totalTiles);

which would create an array with the specified length property, instead of setting the first value in the array to a number. 这将创建具有指定的length属性的数组,而不是将数组中的第一个值设置为数字。 Personally, I would run some performance tests to see if that is even useful; 就个人而言,我将进行一些性能测试,以查看它是否仍然有用。 you may be just as well using var tileData = []; 使用var tileData = [];也可能会很好

A type error is caused when a variable or object passed into a statement is not of a type that is expected for that command and can't be converted into something that is valid. 当传递到语句中的变量或对象的类型不是该命令所期望的类型,并且无法将其转换为有效值时,将导致类型错误。

See here for a full definition of the error. 有关错误的完整定义,请参见此处

So most likely that context or tileData is in an incorrect format or is null or undefined 因此,很可能上下文或tileData的格式不正确,或者为null或未定义

It might be a racing condition . 这可能是赛车状况 You are using drawImage only when the image ./images/all_tiles.png has been loaded. 仅在加载图像./images/all_tiles.png时才使用drawImage。 But you are using the image data on the context before the onload fired. 但是在触发onload 之前 ,您正在上下文中使用图像数据。 Try to move everything which is after the onload handler into the onload handler. 尝试将onload处理程序之后的所有内容移动到onload处理程序中。

The problem here is that the imageObj.onload() function is being called AFTER the rest of the script is executed. 这里的问题是在执行脚本的其余部分之后,会调用imageObj.onload()函数。

This means that queries to getImageData() are returning undefined, as there is no image data in the canvas when called. 这意味着对getImageData()查询返回的是未定义的,因为调用时画布中没有图像数据。

A simple way to fix this is to encapuslate the remaining script in the imageObj.onload function, like so: 解决此问题的一种简单方法是将其余脚本imageObj.onloadimageObj.onload函数中,如下所示:

$(document).ready(function () {
console.log("Client setup...");
canvas = document.getElementById("canvas");
context = canvas.getContext("2d");
canvas.tabIndex = 0;
canvas.focus();
console.log("Client focused.");

var imageObj = new Image();
imageObj.src = "./images/all_tiles.png";

imageObj.onload = function() {

  context.drawImage(imageObj, 0, 0);

  var allLoaded = 0;
  var tilesX = imageWidth / tileWidth;
  var tilesY = imageHeight / tileHeight;
  var totalTiles = tilesX * tilesY;        
  var tileData = new Array(); // Array with NO reserved size
  for(var i=0; i<tilesY; i++)
  {
    for(var j=0; j<tilesX; j++)
    {           
      // Store the image data of each tile in the array.
      tileData.push(context.getImageData(j*tileWidth, i*tileHeight, tileWidth, tileHeight));
      allLoaded++;
    }
  }

  context.putImageData(tileData[0], 0 ,0); // Sample paint
}; // End 'imageObj.onload()' scope.

}); // End document ready function scope.

This ensures that any calls to getImageData() are made after context.drawImage() 这样可以确保在context.drawImage()之后进行对getImageData()任何调用。

You may also have a problem here that you are not drawing the image to cover the canvas. 您在这里可能还存在一个问题,即您没有绘制图像以覆盖画布。 Change the line: 换行:

context.drawImage(imageObj, imageWidth, imageHeight);

to

context.drawImage(imageObj, 0, 0);

EDIT: You also had ImageWidth and imageWidth (same for height). 编辑:您还具有ImageWidthimageWidth (高度相同)。 Rename these. 重命名这些。

EDIT: Reserving the Array size here with new Array(totalTiles) was causing an issue. 编辑:在这里使用new Array(totalTiles)保留数组大小会导致问题。 When we pushed new tile images to the array, it pushed to the end of the pre-allocated array (starting at tileData[totalTiles] ). 当我们将新的图块图像推送到数组时,它推送到预分配数组的末尾(从tileData[totalTiles] )。 This is easily fixed by removing the size argument. 通过删除size参数可以轻松解决此问题。 Otherwise instead of using push() we could copy the image data into the array in a loop, eg: tileData[n] = getImageData(...) , starting at tileData[0] . 否则,除了使用push()我们还可以循环将图像数据复制到数组中,例如: tileData[n] = getImageData(...) ,从tileData[0]

I'm using Chrome. 我正在使用Chrome。

context.drawImage(spritesheet.image, 0, 0, 4608, 768);// Works
context.drawImage(spritesheet.image, 768, 0, 768, 768, 4608, 768); // Doesn't work: Uncaught TypeError: Type error

Thank you! 谢谢!

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

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