這個文章怎么突然這么多人看啊。請大家多關注我其他文章啊
?
?
html:
<html>
<head>
<meta charset="utf8">
<title>html5 pacman吃豆人游戲代碼</title><style>body{background-color: #292929}*{padding:0;margin:0;}.wrapper{width: 960px;margin:0 auto;line-height:36px;text-align:center;color:#999;}canvas{display:block;background: #000;}.mod-botton{height: 32px;padding: 15px 0;text-align: center;}
</style></head>
<body><script src="/demos/googlegg.js"></script><div class="wrapper"><canvas id="canvas" width="960" height="640">不支持畫布</canvas><p>按[空格]暫停或繼續</p>
</div>
<script src="game.js"></script>
<script src="index.js"></script><div style="text-align:center;margin:50px 0; font:normal 14px/24px 'MicroSoft YaHei';">
</div>
</body>
</html>
game.js:
'use strict';
/*
* 小型游戲引擎
*/// requestAnimationFrame polyfill
if (!Date.now)
Date.now = function() { return new Date().getTime(); };
(function() {'use strict';var vendors = ['webkit', 'moz'];for (var i = 0; i < vendors.length && !window.requestAnimationFrame; ++i) {var vp = vendors[i];window.requestAnimationFrame = window[vp+'RequestAnimationFrame'];window.cancelAnimationFrame = (window[vp+'CancelAnimationFrame'] || window[vp+'CancelRequestAnimationFrame']);}if (/iP(ad|hone|od).*OS 6/.test(window.navigator.userAgent) // iOS6 is buggy|| !window.requestAnimationFrame || !window.cancelAnimationFrame) {var lastTime = 0;window.requestAnimationFrame = function(callback) {var now = Date.now();var nextTime = Math.max(lastTime + 16, now);return setTimeout(function() { callback(lastTime = nextTime); },nextTime - now);};window.cancelAnimationFrame = clearTimeout;}
}());function Game(id,params){var _ = this;var settings = {width:960, //畫布寬度height:640 //畫布高度};var _extend = function(target,settings,params){params = params||{};for(var i in settings){target[i] = params[i]||settings[i];}return target;};_extend(_,settings,params);var $canvas = document.getElementById(id);$canvas.width = _.width;$canvas.height = _.height;var _context = $canvas.getContext('2d'); //畫布上下文環境var _stages = []; //布景對象隊列var _events = {}; //事件集合var _index=0, //當前布景索引_hander; //幀動畫控制//活動對象構造var Item = function(params){this._params = params||{};this._id = 0; //標志符this._stage = null; //與所屬布景綁定this._settings = {x:0, //位置坐標:橫坐標y:0, //位置坐標:縱坐標width:20, //寬height:20, //高type:0, //對象類型,0表示普通對象(不與地圖綁定),1表示玩家控制對象,2表示程序控制對象color:'#F00', //標識顏色status:1, //對象狀態,0表示未激活/結束,1表示正常,2表示暫停,3表示臨時,4表示異常orientation:0, //當前定位方向,0表示右,1表示下,2表示左,3表示上speed:0, //移動速度//地圖相關location:null, //定位地圖,Map對象coord:null, //如果對象與地圖綁定,需設置地圖坐標;若不綁定,則設置位置坐標path:[], //NPC自動行走的路徑vector:null, //目標坐標//布局相關frames:1, //速度等級,內部計算器times多少幀變化一次times:0, //刷新畫布計數(用于循環動畫狀態判斷)timeout:0, //倒計時(用于過程動畫狀態判斷)control:{}, //控制緩存,到達定位點時處理update:function(){}, //更新參數信息draw:function(){} //繪制};_extend(this,this._settings,this._params);};Item.prototype.bind = function(eventType,callback){if(!_events[eventType]){_events[eventType] = {};$canvas.addEventListener(eventType,function(e){var position = _.getPosition(e);_stages[_index].items.forEach(function(item){if(Math.abs(position.x-item.x)<item.width/2&&Math.abs(position.y-item.y)<item.height/2){var key = 's'+_index+'i'+item._id;if(_events[eventType][key]){_events[eventType][key](e);}}});e.preventDefault();});}_events[eventType]['s'+this._stage.index+'i'+this._id] = callback.bind(this); //綁定作用域};//地圖對象構造器var Map = function(params){this._params = params||{};this._id = 0; //標志符this._stage = null; //與所屬布景綁定this._settings = {x:0, //地圖起點坐標y:0,size:20, //地圖單元的寬度data:[], //地圖數據x_length:0, //二維數組x軸長度y_length:0, //二維數組y軸長度frames:1, //速度等級,內部計算器times多少幀變化一次times:0, //刷新畫布計數(用于循環動畫狀態判斷)cache:false, //是否靜態(如靜態則設置緩存)update:function(){}, //更新地圖數據draw:function(){}, //繪制地圖};_extend(this,this._settings,this._params);};//獲取地圖上某點的值Map.prototype.get = function(x,y){if(this.data[y]&&typeof this.data[y][x]!='undefined'){return this.data[y][x];}return -1;};//設置地圖上某點的值Map.prototype.set = function(x,y,value){if(this.data[y]){this.data[y][x] = value;}};//地圖坐標轉畫布坐標Map.prototype.coord2position = function(cx,cy){return {x:this.x+cx*this.size+this.size/2,y:this.y+cy*this.size+this.size/2};};//畫布坐標轉地圖坐標Map.prototype.position2coord = function(x,y){var fx = Math.abs(x-this.x)%this.size-this.size/2;var fy = Math.abs(y-this.y)%this.size-this.size/2;return {x:Math.floor((x-this.x)/this.size),y:Math.floor((y-this.y)/this.size),offset:Math.sqrt(fx*fx+fy*fy)};};//尋址算法Map.prototype.finder = function(params){var defaults = {map:null,start:{},end:{},type:'path'};var options = _extend({},defaults,params);if(options.map[options.start.y][options.start.x]||options.map[options.end.y][options.end.x]){ //當起點或終點設置在墻上return [];}var finded = false;var result = [];var y_length = options.map.length;var x_length = options.map[0].length;var steps = []; //步驟的映射for(var y=y_length;y--;){steps[y] = new Array(x_length).fill(0);}var _getValue = function(x,y){ //獲取地圖上的值if(options.map[y]&&typeof options.map[y][x]!='undefined'){return options.map[y][x];}return -1;};var _next = function(to){ //判定是否可走,可走放入列表var value = _getValue(to.x,to.y);if(value<1){if(value==-1){to.x = (to.x+x_length)%x_length;to.y = (to.y+y_length)%y_length;to.change = 1;}if(!steps[to.y][to.x]){result.push(to);}}};var _render = function(list){//找線路var new_list = [];var next = function(from,to){var value = _getValue(to.x,to.y);if(value<1){ //當前點是否可以走if(value==-1){to.x = (to.x+x_length)%x_length;to.y = (to.y+y_length)%y_length;to.change = 1;}if(to.x==options.end.x&&to.y==options.end.y){steps[to.y][to.x] = from;finded = true;}else if(!steps[to.y][to.x]){steps[to.y][to.x] = from;new_list.push(to);}}};list.forEach(function(current){next(current,{y:current.y+1,x:current.x});next(current,{y:current.y,x:current.x+1});next(current,{y:current.y-1,x:current.x});next(current,{y:current.y,x:current.x-1});});if(!finded&&new_list.length){_render(new_list);}};_render([options.start]);if(finded){var current=options.end;if(options.type=='path'){while(current.x!=options.start.x||current.y!=options.start.y){result.unshift(current);current=steps[current.y][current.x];}}else if(options.type=='next'){_next({x:current.x+1,y:current.y});_next({x:current.x,y:current.y+1});_next({x:current.x-1,y:current.y});_next({x:current.x,y:current.y-1});}}return result;};//布景對象構造器var Stage = function(params){this._params = params||{};this._settings = {index:0, //布景索引status:0, //布景狀態,0表示未激活/結束,1表示正常,2表示暫停,3表示臨時,4表示異常maps:[], //地圖隊列audio:[], //音頻資源images:[], //圖片資源items:[], //對象隊列timeout:0, //倒計時(用于過程動畫狀態判斷)update:function(){} //嗅探,處理布局下不同對象的相對關系};_extend(this,this._settings,this._params);};//添加對象Stage.prototype.createItem = function(options){var item = new Item(options);//動態屬性if(item.location){var position = item.location.coord2position(item.coord.x,item.coord.y);item.x = position.x;item.y = position.y;}//關系綁定item._stage = this;item._id = this.items.length;this.items.push(item);return item;};//重置物體位置Stage.prototype.resetItems = function(){this.status = 1;this.items.forEach(function(item,index){_extend(item,item._settings,item._params);if(item.location){var position = item.location.coord2position(item.coord.x,item.coord.y);item.x = position.x;item.y = position.y;}});};//獲取對象列表Stage.prototype.getItemsByType = function(type){return this.items.filter(function(item){if(item.type==type){return item;}});};//添加地圖Stage.prototype.createMap = function(options){var map = new Map(options);//動態屬性map.data = JSON.parse(JSON.stringify(map._params.data));map.y_length = map.data.length;map.x_length = map.data[0].length;map.imageData = null;//關系綁定map._stage = this;map._id = this.maps.length;this.maps.push(map);return map;};//重置地圖Stage.prototype.resetMaps = function(){this.status = 1;this.maps.forEach(function(map){_extend(map,map._settings,map._params);map.data = JSON.parse(JSON.stringify(map._params.data));map.y_length = map.data.length;map.x_length = map.data[0].length;map.imageData = null;});};//重置Stage.prototype.reset = function(){_extend(this,this._settings,this._params);this.resetItems();this.resetMaps();};//綁定事件Stage.prototype.bind = function(eventType,callback){if(!_events[eventType]){_events[eventType] = {};window.addEventListener(eventType,function(e){var key = 's' + _index;if(_events[eventType][key]){_events[eventType][key](e);}e.preventDefault();});}_events[eventType]['s'+this.index] = callback.bind(this); //綁定事件作用域};//動畫開始this.start = function() {var f = 0; //幀數計算var fn = function(){var stage = _stages[_index];_context.clearRect(0,0,_.width,_.height); //清除畫布_context.fillStyle = '#000000';_context.fillRect(0,0,_.width,_.height);f++;if(stage.timeout){stage.timeout--;}if(stage.update()!=false){ //update返回false,則不繪制stage.maps.forEach(function(map){if(!(f%map.frames)){map.times = f/map.frames; //計數器}if(map.cache){if(!map.imageData){_context.save();map.draw(_context);map.imageData = _context.getImageData(0,0,_.width,_.height);_context.restore();}else{_context.putImageData(map.imageData,0,0);}}else{map.update();map.draw(_context);}});stage.items.forEach(function(item){if(!(f%item.frames)){item.times = f/item.frames; //計數器}if(stage.status==1&&item.status!=2){ //對象及布景狀態都不處于暫停狀態if(item.location){item.coord = item.location.position2coord(item.x,item.y);}if(item.timeout){item.timeout--;}item.update();}item.draw(_context);});}_hander = requestAnimationFrame(fn);};_hander = requestAnimationFrame(fn);};//動畫結束this.stop = function(){_hander&&cancelAnimationFrame(_hander);};//事件坐標this.getPosition = function(e){var box = $canvas.getBoundingClientRect();return {x:e.clientX-box.left*(_.width/box.width),y:e.clientY-box.top*(_.height/box.height)};}//創建布景this.createStage = function(options){var stage = new Stage(options);stage.index = _stages.length;_stages.push(stage);return stage;};//指定布景this.setStage = function(index){_stages[_index].status = 0;_index = index;_stages[_index].status = 1;return _stages[_index];};//下個布景this.nextStage = function(){if(_index<_stages.length-1){return this.setStage(++_index);}else{throw new Error('unfound new stage.');}};//初始化游戲引擎this.init = function(){_index = 0;this.start();};
}
index.js:
//主程序,業務邏輯
(function(){var _DATA = [ //地圖數據[1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1],[1,0,0,0,0,0,0,0,0,0,0,0,0,1,1,0,0,0,0,0,0,0,0,0,0,0,0,1],[1,0,1,1,1,1,0,1,1,1,1,1,0,1,1,0,1,1,1,1,1,0,1,1,1,1,0,1],[1,0,1,1,1,1,0,1,1,1,1,1,0,1,1,0,1,1,1,1,1,0,1,1,1,1,0,1],[1,0,1,1,1,1,0,1,1,1,1,1,0,1,1,0,1,1,1,1,1,0,1,1,1,1,0,1],[1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1],[1,0,1,1,1,1,0,1,1,0,1,1,1,1,1,1,1,1,0,1,1,0,1,1,1,1,0,1],[1,0,1,1,1,1,0,1,1,0,1,1,1,1,1,1,1,1,0,1,1,0,1,1,1,1,0,1],[1,0,0,0,0,0,0,1,1,0,0,0,0,1,1,0,0,0,0,1,1,0,0,0,0,0,0,1],[1,1,1,1,1,1,0,1,1,1,1,1,0,1,1,0,1,1,1,1,1,0,1,1,1,1,1,1],[1,1,1,1,1,1,0,1,1,1,1,1,0,1,1,0,1,1,1,1,1,0,1,1,1,1,1,1],[1,1,1,1,1,1,0,1,1,0,0,0,0,0,0,0,0,0,0,1,1,0,1,1,1,1,1,1],[1,1,1,1,1,1,0,1,1,0,1,1,1,2,2,1,1,1,0,1,1,0,1,1,1,1,1,1],[1,1,1,1,1,1,0,1,1,0,1,2,2,2,2,2,2,1,0,1,1,0,1,1,1,1,1,1],[0,0,0,0,0,0,0,0,0,0,1,2,2,2,2,2,2,1,0,0,0,0,0,0,0,0,0,0],[1,1,1,1,1,1,0,1,1,0,1,2,2,2,2,2,2,1,0,1,1,0,1,1,1,1,1,1],[1,1,1,1,1,1,0,1,1,0,1,1,1,1,1,1,1,1,0,1,1,0,1,1,1,1,1,1],[1,1,1,1,1,1,0,1,1,0,0,0,0,0,0,0,0,0,0,1,1,0,1,1,1,1,1,1],[1,1,1,1,1,1,0,1,1,0,1,1,1,1,1,1,1,1,0,1,1,0,1,1,1,1,1,1],[1,1,1,1,1,1,0,1,1,0,1,1,1,1,1,1,1,1,0,1,1,0,1,1,1,1,1,1],[1,0,0,0,0,0,0,0,0,0,0,0,0,1,1,0,0,0,0,0,0,0,0,0,0,0,0,1],[1,0,1,1,1,1,0,1,1,1,1,1,0,1,1,0,1,1,1,1,1,0,1,1,1,1,0,1],[1,0,1,1,1,1,0,1,1,1,1,1,0,1,1,0,1,1,1,1,1,0,1,1,1,1,0,1],[1,0,0,0,1,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1,1,0,0,0,1],[1,1,1,0,1,1,0,1,1,0,1,1,1,1,1,1,1,1,0,1,1,0,1,1,0,1,1,1],[1,1,1,0,1,1,0,1,1,0,1,1,1,1,1,1,1,1,0,1,1,0,1,1,0,1,1,1],[1,0,0,0,0,0,0,1,1,0,0,0,0,1,1,0,0,0,0,1,1,0,0,0,0,0,0,1],[1,0,1,1,1,1,1,1,1,1,1,1,0,1,1,0,1,1,1,1,1,1,1,1,1,1,0,1],[1,0,1,1,1,1,1,1,1,1,1,1,0,1,1,0,1,1,1,1,1,1,1,1,1,1,0,1],[1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1],[1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1]],_GOODS = { //能量豆'1,3':1,'26,3':1,'1,23':1,'26,23':1},_COS = [1,0,-1,0],_SIN = [0,1,0,-1],_COLOR = ['#F00','#F93','#0CF','#F9C'],//紅,橙,_LIFE = 3,_SCORE = 0; //得分var game = new Game('canvas');//啟動頁(function(){var stage = game.createStage();//logostage.createItem({x:game.width/2,y:game.height*.45,width:100,height:100,frames:3,draw:function(context){var t = Math.abs(5-this.times%10);context.fillStyle = '#FFE600';context.beginPath();context.arc(this.x,this.y,this.width/2,t*.04*Math.PI,(2-t*.04)*Math.PI,false);context.lineTo(this.x,this.y);context.closePath();context.fill();context.fillStyle = '#000';context.beginPath();context.arc(this.x+5,this.y-27,7,0,2*Math.PI,false);context.closePath();context.fill();}});//游戲名stage.createItem({x:game.width/2,y:game.height*.6,draw:function(context){context.font = 'bold 42px Helvetica';context.textAlign = 'center';context.textBaseline = 'middle';context.fillStyle = '#FFF';context.fillText('Pac-Man',this.x,this.y);}});//版權信息stage.createItem({x:game.width-12,y:game.height-5,draw:function(context){context.font = '14px Helvetica';context.textAlign = 'right';context.textBaseline = 'bottom';context.fillStyle = '#AAA';context.fillText('? passer-by.com',this.x,this.y);}});//事件綁定stage.bind('keydown',function(e){switch(e.keyCode){case 13:case 32:game.nextStage();break;}});})();//游戲主程序(function(){var stage,map,beans,player,times;stage = game.createStage({update:function(){var stage = this;if(stage.status==1){ //場景正常運行items.forEach(function(item){if(map&&!map.get(item.coord.x,item.coord.y)&&!map.get(player.coord.x,player.coord.y)){var dx = item.x-player.x;var dy = item.y-player.y;if(dx*dx+dy*dy<750&&item.status!=4){ //物體檢測if(item.status==3){item.status = 4;_SCORE += 10;}else{stage.status = 3;stage.timeout = 30;}}}});if(JSON.stringify(beans.data).indexOf(0)<0){ //當沒有物品的時候,進入結束畫面game.nextStage();}}else if(stage.status==3){ //場景臨時狀態if(!stage.timeout){_LIFE--;if(_LIFE){stage.resetItems();}else{game.nextStage();return false;}}}}});//繪制地圖map = stage.createMap({x:60,y:10,data:_DATA,cache:true,draw:function(context){context.lineWidth = 2;for(var j=0; j<this.y_length; j++){for(var i=0; i<this.x_length; i++){var value = this.get(i,j);if(value){var code = [0,0,0,0];if(this.get(i+1,j)&&!(this.get(i+1,j-1)&&this.get(i+1,j+1)&&this.get(i,j-1)&&this.get(i,j+1))){code[0]=1;}if(this.get(i,j+1)&&!(this.get(i-1,j+1)&&this.get(i+1,j+1)&&this.get(i-1,j)&&this.get(i+1,j))){code[1]=1;}if(this.get(i-1,j)&&!(this.get(i-1,j-1)&&this.get(i-1,j+1)&&this.get(i,j-1)&&this.get(i,j+1))){code[2]=1;}if(this.get(i,j-1)&&!(this.get(i-1,j-1)&&this.get(i+1,j-1)&&this.get(i-1,j)&&this.get(i+1,j))){code[3]=1;}if(code.indexOf(1)>-1){context.strokeStyle=value==2?"#FFF":"#09C";var pos = this.coord2position(i,j);switch(code.join('')){case '1100':context.beginPath();context.arc(pos.x+this.size/2,pos.y+this.size/2,this.size/2,Math.PI,1.5*Math.PI,false);context.stroke();context.closePath();break;case '0110':context.beginPath();context.arc(pos.x-this.size/2,pos.y+this.size/2,this.size/2,1.5*Math.PI,2*Math.PI,false);context.stroke();context.closePath();break;case '0011':context.beginPath();context.arc(pos.x-this.size/2,pos.y-this.size/2,this.size/2,0,.5*Math.PI,false);context.stroke();context.closePath();break;case '1001':context.beginPath();context.arc(pos.x+this.size/2,pos.y-this.size/2,this.size/2,.5*Math.PI,1*Math.PI,false);context.stroke();context.closePath();break;default:var dist = this.size/2;code.forEach(function(v,index){if(v){context.beginPath();context.moveTo(pos.x,pos.y);context.lineTo(pos.x-_COS[index]*dist,pos.y-_SIN[index]*dist);context.stroke();context.closePath(); }});}}}}}}});//物品地圖beans = stage.createMap({x:60,y:10,data:_DATA,frames:8,draw:function(context){for(var j=0; j<this.y_length; j++){for(var i=0; i<this.x_length; i++){if(!this.get(i,j)){var pos = this.coord2position(i,j);context.fillStyle = "#F5F5DC";if(_GOODS[i+','+j]){context.beginPath();context.arc(pos.x,pos.y,3+this.times%2,0,2*Math.PI,true);context.fill();context.closePath();}else{context.fillRect(pos.x-2,pos.y-2,4,4);}}}}}});//得分stage.createItem({x:690,y:100,draw:function(context){context.font = 'bold 28px Helvetica';context.textAlign = 'left';context.textBaseline = 'bottom';context.fillStyle = '#C33';context.fillText('SCORE',this.x,this.y);context.font = '28px Helvetica';context.textAlign = 'left';context.textBaseline = 'top';context.fillStyle = '#FFF';context.fillText(_SCORE,this.x+12,this.y);}});//狀態文字stage.createItem({x:690,y:320,frames:25,draw:function(context){if(stage.status==2&&this.times%2){context.font = '24px Helvetica';context.textAlign = 'left';context.textBaseline = 'center';context.fillStyle = '#09F';context.fillText('PAUSE',this.x,this.y);}}});//生命值stage.createItem({x:705,y:540,width:30,height:30,draw:function(context){for(var i=0;i<_LIFE-1;i++){var x=this.x+40*i,y=this.y;context.fillStyle = '#FFE600';context.beginPath();context.arc(x,y,this.width/2,.15*Math.PI,-.15*Math.PI,false);context.lineTo(x,y);context.closePath();context.fill();}}});//NPCfor(var i=0;i<4;i++){stage.createItem({width:30,height:30,orientation:3,color:_COLOR[i],location:map,coord:{x:12+i,y:14},vector:{x:12+i,y:14},type:2,frames:10,speed:1,timeout:Math.floor(Math.random()*120),update:function(){var new_map;if(this.status==3&&!this.timeout){this.status = 1;}if(!this.coord.offset){ //到達坐標中心時計算if(this.status==1){if(!this.timeout){ //定時器new_map = JSON.parse(JSON.stringify(map.data).replace(/2/g,0));var id = this._id;items.forEach(function(item){if(item._id!=id&&item.status==1){ //NPC將其它所有還處于正常狀態的NPC當成一堵墻new_map[item.coord.y][item.coord.x]=1;}});this.path = map.finder({map:new_map,start:this.coord,end:player.coord});if(this.path.length){this.vector = this.path[0];}}}else if(this.status==3){new_map = JSON.parse(JSON.stringify(map.data).replace(/2/g,0));var id = this._id;items.forEach(function(item){if(item._id!=id){new_map[item.coord.y][item.coord.x]=1;}});this.path = map.finder({map:new_map,start:player.coord,end:this.coord,type:'next'});if(this.path.length){this.vector = this.path[Math.floor(Math.random()*this.path.length)];}}else if(this.status==4){new_map = JSON.parse(JSON.stringify(map.data).replace(/2/g,0));this.path = map.finder({map:new_map,start:this.coord,end:this._params.coord});if(this.path.length){this.vector = this.path[0];}else{this.status = 1;}}//是否轉變方向if(this.vector.change){this.coord.x = this.vector.x;this.coord.y = this.vector.y;var pos = map.coord2position(this.coord.x,this.coord.y);this.x = pos.x;this.y = pos.y;}//方向判定if(this.vector.x>this.coord.x){this.orientation = 0;}else if(this.vector.x<this.coord.x){this.orientation = 2;}else if(this.vector.y>this.coord.y){this.orientation = 1;}else if(this.vector.y<this.coord.y){this.orientation = 3;}}this.x += this.speed*_COS[this.orientation];this.y += this.speed*_SIN[this.orientation];},draw:function(context){var isSick = false;if(this.status==3){isSick = this.timeout>80||this.times%2?true:false;}if(this.status!=4){context.fillStyle = isSick?'#BABABA':this.color;context.beginPath();context.arc(this.x,this.y,this.width*.5,0,Math.PI,true);switch(this.times%2){case 0:context.lineTo(this.x-this.width*.5,this.y+this.height*.4);context.quadraticCurveTo(this.x-this.width*.4,this.y+this.height*.5,this.x-this.width*.2,this.y+this.height*.3);context.quadraticCurveTo(this.x,this.y+this.height*.5,this.x+this.width*.2,this.y+this.height*.3);context.quadraticCurveTo(this.x+this.width*.4,this.y+this.height*.5,this.x+this.width*.5,this.y+this.height*.4);break;case 1:context.lineTo(this.x-this.width*.5,this.y+this.height*.3);context.quadraticCurveTo(this.x-this.width*.25,this.y+this.height*.5,this.x,this.y+this.height*.3);context.quadraticCurveTo(this.x+this.width*.25,this.y+this.height*.5,this.x+this.width*.5,this.y+this.height*.3);break;}context.fill();context.closePath();}context.fillStyle = '#FFF';if(isSick){context.beginPath();context.arc(this.x-this.width*.15,this.y-this.height*.21,this.width*.08,0,2*Math.PI,false);context.arc(this.x+this.width*.15,this.y-this.height*.21,this.width*.08,0,2*Math.PI,false);context.fill();context.closePath();}else{context.beginPath();context.arc(this.x-this.width*.15,this.y-this.height*.21,this.width*.12,0,2*Math.PI,false);context.arc(this.x+this.width*.15,this.y-this.height*.21,this.width*.12,0,2*Math.PI,false);context.fill();context.closePath();context.fillStyle = '#000';context.beginPath();context.arc(this.x-this.width*(.15-.04*_COS[this.orientation]),this.y-this.height*(.21-.04*_SIN[this.orientation]),this.width*.07,0,2*Math.PI,false);context.arc(this.x+this.width*(.15+.04*_COS[this.orientation]),this.y-this.height*(.21-.04*_SIN[this.orientation]),this.width*.07,0,2*Math.PI,false);context.fill();context.closePath();}}});}items = stage.getItemsByType(2);//主角player = stage.createItem({width:30,height:30,type:1,location:map,coord:{x:13.5,y:23},orientation:2,speed:2,frames:10,update:function(){var coord = this.coord;if(!coord.offset){if(this.control.orientation!='undefined'){if(!map.get(coord.x+_COS[this.control.orientation],coord.y+_SIN[this.control.orientation])){this.orientation = this.control.orientation;}}this.control = {};var value = map.get(coord.x+_COS[this.orientation],coord.y+_SIN[this.orientation]);if(value==0){this.x += this.speed*_COS[this.orientation];this.y += this.speed*_SIN[this.orientation];}else if(value<0){this.x -= map.size*(map.x_length-1)*_COS[this.orientation];this.y -= map.size*(map.y_length-1)*_SIN[this.orientation];}}else{if(!beans.get(this.coord.x,this.coord.y)){ //吃豆_SCORE++;beans.set(this.coord.x,this.coord.y,1);if(_GOODS[this.coord.x+','+this.coord.y]){ //吃到能量豆items.forEach(function(item){if(item.status==1||item.status==3){ //如果NPC為正常狀態,則置為臨時狀態item.timeout = 450;item.status = 3;}});}}this.x += this.speed*_COS[this.orientation];this.y += this.speed*_SIN[this.orientation];}},draw:function(context){context.fillStyle = '#FFE600';context.beginPath();if(stage.status!=3){ //玩家正常狀態if(this.times%2){context.arc(this.x,this.y,this.width/2,(.5*this.orientation+.20)*Math.PI,(.5*this.orientation-.20)*Math.PI,false);}else{context.arc(this.x,this.y,this.width/2,(.5*this.orientation+.01)*Math.PI,(.5*this.orientation-.01)*Math.PI,false);}}else{ //玩家被吃if(stage.timeout) {context.arc(this.x,this.y,this.width/2,(.5*this.orientation+1-.02*stage.timeout)*Math.PI,(.5*this.orientation-1+.02*stage.timeout)*Math.PI,false);}}context.lineTo(this.x,this.y);context.closePath();context.fill();}});//事件綁定stage.bind('keydown',function(e){switch(e.keyCode){case 13: //回車case 32: //空格this.status = this.status==2?1:2;break;case 39: //右player.control = {orientation:0};break;case 40: //下player.control = {orientation:1};break;case 37: //左player.control = {orientation:2};break;case 38: //上player.control = {orientation:3};break;}});})();//結束畫面(function(){var stage = game.createStage();//游戲結束stage.createItem({x:game.width/2,y:game.height*.35,draw:function(context){context.fillStyle = '#FFF';context.font = 'bold 48px Helvetica';context.textAlign = 'center';context.textBaseline = 'middle';context.fillText('GAME OVER',this.x,this.y);}});//記分stage.createItem({x:game.width/2,y:game.height*.5,draw:function(context){context.fillStyle = '#FFF';context.font = '20px Helvetica';context.textAlign = 'center';context.textBaseline = 'middle';context.fillText('FINAL SCORE: '+(_SCORE+50*Math.max(_LIFE-1,0)),this.x,this.y);}});//事件綁定stage.bind('keydown',function(e){switch(e.keyCode){case 13: //回車case 32: //空格_SCORE = 0;_LIFE = 3;var st = game.setStage(1);st.reset();break;}});})();game.init();
})();
?