Sabtu, 16 Februari 2013

Simple way to start html5 canvas game


redship.png:

example.js:



var renderer = null;
var sprites = null;
var FPS = 60;


function init(canvas, tex)
{
this.renderer = new KOEN2D.Renderer(canvas);
var a = [];
var p2 = Math.PI * 2;
var s;
for (var i = 0; i < 2000; i++){
a.push(new KOEN2D.Sprite());
a[i].name = "sprite" + i.toString();
a[i].image = tex;
a[i].position.x = Math.random() * 500 + 50;
a[i].position.y = Math.random() * 300 + 50;
a[i].rotation = Math.random() * p2;
a[i].vector.x = Math.cos(a[i].rotation);
a[i].vector.y = Math.sin(a[i].rotation);
a[i].scaleX = 0.25;
a[i].scaleY = 0.25;
a[i].speed = Math.random() * 5 + 1;
console.log(a[i].name + " x " + a[i].position.x);
}
this.sprites = a;
window.setInterval(this.step, FPS);
};


function step(e)
{
if (this.sprites.length == 0) return;
for (var i = 0; i < this.sprites.length; i++){ this.stepSprite(this.sprites[i]); }
renderer.render(this.sprites);
};


function stepSprite(o)
{
var rotChange = false;
o.position.x += (o.vector.x * o.speed);
o.position.y += (o.vector.y * o.speed);


if (o.position.x > 695 || o.position.x < 25){
o.vector.x *= -1;
o.position.x += (o.vector.x * o.speed * 2);
rotChange = true;
}
if (o.position.y > 375 || o.position.y < 25){
o.vector.y *= -1;
o.position.y += (o.vector.y * o.speed * 2);
rotChange = true;
}
if (rotChange){
o.rotation = Math.atan2(o.vector.y, o.vector.x);
}
};


var tex = new Image();
tex.src = "res/redship.png";
tex.onload = function(){init(document.getElementById("myCanvas"), tex);};

koen2d.js:




( function () {



var lastTime = 0;
var vendors = [ 'ms', 'moz', 'webkit', 'o' ];



for ( var x = 0; x < vendors.length && !window.requestAnimationFrame; ++ x ) {



window.requestAnimationFrame = window[ vendors[ x ] + 'RequestAnimationFrame' ];
window.cancelAnimationFrame = window[ vendors[ x ] + 'CancelAnimationFrame' ] || window[ vendors[ x ] + 'CancelRequestAnimationFrame' ];
}



if ( !window.requestAnimationFrame ) {



window.requestAnimationFrame = function ( callback, element ) {
var currTime = Date.now(), timeToCall = Math.max( 0, 16 - ( currTime - lastTime ) );
var id = window.setTimeout( function() { callback( currTime + timeToCall ); }, timeToCall );
lastTime = currTime + timeToCall;
return id;
};
}

if ( !window.cancelAnimationFrame ) {
window.cancelAnimationFrame = function ( id ) { clearTimeout( id ); };
}
}() );

var KOEN2D = KOEN2D || {
VERSION: '2013_1.0',
P180:Math.PI / 180,
PROUND:Math.PI * 2,
lastID:0
};

// Point

KOEN2D.Point = function(xx, yy)
{
this.name = "point" + (KOEN2D.lastID++);
this.x = xx;
this.y = yy;
};
KOEN2D.Point.prototype = {
constructor:KOEN2D.Point,
name:'',
x:0,
y:0
};
KOEN2D.Point.add = function(p1, p2) {
return new KOEN2D.Point(p1.x + p2.x, p1.y + p2.y);
};
KOEN2D.Point.angle = function(p1, p2) {
var dx = p1.x - p1.x;
var dy = p2.y - p1.y;
return Math.atan2(dy, dx);
};
KOEN2D.Point.clone = function(p) {
return new KOEN2D.Point(p.x, p.y);
};
KOEN2D.Point.distance = function(p1, p2) {
var dx = p1.x - p1.x;
var dy = p2.y - p1.y;
return Math.sqrt(dx * dx + dy * dy);
};
KOEN2D.Point.multiply = function(p, n) {
return new KOEN2D.Point(p.x * n, p.y * n);
};
KOEN2D.Point.normalize = function(p) {
var d = Math.sqrt(p.x * p.x + p.y * p.y);
if (d > 1)
{
p.x /= d;
p.y /= d;
}
};
KOEN2D.Point.subtract = function(p1, p2) {
return new KOEN2D.Point(p1.x - p2.x, p1.y - p2.y);
};

KOEN2D.Renderer = function(canvas){
this.canvas = canvas;
this.context = canvas.getContext("2d");
};
KOEN2D.Renderer.prototype = {
constructor:KOEN2D.Renderer,
canvas:null,
context:null,
render:function(a)
{
this.context.fillStyle = "#333333";
this.context.fillRect(0, 0, this.canvas.width, this.canvas.height);
//sprites.sortOn("y", Array:NUMERIC);
//a.sort(function(a,b) {return (a.y > b.y) ? 1 : 0; });

for (var i = 0; i < a.length; i++) { this.renderItem(this.context, a[i]); }
},
renderItem:function(c, o)
{
c.save();
c.translate(o.position.x, o.position.y);
c.scale(o.scaleX, o.scaleY);
c.rotate(o.rotation);
c.drawImage(o.image, -o.image.width * 0.5, -o.image.height * 0.5);
c.restore();
}
}

// rotation in rad;
KOEN2D.Sprite = function(){
this.name = "sprite_" + (KOEN2D.lastID++);
this.position = new KOEN2D.Point(0, 0);
this.vector = new KOEN2D.Point(0, 0);
// why defining object in prototype will cause single object for every new object?
};
KOEN2D.Sprite.prototype = {
constructor:KOEN2D.Sprite,
name:'',
position:null,
rotation:0,
vector:null,
scaleX:1.0,
scaleY:1.0,
speed:0.0,
image:null,
data:null,
dispose:function(){
this.image = null;
this.data = null;
}
};

The html body contain canvas with id mycanvas.
The footer inlcudes js/example.js and js/koen2d.js.

That's all. Look at the speed. I can put more than 3000 sprites in chrome!.

Tidak ada komentar:

Posting Komentar