[译]怎样用HTML5 Canvas制作一个简单的游戏
这是我翻译自LostDecadeGames主页的一篇文章,原文地址:How To Make A Simple HTML5 Canvas Game。
下面是正文:
自从我制作了一些HTML5游戏(例如Crypt Run)后,我收到了很多建议,要求我写一篇关于怎样利用HTML5 Canvas制作游戏的入门教程。花了一点时间考虑怎么着手写这篇文章后,我决定先实现一个我觉得最最简单的游戏,然后一行代码一行代码地进行讲解。
让我们开始吧,首先看看game.js,当然你也可以先玩玩这个游戏(译注:附件是游戏源码,用浏览器打开其中的index.html就可以玩了,或者也可以到lostdecadegames官网上去玩)。
附件下载地址:simple_canvas_game
1. 创建一个Canvas对象
// Create the canvas
var canvas = document.createElement("canvas");
var ctx = canvas.getContext("2d");
canvas.width = 512;
canvas.height = 480;
document.body.appendChild(canvas);
我们首先要做的是创建一个canvas对象。可以用JavaScript或HTML来做,都非常简单。此处我用的是JS。当创建了canvas之后,我们就可以获取它的上下文对象(context)、设置尺寸,并且把它加到当前文档中。
2. 载入图片
// Background image
var bgReady = false;
var bgImage = new Image();
bgImage.onload = function () {
bgReady = true;
};
bgImage.src = "images/background.png";
游戏需要图像,所以让我们载入一些图片吧。我想尽量简单化,所以只用了Image对象来做,当然,还可以将载入图像的功能封装成一个类或别的任何形式。代 码中的bgReady用来标识图片是否已完全载入,只有当图片载入完成后,我们才能使用它,如果在载入完成前就对其进行绘制或渲染,JS将会报一个DOM error的错误。
我们会用到三张图片(背景、英雄、怪物),每张图片都需要这样处理。
3. 定义游戏要使用的对象
// Game objects
var hero = {
speed: 256, // movement in pixels per second
x: 0,
y: 0
};
var monster = {
x: 0,
y: 0
};
var monstersCaught = 0;
定义一些变量,稍后会用到。hero对象的speed属性表示英雄的移动速度(像素/秒);monster对象不会移动,所以仅仅具有一对坐标;monstersCaught表示玩家抓住的怪物数量。
4. 处理玩家输入
// Handle keyboard controls
var keysDown = {};
addEventListener("keydown", function (e) {
keysDown[e.keyCode] = true;
}, false);
addEventListener("keyup", function (e) {
delete keysDown[e.keyCode];
}, false);
现在进行输入的处理。(对具有web开发背景的人来说,这是目前为止第一个具有挑战性的部分)对一般的网页来说,当用户开始输入时,可能需要马上开始播放 动画或请求数据。但在这里,我们想让游戏逻辑在一个单独的地方对游戏中发生的事情进行处理。为此我们需要将用户输入保存下来以备稍后处理,而不是立即处 理。 
我们通过简单地将事件对应的键编码(keyCode)保存在keysDown变量中来实现。如果该变量中具有某个键编码,就表示用户目前正按下这个键。简单吧!
5. 新游戏
// Reset the game when the player catches a monster
var reset = function () {
hero.x = canvas.width / 2;
hero.y = canvas.height / 2; // Throw the monster somewhere on the screen randomly
monster.x = 32 + (Math.random() * (canvas.width - 64));
monster.y = 32 + (Math.random() * (canvas.height - 64));
};
通过调用reset函数来开始新游戏。该函数将英雄(即玩家角色)放到屏幕中间,然后随机选择一个位置来安置怪物。
6. 更新对象
// Update game objects
var update = function (modifier) {
if (38 in keysDown) { // Player holding up
hero.y -= hero.speed * modifier;
}
if (40 in keysDown) { // Player holding down
hero.y += hero.speed * modifier;
}
if (37 in keysDown) { // Player holding left
hero.x -= hero.speed * modifier;
}
if (39 in keysDown) { // Player holding right
hero.x += hero.speed * modifier;
} // Are they touching?
if (
hero.x <= (monster.x + 32)
&& monster.x <= (hero.x + 32)
&& hero.y <= (monster.y + 32)
&& monster.y <= (hero.y + 32)
) {
++monstersCaught;
reset();
}
};
这是update函数,游戏每隔一定时间会调用它一次。它所做的第一件事情是检查用户是否按下了上下左右四个箭头键。如果是,就将我们的英雄向相应的方向移动。
update有一个modifier参数,这看起来好像有点奇怪。你会在游戏的主函数即main函数中看到它,不过我在这
儿先解释一下。modifier参数是一个从1开始的与时间相关的数。如果间隔刚好为1秒时,它的值就会为1,英雄移动的距离即为256像素(英雄的速度
为256像素/秒);而如果间隔是0.5秒,它的值就为0.5,即英雄移动的距离为其速度的一半,以此类推。通常update函数调用的间隔很短,所以
modifier的值很小,但用这种方式能够确保不管代码执行的速度怎么样,英雄的移动速度都是相同的。
我们已经实现了根据用户的输入来移动英雄,但我们还可以在移动英雄时对其进行检查,以确定是否有其他事件发生。例如:英雄是否与怪物发生了碰撞——当英雄与怪物发生碰撞时,我们为玩家进行计分(monstersCaught加1)并重置游戏(调用reset函数)。
7. 渲染对象
// Draw everything
var render = function () {
if (bgReady) {
ctx.drawImage(bgImage, 0, 0);
} if (heroReady) {
ctx.drawImage(heroImage, hero.x, hero.y);
} if (monsterReady) {
ctx.drawImage(monsterImage, monster.x, monster.y);
} // Score
ctx.fillStyle = "rgb(250, 250, 250)";
ctx.font = "24px Helvetica";
ctx.textAlign = "left";
ctx.textBaseline = "top";
ctx.fillText("Goblins caught: " + monstersCaught, 32, 32);
};
当你能够看到你的行动时游戏才会变得更有趣,所以让我们在屏幕上绘制吧。首先我们将背景图片绘制到canvas,然后是英雄和怪物。注意顺序很重要,因为任何位于表层的图片都会将其下面的像素覆盖掉。
接下来是文字,这有些不同,我们调用fillText函数显示玩家的分数。因为不需要复杂的动画或者对文字进行移动,所以只是绘制一下就ok了。
8. 游戏主循环
// The main game loop
var main = function () {
var now = Date.now();
var delta = now - then; update(delta / 1000);
render(); then = now;
};
游戏的主循环用来控制游戏流程。首先我们要获得当前的时间,这样我们才能计算时间差(自上次循环以来经过的时间)。然后计算modifier的值并交给update(需要将delta除以1000以将其转换为毫秒)。最后调用render并更新记录的时间。
更多关于游戏循环的内容见“Onslaught! Arena Case Study”。
9. 开始游戏吧
// Let's play this game!
reset();
var then = Date.now();
setInterval(main, 1); // Execute as fast as possible
快完成了,这是最后一段代码。首先调用reset来开始新游戏。(还记得吗,这会将英雄置中并随机安放怪物)。然后将起始时间保存到变量then中并启动游戏的主循环。
OK!(但愿)你现在已经理解了在HTML5 Canvas中用JS来开发游戏的基础知识了。建议最好是能够自己亲自试一把!
[译]怎样用HTML5 Canvas制作一个简单的游戏的更多相关文章
- 怎样用HTML5 Canvas制作一个简单的游戏
		原文连接: How To Make A Simple HTML5 Canvas Game 自从我制作了一些HTML5游戏(例如Crypt Run)后,我收到了很多建议,要求我写一篇关于怎样利用HTML ... 
- html5 canvas 实现一个简单的叮当猫头部
		原文:html5 canvas 实现一个简单的叮当猫头部 html5的canvas是很强大的,今天也是温习了一下之前的基础知识,然后学着做了一个简单的小案例.虽然在这一块几乎空白,但还是乐于尝试... ... 
- 【Bugly干货分享】一起用 HTML5 Canvas 做一个简单又骚气的粒子引擎
		Bugly 技术干货系列内容主要涉及移动开发方向,是由Bugly邀请腾讯内部各位技术大咖,通过日常工作经验的总结以及感悟撰写而成,内容均属原创,转载请标明出处. 前言 好吧,说是“粒子引擎”还是大言不 ... 
- 一起用HTML5 canvas做一个简单又骚气的粒子引擎
		前言 好吧,说是"粒子引擎"还是大言不惭而标题党了,离真正的粒子引擎还有点远.废话少说,先看demo 本文将教会你做一个简单的canvas粒子制造器(下称引擎). 世界观 这个简单 ... 
- 用Canvas写一个简单的游戏--别踩白块儿
		第一次写博客也不知怎么写,反正就按照我自己的想法来吧!怎么说呢?还是不要扯那些多余的话了,直接上正题吧! 第一次用canvas写游戏,所以挑个简单实现点的来干:别踩白块儿,其他那些怎么操作的那些就不用 ... 
- 使用pygame制作一个简单的游戏
		翻译自Will McGugan的<Beginning Game Development with Python and Pygame –From Novice to Professional&g ... 
- 如何使用 HTML5 Canvas 制作水波纹效果
		今天,我们继续分享 JavaScript 实现的效果例子,这篇文章会介绍使用 JavaScript 实现水波纹效果.水波效果以图片为背景,点击图片任意位置都会触发.有时候,我们使用普通的 Javasc ... 
- [译]终极塔防——运用HTML5从头创建一个塔防游戏
		翻译共享一篇CodeProject的高星力作,原文地址:http://www.codeproject.com/Articles/737238/Ultimate-Tower-Defense 下载演示项目 ... 
- 实例学习SSIS(一)--制作一个简单的ETL包
		原文:实例学习SSIS(一)--制作一个简单的ETL包 导读: 实例学习SSIS(一)--制作一个简单的ETL包 实例学习SSIS(二)--使用迭代 实例学习SSIS(三)--使用包配置 实例学习SS ... 
随机推荐
- The driver has not received any packets from the server
			解决方法: jdbc的url添加参数: jdbc.url=jdbc:mysql://localhost:3306/totosea?useUnicode=true&characterEncodi ... 
- 全面解析JavaScript的Backbone.js框架中的Router路由
			这篇文章主要介绍了Backbone.js框架中的Router路由功能,Router在Backbone中相当于一个MVC框架中的Controller控制器功能,需要的朋友可以参考下. Backbone ... 
- php 在线预览word
			一般类似oa或者crm等管理系统可能都会遇到需要再线查看word文档的功能,类似百度文库. 记得去年小组中的一个成员负责的项目就需要这个的功能,后面说是实现比较困难,就将就着用chm格式替代了.今天看 ... 
- Linux环境下用Weblogic发布项目【一】 --  安装Weblogic
			一.Weblogic安装系统环境: 1.前提条件: a.在笔记本[Windows7]上安装远程连接Linux软件:F-Secure SSH File Transfer Trial[简写为:FSSH] ... 
- windows下安装git
			1.从Git官网下载windows版本的git:http://git-scm.com/downloads 2.一般使用默认设置即可:一路next,git安装完毕! 3.但是如果这时你打开windows ... 
- [mysql][【优化集合】mysql数据库优化集合
			三个层面: 1.系统层面 2.mysql配置参数 3.sql语句优化 =========================================================== 一.系统层 ... 
- Linux网络监控工具nethogs
			Linux网络监控工具nethogs 标签: 监控工具linux 2015-12-17 22:06 448人阅读 评论(0) 收藏 举报 分类: linux(40) 版权声明:本文为博主原创文章, ... 
- 不可不知的robots.txt文件
			robots.txt基本介绍 robots.txt是一个纯文本文件,在这个文件中网站管理者可以声明该网站中不想被robots访问的部分,或者指定搜索引擎只收录指定的内容. 当一个搜索机器人(有的叫搜索 ... 
- Anaconda创建python(2.7/3.6)的虚拟环境后需要添加ipykernel
			今天在工作的过程中遇到这样一个问题:安装完Anaconda利用conda创建了虚拟环境,但是启动jupyter notebook之后却找不到虚拟环境中的python kernel.后来上网找到了解决办 ... 
- YAML schema reference
			YAML schema reference 10/30/2018 14 minutes to read Azure Pipelines Here's a detailed reference guid ... 
