最近公司作项目的时候正好使用到phaser,在这里作一下本身整理出来的一些心得,方便你们参考,phaser这一个游戏引擎一般是作2d游戏的,入门也很是简单,只需你会一点的javascript,可是你想作一个比较完美的游戏的话,那么光靠一点点的javascript是远远不够的,本篇博客将快速带你入门phaser。javascript
phaser是一款快速,免费及开源HTML5游戏框架,它支持WebGL和Canvas两种渲染模式,能够在任何web浏览器环境下运行,游戏能够经过第三方工具转为iOS、Android 支持的 Native APP,容许使用 JavaScript 和 TypeScript 进行开发。html
phaser中的一切都是从Game类开始,因此咱们暂时将Game类看成phaser的中心吧!当你new了一个Game以后,game中的不少属性就有了,phaser的核心能够用以下这张图表示。java
这里咱们常用的对象有load,time,world,input,camera。git
<!DOCTYPE html> <html> <head> <meta charset="UTF-8"> <title>快速入门phaser</title> </head> <body> <script src="../../js/phaser.min.js" type="text/javascript" charset="utf-8"></script> <script type="text/javascript"> var game=new Phaser.Game(800,600,Phaser.AUTO,'',{preload:preload,create:create,update:update}); function preload(){ console.log('preload'); } function create(){ console.log('create'); } function update(){ console.log('update'); } </script> </body> </html>
<!DOCTYPE html> <html> <head> <meta charset="UTF-8"> <title>快速入门phaser<</title> </head> <body> <script src="../../js/phaser.min.js" type="text/javascript" charset="utf-8"></script> <script type="text/javascript"> var game=new Phaser.Game(800,600,Phaser.AUTO); var main=function(game){ this.init=function(){ //游戏场景初始化 } this.preload=function(){ //游戏资源预加载 } this.create=function(){ //游戏场景建立 } this.update=function(){ //游戏逻辑实现 } this.render=function(){ //游戏自定义渲染 } } </script> </body> </html>
<!DOCTYPE html> <html> <head> <meta charset="UTF-8"> <title>快速入门phaser</title> </head> <body> <script src="../../js/phaser.min.js" type="text/javascript" charset="utf-8"></script> <script type="text/javascript"> var game=new Phaser.Game(800,600,Phaser.AUTO); game.state.add('state',state); game.state.start('state'); function state(){ this.init=function(){} this.preload=function(){} this.create=function(){} this.update=function(){} this.render=function(){} } </script> </body> </html>
<!DOCTYPE html> <html> <head> <meta charset="UTF-8"> <title>快速入门phaser</title> </head> <body> <script src="../../js/phaser.min.js" type="text/javascript" charset="utf-8"></script> <script type="text/javascript"> var game=new Phaser.Game(800,600,Phaser.AUTO,state); function state(){ this.init=function(){ } this.preload=function(){ } this.create=function(){ } this.update=function(){ } this.render=function(){ } } </script> </body> </html>
<!DOCTYPE html> <html> <head> <meta charset="UTF-8"> <title>快速入门phasr</title> </head> <body> <script src="../../js/phaser.min.js" type="text/javascript" charset="utf-8"></script> <script type="text/javascript"> var config={ width:800, height:600, renderer:Phaser.AUTO, antialias:true, multiTexture:true, state:{ preload:preload, create:create, update:update } } var game=new Phaser.Game(config); function preload(){ } function create(){ } function update(){ } </script> </body> </html>
在开发中,咱们常用方式五建立phaser对象,固然你也能够根据本身的喜爱选择,就看你是喜欢函数建立仍是对象建立。github
Name | Type | Default |
width:游戏宽度 | number|string | 800 |
height:游戏高度 | number|string | 600 |
renderer:游戏渲染方式 | number | Phaser.AUTO |
parent:游戏容器 | string|HTMLElement | '' |
state:游戏默认场景 | object | null |
transparent:画布元素是否透明 | boolean | false |
antialias:是否开启抗锯齿 | boolean | true |
physicsConfig:物理引擎配置 | object | null |
画布宽度,数字或字符串类型可选参数,默认为800,若是以字符串的形式给出,该值必须在0到100之间,为百分比,若是没有指定父容器,则默认为浏览器窗口web
画布高度canvas
指定渲染机制,值能够是Phaser.WebGL,Phaser.Canvas,Phaser.AUTO(自动尝试使用WebGL,若是浏览器或设备不支持,使用canvas)或者Phaser.HEADLESS(不进行渲染)浏览器
想插入游戏画布的DOM元素,画布的父元素,可选值为DOM自己或者是id,若是为空字符串,画布将被插入到body元素中框架
默认的状态对象,对象类型,能够是null,也能够是Phaser.state函数(初始化,预加载,建立,更新,渲染)dom
画布背景是否透明,布尔值,默认为false
是否绘制为平滑纹理,布尔值,默认为true
一个物理配置对象,在Physics world建立时传递,对象默认为null
参考文档:https://photonstorm.github.io/phaser-ce/Phaser.Game.html
中文网:http://www.phaserengine.com/
phaser小站:https://www.phaser-china.com/example-detail-422.html
社区:http://club.phaser-china.com/
接下来咱们经过phaser实现一个小游戏以及快速入门,见识下phaser开发游戏的功能有多么的强大,须要说明的是,这个就是phaser官方入门的案例,废话很少说,直接上源码。
<!DOCTYPE html> <html> <head> <meta charset="UTF-8"> <title>phaser入门小游戏</title> </head> <body> <script src="../../js/phaser.min.js" type="text/javascript" charset="utf-8"></script> <script type="text/javascript"> var config={ width:800, height:600, renderer:Phaser.AUTO, antialias:true, multiTexture:true, state:{ preload:preload, create:create, update:update, } } var game=new Phaser.Game(config); function preload(){ //加载资源 } function create(){ //对象的建立及初始化 } function update(){ //游戏主循环 } </script> </body> </html>
在这里,咱们已经建立了游戏场景和加载了游戏场景,可是咱们看到一片黑的,接下来咱们加点东西。
<!DOCTYPE html> <html> <head> <meta charset="UTF-8"> <title>phaser入门小游戏</title> </head> <body> <script src="../../js/phaser.min.js" type="text/javascript" charset="utf-8"></script> <script type="text/javascript"> var config={ width:800, height:600, renderer:Phaser.AUTO, antialias:true, multiTexture:true, state:{ preload:preload, create:create, update:update, } } var game=new Phaser.Game(config); function preload(){ //加载资源 game.load.image('sky','../../assets/sky.png'); game.load.image('ground','../../assets/star.png'); game.load.image('star','../../assets/star.png'); game.load.spritesheet('dude','../../assets/dude.png',32,48); } function create(){ //对象的建立及初始化 game.add.sprite(0,0,'star'); } function update(){ //游戏主循环 } </script> </body> </html>
咱们看到屏幕的左上角出现了一颗星星,可是仍是缺点什么,这种效果依然不是咱们想要的效果,接下来咱们让它更具体化。
<!DOCTYPE html> <html> <head> <meta charset="UTF-8"> <title>phaser入门小游戏</title> </head> <body> <script src="../../js/phaser.min.js" type="text/javascript" charset="utf-8"></script> <script type="text/javascript"> var config={ width:800, height:600, renderer:Phaser.AUTO, antialias:true, multiTexture:true, state:{ preload:preload, create:create, update:update, } } var game=new Phaser.Game(config); var platforms;//场地 function preload(){ //加载资源 game.load.image('sky','../../assets/sky.png'); game.load.image('ground','../../assets/platform.png'); game.load.image('star','../../assets/star.png'); game.load.spritesheet('dude','../../assets/dude.png',32,48); } function create(){ //对象的建立及初始化 game.physics.startSystem(Phaser.Physics.ARCADE); game.add.sprite(0,0,'sky'); //将图片添加到游戏场景中 platforms=game.add.group(); platforms.enableBody=true; var ground=platforms.create(0,game.world.height-64,'ground'); ground.scale.setTo(2,2); ground.body.immovable=true; var ledge=platforms.create(400,400,'ground'); ledge.body.immovable=true; ledge=platforms.create(-150,250,'ground'); ledge.body.immovable=true; } function update(){ //游戏主循环 } </script> </body> </html>
在这里咱们已经将场景加入进来了以及开启了物理引擎,固然这只是为后面作准备,而后咱们建立了天空,大地和两个平板。大地和平板的位置定位,咱们是经过坐标来进行的,
其中,大地和两个平板都被加到了platforms这个组中,这个组咱们为它启动了物理属性,而后咱们设置了大地和两个平板是不能动的,这样他们就不会因为撞击被改变位置。接下来,咱们来加入一个小人,这个小人也是咱们游戏的主角。
<!DOCTYPE html> <html> <head> <meta charset="UTF-8"> <title>phaser入门小游戏</title> </head> <body> <script src="../../js/phaser.min.js" type="text/javascript" charset="utf-8"></script> <script type="text/javascript"> var config={ width:800, height:600, renderer:Phaser.AUTO, antialias:true, multiTexture:true, state:{ preload:preload, create:create, update:update, } } var game=new Phaser.Game(config); var platforms;//场地 var player;//游戏主角 function preload(){ //加载资源 game.load.image('sky','../../assets/sky.png'); game.load.image('ground','../../assets/platform.png'); game.load.image('star','../../assets/star.png'); game.load.spritesheet('dude','../../assets/dude.png',32,48); } function create(){ //对象的建立及初始化 game.physics.startSystem(Phaser.Physics.ARCADE); game.add.sprite(0,0,'sky'); //夹图片添加到游戏场景中 platforms=game.add.group(); platforms.enableBody=true; var ground=platforms.create(0,game.world.height-64,'ground'); ground.scale.setTo(2,2); ground.body.immovable=true; var ledge=platforms.create(400,400,'ground'); ledge.body.immovable=true; ledge=platforms.create(-150,250,'ground'); ledge.body.immovable=true; //加载主角 player=game.add.sprite(32,game.world.height-150,'dude'); game.physics.arcade.enable(player); player.body.bounce.y=0.2; //设置主角的弹性 player.body.gravity.y=300; //设置主角的重力 player.body.collideWorldBounds=true; player.animations.add('left',[0,1,2,3],10,true); //设置主角向左方向的序列帧 player.animations.add('right',[5,6,7,8],10,true); //设置主角向右方向的序列帧 } function update(){ //游戏主循环 } </script> </body> </html>
dude.png图片
一样是经过game.add.sprite将精灵加入进来,可是你们仔细看看dude.png这张资源图片,这是一个帧动画序列,里面包含了主角左移和右移的动画帧。咱们一样给它开启了物理属性,而后设置了它的弹性和重力。player.body.collideWorldBounds = true;这句话设置了它会与边界进行碰撞,这就是为何主角落下的时候,到游戏区域边界就不会掉下去,你们能够把这句话注释掉再运行,看看会是什么状况。在这里,咱们还为小人添加了两个动画,一个是向左移动,一个是向右移动,分别指定了响应的动画帧,这也是为后续的动画作准备。
<!DOCTYPE html> <html> <head> <meta charset="UTF-8"> <title>phaser入门小游戏</title> </head> <body> <script src="../../js/phaser.min.js" type="text/javascript" charset="utf-8"></script> <script type="text/javascript"> var config={ width:800, height:600, renderer:Phaser.AUTO, antialias:true, multiTexture:true, state:{ preload:preload, create:create, update:update, } } var game=new Phaser.Game(config); var platforms;//场地 var player;//游戏主角 function preload(){ //加载资源 game.load.image('sky','../../assets/sky.png'); game.load.image('ground','../../assets/platform.png'); game.load.image('star','../../assets/star.png'); game.load.spritesheet('dude','../../assets/dude.png',32,48); } function create(){ //对象的建立及初始化 game.physics.startSystem(Phaser.Physics.ARCADE); game.add.sprite(0,0,'sky'); //夹图片添加到游戏场景中 platforms=game.add.group(); platforms.enableBody=true; var ground=platforms.create(0,game.world.height-64,'ground'); ground.scale.setTo(2,2); ground.body.immovable=true; var ledge=platforms.create(400,400,'ground'); ledge.body.immovable=true; ledge=platforms.create(-150,250,'ground'); ledge.body.immovable=true; //加载主角 player=game.add.sprite(32,game.world.height-150,'dude'); game.physics.arcade.enable(player); player.body.bounce.y=0.2; //设置主角的弹性 player.body.gravity.y=300; //设置主角的重力 player.body.collideWorldBounds=true; player.animations.add('left',[0,1,2,3],10,true); //设置主角向左方向的序列帧 player.animations.add('right',[5,6,7,8],10,true); //设置主角向右方向的序列帧 } function update(){ //游戏主循环 game.physics.arcade.collide(player,platforms); } </script> </body> </html>
是否是很惊讶?要让主角站在地上,只要在update中加上一句,game.physics.arcade.collide(player, platforms);就能够了,这句话表示,检测主角与platforms组的碰撞,而大地正是在platforms组中,这样,主角就不会穿过大地了。一样地,当主角与两个平板碰撞时,也不会穿过了。接下来咱们让主角运动。
<!DOCTYPE html> <html> <head> <meta charset="UTF-8"> <title>phaser入门小游戏</title> </head> <body> <script src="../../js/phaser.min.js" type="text/javascript" charset="utf-8"></script> <script type="text/javascript"> var config={ width:800, height:600, renderer:Phaser.AUTO, antialias:true, multiTexture:true, state:{ preload:preload, create:create, update:update, } } var game=new Phaser.Game(config); var platforms;//场地 var player;//游戏主角 var cursors;//控制键 function preload(){ //加载资源 game.load.image('sky','../../assets/sky.png'); game.load.image('ground','../../assets/platform.png'); game.load.image('star','../../assets/star.png'); game.load.spritesheet('dude','../../assets/dude.png',32,48); } function create(){ //对象的建立及初始化 game.physics.startSystem(Phaser.Physics.ARCADE); game.add.sprite(0,0,'sky'); //夹图片添加到游戏场景中 platforms=game.add.group(); platforms.enableBody=true; var ground=platforms.create(0,game.world.height-64,'ground'); ground.scale.setTo(2,2); ground.body.immovable=true; var ledge=platforms.create(400,400,'ground'); ledge.body.immovable=true; ledge=platforms.create(-150,250,'ground'); ledge.body.immovable=true; //加载主角 player=game.add.sprite(32,game.world.height-150,'dude'); game.physics.arcade.enable(player); player.body.bounce.y=0.2; //设置主角的弹性 player.body.gravity.y=300; //设置主角的重力 player.body.collideWorldBounds=true; player.animations.add('left',[0,1,2,3],10,true); //设置主角向左方向的序列帧 player.animations.add('right',[5,6,7,8],10,true); //设置主角向右方向的序列帧 //建立控制键对象 cursors=game.input.keyboard.createCursorKeys(); } function update(){ //游戏主循环 game.physics.arcade.collide(player,platforms); //控制主角开始 player.body.velocity.x=0; if(cursors.left.isDown){ player.body.velocity.x=-150; player.animations.play('left');//播放主角向左运动的序列帧动画 }else if(cursors.right.isDown){ player.body.velocity.x=150; player.animations.play('right');//播放主角向右的序列帧动画 }else{ player.animations.stop();//中止动画 player.frame=4; //小球静止时显示第四帧动画 } if(cursors.up.isDown&&player.body.touching.down){ player.body.velocity.y=-350; } } </script> </body> </html>
咱们但愿让主角在按下方向左键的时候,向左移动,按下方向右键的时候,向右移动,为了实现这一功能,咱们又定义了一个cursors,咱们经过cursors = game.input.keyboard.createCursorKeys();来获取系统的键盘输入对象。而后,咱们在update中,经过cursors.left.isDown来判断用户是否按下了键盘左键,若是按下了,咱们给主角设置一个速度,而后播放左移的动画,方向右键的逻辑是同样的。若是方向左键和右键都没有按下,那么咱们就经过player.frame来设置小人停在第4帧。小人的跳跃是经过方向上键来实现的,可是这里有一个条件,就是小人在空中的时候,不容许跳跃,因此,加上了一个player.body.touching.down的判断条件。
<!DOCTYPE html> <html> <head> <meta charset="UTF-8"> <title>phaser入门小游戏</title> </head> <body> <script src="../../js/phaser.min.js" type="text/javascript" charset="utf-8"></script> <script type="text/javascript"> var config={ width:800, height:600, renderer:Phaser.AUTO, antialias:true, multiTexture:true, state:{ preload:preload, create:create, update:update, } } var game=new Phaser.Game(config); var platforms;//场地 var player;//游戏主角 var cursors;//控制键 var stars;//星星 function preload(){ //加载资源 game.load.image('sky','../../assets/sky.png'); game.load.image('ground','../../assets/platform.png'); game.load.image('star','../../assets/star.png'); game.load.spritesheet('dude','../../assets/dude.png',32,48); } function create(){ //对象的建立及初始化 game.physics.startSystem(Phaser.Physics.ARCADE); game.add.sprite(0,0,'sky'); //夹图片添加到游戏场景中 platforms=game.add.group(); platforms.enableBody=true; var ground=platforms.create(0,game.world.height-64,'ground'); ground.scale.setTo(2,2); ground.body.immovable=true; var ledge=platforms.create(400,400,'ground'); ledge.body.immovable=true; ledge=platforms.create(-150,250,'ground'); ledge.body.immovable=true; //加载主角 player=game.add.sprite(32,game.world.height-150,'dude'); game.physics.arcade.enable(player); player.body.bounce.y=0.2; //设置主角的弹性 player.body.gravity.y=300; //设置主角的重力 player.body.collideWorldBounds=true; player.animations.add('left',[0,1,2,3],10,true); //设置主角向左方向的序列帧 player.animations.add('right',[5,6,7,8],10,true); //设置主角向右方向的序列帧 //建立控制键对象 cursors=game.input.keyboard.createCursorKeys(); //加载星星 stars=game.add.group(); //把星星先添加到组中 stars.enableBody = true; for(var i=0;i<20;i++){ var star=stars.create(i*70,0,'star'); star.body.gravity.y=300; //设置星星的重力 star.body.bounce.y=0.7+Math.random()*0.2; //设置星星的弹性 } } function update(){ //游戏主循环 game.physics.arcade.collide(player,platforms); //星星加载相关 game.physics.arcade.collide(stars,platforms); game.physics.arcade.overlap(player,stars,collectStar,null,this); //控制主角开始 player.body.velocity.x=0; if(cursors.left.isDown){ player.body.velocity.x=-150; player.animations.play('left');//播放主角向左运动的序列帧动画 }else if(cursors.right.isDown){ player.body.velocity.x=150; player.animations.play('right');//播放主角向右的序列帧动画 }else{ player.animations.stop();//中止动画 player.frame=4; //小球静止时显示第四帧动画 } if(cursors.up.isDown&&player.body.touching.down){ player.body.velocity.y=-350; } } function collectStar(player,stars){ stars.kill();//销毁星星 } </script> </body> </html>
在create中,咱们又建立了一个stars的组,在这个组中,添加了星星,而后设置了它们的重力,随机设置了弹性,因此它们掉落的时候,碰到平板或者地面,会弹起不一样的高度。一样,星星也不能穿过地面,因此在update中,添加了碰撞检测。
还有一层碰撞检测就是小人和星星的碰撞,当主角和星星发生碰撞的时候,须要让星星消失,这时候,再添加碰撞检测的时候,咱们还添加了一个回调函数collectStar,在这里面,咱们的player和star都会做为参数传递进来,经过调用star.kill();将星星销毁。
<!DOCTYPE html> <html> <head> <meta charset="UTF-8"> <title>phaser入门小游戏</title> </head> <body> <script src="../../js/phaser.min.js" type="text/javascript" charset="utf-8"></script> <script type="text/javascript"> var config={ width:800, height:600, renderer:Phaser.AUTO, antialias:true, multiTexture:true, state:{ preload:preload, create:create, update:update, } } var game=new Phaser.Game(config); var platforms;//场地 var player;//游戏主角 var cursors;//控制键 var stars;//星星 var score=0;//初始分数为0 var scoreText;//展现分数的文本 function preload(){ //加载资源 game.load.image('sky','../../assets/sky.png'); game.load.image('ground','../../assets/platform.png'); game.load.image('star','../../assets/star.png'); game.load.spritesheet('dude','../../assets/dude.png',32,48); } function create(){ //对象的建立及初始化 game.physics.startSystem(Phaser.Physics.ARCADE); game.add.sprite(0,0,'sky'); //夹图片添加到游戏场景中 platforms=game.add.group(); platforms.enableBody=true; var ground=platforms.create(0,game.world.height-64,'ground'); ground.scale.setTo(2,2); ground.body.immovable=true; var ledge=platforms.create(400,400,'ground'); ledge.body.immovable=true; ledge=platforms.create(-150,250,'ground'); ledge.body.immovable=true; //加载主角 player=game.add.sprite(32,game.world.height-150,'dude'); game.physics.arcade.enable(player); player.body.bounce.y=0.2; //设置主角的弹性 player.body.gravity.y=300; //设置主角的重力 player.body.collideWorldBounds=true; player.animations.add('left',[0,1,2,3],10,true); //设置主角向左方向的序列帧 player.animations.add('right',[5,6,7,8],10,true); //设置主角向右方向的序列帧 //建立控制键对象 cursors=game.input.keyboard.createCursorKeys(); //加载星星 stars=game.add.group(); //把星星先添加到组中 stars.enableBody = true; for(var i=0;i<20;i++){ var star=stars.create(i*70,0,'star'); star.body.gravity.y=300; //设置星星的重力 star.body.bounce.y=0.7+Math.random()*0.2; //设置星星的弹性 } //分数相关 scoreText=game.add.text(16,16,'分数:0',{fontSize:'32px',fill:'#000'}); } function update(){ //游戏主循环 game.physics.arcade.collide(player,platforms); //星星加载相关 game.physics.arcade.collide(stars,platforms); game.physics.arcade.overlap(player,stars,collectStar,null,this); //控制主角开始 player.body.velocity.x=0; if(cursors.left.isDown){ player.body.velocity.x=-150; player.animations.play('left');//播放主角向左运动的序列帧动画 }else if(cursors.right.isDown){ player.body.velocity.x=150; player.animations.play('right');//播放主角向右的序列帧动画 }else{ player.animations.stop();//中止动画 player.frame=4; //小球静止时显示第四帧动画 } if(cursors.up.isDown&&player.body.touching.down){ player.body.velocity.y=-350; } } function collectStar(player,stars){ stars.kill();//销毁星星 score+=10; scoreText.text='分数:'+score; } </script> </body> </html>
咱们经过game.add.text为场景加上一个文本,显示在左上角,在collectStar的时候,将分数进行累加,而后更新显示,这样就结束啦。到这里,一个简单的小游戏就实现了,是否是比想象中的简单呢?