在javascript中加载用于在画布上绘图的图像

时间:2013-09-08 17:49:07

标签: javascript canvas drawimage

我一直在努力教我11岁的儿子用javascript编程,但我自己也是一名java程序员,我不太确定下面的工作。编写的代码在drawRocket方法中显示一个简单的块,但我的儿子希望它显示火箭的图像。但是,如果我在drawImage方法中发表评论并注释掉drawRect方法,那么它就不会显示火箭图像。

据我所知,通过在stackoverflow上阅读关于此主题的各种线程,问题是javascript不会同步加载图像,因此我需要在火箭图像对象上使用onload侦听器编写代码。但是,我尝试用此代码替换main()调用(并从main方法中删除两行):

var rocket = new Image();
rocket.onload = main(rocket);
rocket.src = "rocket.jpg";

它仍然无效。我尝试了其他各种各样的东西,但似乎没有什么对我有用。 rocket.jpg图片很好。

毫无疑问,答案非常简单,但我在2小时后仍在苦苦挣扎。有什么帮助吗?

谢谢!

下进行。

P.S。燃煤火箭是下一件大事;)

<head>
<script>

function drawSky(ctx) {
   ctx.fillStyle = "rgb(0,0,50)";
   ctx.fillRect(0, 0, 300, 300);
}

function drawGround(ctx) {
   ctx.fillStyle = "rgb(150,150,127)";
   ctx.fillRect(0, 295, 300, 5);
}

function drawRocket(ctx, rocket, height) {
   var drawHeight = 250 - height*2;
   if (drawHeight > 245)
      drawHeight = 245;

//   ctx.drawImage(rocket, 140, drawHeight, 20, 50);

   ctx.fillStyle = "rgb(255,0,0)";
   ctx.fillRect(140, drawHeight, 20, 50);
}

function drawExplosion(ctx, size) {
   ctx.fillStyle = "rgb(255,102,0)";
   ctx.beginPath();
   ctx.arc(150, 295, size, 180*Math.PI/180, 360*Math.PI/180);
   ctx.fill();
}

function drawCoalBar(ctx, coal) {

   ctx.fillStyle = "rgb(255,255,255)";
   ctx.fillText("COAL", 10, 25);   


   if (coal <= 15)
      ctx.fillStyle = "rgb(255,0,0)";  
   else if (coal <= 30)
      ctx.fillStyle = "rgb(255,125,0)";
   else
      ctx.fillStyle = "rgb(255,225,0)";


   ctx.fillRect(45, 15, coal*4, 10);   
   ctx.strokeStyle = "rgb(255,255,255)";
   ctx.strokeRect(45, 15, 60*4, 10);   

}

function main() {

var canvas = document.getElementById('gameview');
var ctx = canvas.getContext('2d');

var rocket = new Image();
rocket.src = "rocket.jpg";

drawSky(ctx);
drawGround(ctx);

var name = prompt("What is your name?");
document.write("<p>Good luck Captain " + name + "!</p>");

var height = 100;
var speed = 0;
var coal = 60;
var burn = 0;
var gravity = 5;
var maxSpeedForSafeLanding = 8;

document.write("<p>");
document.write("The maximum speed for a safe landing is " + maxSpeedForSafeLanding + "m/s.");
document.write("<p>");

while (height > 0)
{
   document.write("Burn: " + burn + "kg");
   document.write(" - Height: " + height + "m");
   document.write(" - Speed: " + speed + "m/s");
   document.write(" - Coal: " + coal + "kg");
   document.write("<br />"); 

   drawSky(ctx);
   drawGround(ctx);
   drawRocket(ctx, rocket, height);
   drawCoalBar(ctx, coal);   


   // Ask for ammount of coal to burn
   var burn = prompt("How much coal do you want to burn?");
   burn = Number(burn);

   if (burn > coal)
     burn = coal;

   if (-burn > coal)
     burn = -coal;


   if (burn >= 0)
     coal = coal - burn;
   else
     coal = coal + burn;

   speed = speed + gravity - burn;

   height = height - speed; 
}

document.write("</p>");

drawSky(ctx);
drawGround(ctx);


if (speed <= maxSpeedForSafeLanding) {
   drawRocket(ctx, 0);

   document.write("<p>Congratulations Captain " + name + ".  You landed safely with a speed of " + speed + "m/s and you still have " + coal + "kg of coal left.</p>");
} else {
   drawExplosion(ctx, 25+coal*2+speed*2);

   document.write("<p>Rest In Peace Captain " + name + ".  You crashed with a speed of " + speed + "m/s and you still had " + coal + "kg of coal left.You will be burried on the planet you crashed on.</p>");
}

drawCoalBar(ctx, coal);
}
</script>
</head>

<body>

<h1>Rocket Lander Game</h1>

<canvas id="gameview" width="300" height="300"></canvas>

<script>
main();
</script>

</body>

2 个答案:

答案 0 :(得分:0)

试试这个:

var rocket = new Image();
rocket.onload = function(){ main(rocket) };
rocket.src = "rocket.jpg";

答案 1 :(得分:0)

正在发生的是您正在调用函数main()main结果已被赋予onload

你可以简单地把它写成为{em>引用给main而不是::

rocket.onload = main;  //main will be invoked when image is loaded

rocket.onload = function(e) { main() };

在后者中,我们给出一个匿名函数作为参数,当调用它时main()被调用。如果您想在调用main()之前对图像执行其他操作,这将非常有用。

由于rocket在这种情况下是全局可用的,因此无需将其作为main的参数提供,但如果您需要使用其他图像调用main,这当然是好的这样做的方式。但是你可以在main中添加一个参数变量:

function main(image) {

    /// ctx.drawImage(image, 0, 0); etc..
}

还考虑为图像实现onerror回调处理程序,以防图像加载出现问题。