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

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/11540041/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-10-26 13:35:53  来源:igfitidea点击:

JavaScript - Uncaught TypeError: Type error

javascriptjqueryhtml

提问by test

I am trying to break a spritesheet and well, it's not putting it into a 2D array like it should. 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

我试图打破一个 spritesheet,好吧,它并没有像它应该的那样将它放入一个 2D 数组中。在我的代码末尾,在 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

Here is example fiddle of code above http://jsfiddle.net/47XUA/

这是http://jsfiddle.net/47XUA/上面代码的示例小提琴

回答by apsillers

Your problem is that the first element of tileDatais not an ImageDataobject, it's a plain number! When you initialized your array you used:

你的问题是第一个元素tileData不是一个ImageData对象,它是一个普通的数字!当你初始化你的数组时,你使用了:

var tileData = [totalTiles];

This means that tileData[0]is equal to the value of totalTiles, which is the number 483. You are providing a number instead of an ImageDataobject to putImageData, and the browser is throwing an error in confusion. If you look at any other element in the rest of your array, you'll see it is successfully being populated with ImageDataobjects as you expect; only the first element in the array is a number.

这意味着tileData[0]等于 的值totalTiles,即数字483。您正在向 提供数字而不是ImageData对象putImageData,并且浏览器在混淆中抛出错误。如果您查看数组其余部分中的任何其他元素,您会发现它已ImageData按预期成功填充了对象;只有数组中的第一个元素是数字。

You probably meant to do:

你可能打算这样做:

var tileData = new Array(totalTiles);

which would create an array with the specified lengthproperty, instead of setting the first value in the array to a number. Personally, I would run some performance tests to see if that is even useful; you may be just as well using var tileData = [];

这将创建一个具有指定length属性的数组,而不是将数组中的第一个值设置为数字。就个人而言,我会运行一些性能测试,看看这是否有用;你也可以使用var tileData = [];

回答by Dave Tameside

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 herefor a full definition of the error.

有关错误的完整定义,请参见此处

So most likely that context or tileData is in an incorrect format or is null or undefined

所以很可能 context 或 tileData 的格式不正确,或者为 null 或未定义

回答by devnull69

It might be a racing condition. You are using drawImage only when the image ./images/all_tiles.pnghas been loaded. But you are using the image data on the context beforethe onload fired. Try to move everything which is after the onload handler into the onload handler.

这可能是一种赛车状况。仅在./images/all_tiles.png加载图像时才使用 drawImage 。但是您在 onload 触发之前在上下文中使用图像数据。尝试将 onload 处理程序之后的所有内容移动到 onload 处理程序中。

回答by Aesthete

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.onloadfunction, like so:

解决此问题的一个简单方法是将剩余的脚本封装在imageObj.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()

这可确保getImageData()在之后进行任何调用context.drawImage()

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 ImageWidthand imageWidth(same for height). Rename these.

编辑:你也有ImageWidthimageWidth(身高相同)。重命名这些。

EDIT: Reserving the Array size here with new Array(totalTiles)was causing an issue. When we pushed new tile images to the array, it pushed to the end of the pre-allocated array (starting at tileData[totalTiles]). This is easily fixed by removing the size argument. 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].

编辑:在此处保留数组大小new Array(totalTiles)导致了问题。当我们将新的切片图像推送到数组时,它推送到预分配数组的末尾(从 开始tileData[totalTiles])。这可以通过删除 size 参数轻松解决。否则,push()我们可以将图像数据复制到循环中的数组中,例如:tileData[n] = getImageData(...),从 开始,而不是使用tileData[0]

回答by Lorenzo De Tomasi

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!

谢谢!