Jump to content

Some OOP technique in Phaser


Raiper34
 Share

Recommended Posts

Hi, 

 

I am new in Phaser and I working with OOP in Java some month ago, I would like to use OOP in Phaser too, because i think OOP is very good for games, so my question is, is it possible? I want to make one js files only with player and his actions/functions... I am a bit confused, yes i newer worked with pure js but i know, that there is no clases.... but how in Phaser? Can you give me any example please?

Link to comment
Share on other sites

If you are willing to try something new, take a look at TypeScript. It works very well with Phaser. The type definitions are missing a few things here and there, but things are generally fine.

TS aims to make JS more manageable. As TS is a superset of JS, all JS code is valid in TS, but TS also adds classes, interfaces, enums and a few other things that make life easier. I've been writing in TS for half a year now and I don't want to look at JS code any more.

Link to comment
Share on other sites

I would like to use OOP in Phaser too, because i think OOP is very good for games, so my question is, is it possible? 

JavaScript is an object-oriented language, just like Java.

So, all the code you write for Phaser is already OOP code.

But JavaScript is a very different language than Java.

Are there features in Java that you're looking in JavaScript that you can't find?

If you can describe them, we'll be able to tell you how to implement them.

Link to comment
Share on other sites

Look inside Phaser source file and observe how it defines JS-style classes with inheritance. See Phaser.Image extending PIXI.Sprite, for example.

 

Especially take notice of this construct:

ChildClass.prototype = Object.create (ParentClass.prototype);ChildClass.prototype.constructor = ChildClass;
Link to comment
Share on other sites

Here is an OOP example from my game.  I want to have a base unit type that is a sprite.

function Unit(game, x, y, spriteName) {   
	Phaser.Sprite.call(this, game, x, y, 'units', spriteName);   
	// base unit stuff goes here
}
Unit.prototype = Object.create(Phaser.Sprite.prototype);
Unit.prototype.constructor = Unit;

Now I want to define a soldier that extends Unit.

function Soldier (game, x, y, team, spriteName) {   
	this.team = team;   
	Unit.call(this, game, x, y, spriteName);
}
Soldier.prototype = Object.create(Unit.prototype);
Soldier.prototype.constructor = Soldier;
Soldier.prototype.lookForTargets = function() {   
	// code to look for targets
};
// override the Sprite.update function
Soldier.prototype.update = function() {   
	this.lookForTargets();   
	// now execute the base class handlers for update()   
	Unit.prototype.update.call(this);
};

Now I could add a Tank, Airplane, etc that all extend Unit.  I could also add a Sniper that extends Soldier.  You get the picture.

Link to comment
Share on other sites

Javascript uses prototypal inheritance. If you're new to the language I highly recommend learning about how what the prototype chain is and how it works and watching Douglas Crockford's videos about the language (https://www.youtube.com/playlist?list=PL7664379246A246CB).

 

@sanojian 's example is the most common way to do inheritance in js but the language is very flexible so there are many ways to end up with the object you want. 

 

Using Typescript will give you an experience very close to other classical OOP languages but you should still now how the language the typescript compiler is targeting works. 

Link to comment
Share on other sites

Using OOP in JavaScript is just a matter of organization, architecture, and discipline. JS gives you all the tools you need to build object-oriented code, it just doesn't enforce many of the principles by itself, so you need to use good practices and be consistent. That's always more important for a well-written program anyway.

 

If you are looking for compiler/interpreter-enforced elements like private member variables, take a look at Object.defineProperty.

 

It's a little awkward, but it gives you more control over how certain elements can be interacted with.

 

I also recommend Douglas Crockford's JavaScript: The Good Parts. JavaScript is kind of a Frankenstein's language. Crockford does a very good job of explaining why things are the way they are and how you should use JavaScript to take advantage of its perks while avoiding the bad parts that will make your code hard to handle.

 

You can probably find resources online, by Crockford or others. I just like the book, it's very well-written.

Link to comment
Share on other sites

Good to know Javascript well, but Typescript increases productivity and helps you to prevent errors (especially in large projects). You also get intellisense and if you code under Windows, then you can have this all with luxury Visual Studio 2013 (2015). Typescript is developed by the same smart guy who came with C# (Anders Hejlsberg) ...

Link to comment
Share on other sites

You can use the "new" keyword like you would in any other OOP language.

 

You first have to construct a prototype object with a constructor function that JavaScript recognizes as a constructor (otherwise you will get a runtime error using "new"). Red Spark's post shows you how.

 

1. Define your constructor function, giving it the name of the object class you want to create.

2. Give your constructor function a prototype object. This should be the superclass of the object you want to make (the class your class inherits from). Use Object.prototype if you don't want to inherit from anything.

3. Set the special variable constructor in your prototype object to your constructor function from #1. This tells the "new" keyword what to use to set up your new object.

 

This example is completely Phaser-independent. Doing it in Phaser is identical to doing it in JavaScript (though of course the content of your constructor will interact with elements of Phaser).

 SampleObject  = function(x,y) {      this.x = x;      this.y = y;      return this;}; //1 SampleObject.prototype = Object.create(Object.prototype); //2SampleObject.prototype.constructor = SampleObject; //3 var instance1 = new SampleObject(0,0);var instance2 = new SampleObject(8,55);
Link to comment
Share on other sites

 

You can use the "new" keyword like you would in any other OOP language.

 

You first have to construct a prototype object with a constructor function that JavaScript recognizes as a constructor (otherwise you will get a runtime error using "new"). Red Spark's post shows you how.

 

1. Define your constructor function, giving it the name of the object class you want to create.

2. Give your constructor function a prototype object. This should be the superclass of the object you want to make (the class your class inherits from). Use Object.prototype if you don't want to inherit from anything.

3. Set the special variable constructor in your prototype object to your constructor function from #1. This tells the "new" keyword what to use to set up your new object.

 

This example is completely Phaser-independent. Doing it in Phaser is identical to doing it in JavaScript (though of course the content of your constructor will interact with elements of Phaser).

 SampleObject  = function(x,y) {      this.x = x;      this.y = y;      return this;}; //1 SampleObject.prototype = Object.create(Object.prototype); //2SampleObject.prototype.constructor = SampleObject; //3 var instance1 = new SampleObject(0,0);var instance2 = new SampleObject(8,55);

Thanks i will try it, but can you clarify me what exactly this line mean? SampleObject.prototype = Object.create(Object.prototype); //2

edit: sorry i see it, i was tired only... thanks very much :)

Link to comment
Share on other sites

Thanks i understand it now, but i have one problem 

Objectron = function Objectron(game, x, y) {   Phaser.Sprite.call(this, game, x, y, 'character');   game.add.existing(this);};Objectron.prototype.update = function(){    this.angle += 5;};Objectron.prototype = Object.create(Phaser.Sprite.prototype);Objectron.prototype.constructor = Objectron;

Why angle does not work? when i call it via created object object.angle += 5; then it is working, but i do not like it, i want to do it this way....

Link to comment
Share on other sites

Thanks i understand it now, but i have one problem 

Objectron = function Objectron(game, x, y) {   Phaser.Sprite.call(this, game, x, y, 'character');   game.add.existing(this);};Objectron.prototype.update = function(){    this.angle += 5;};Objectron.prototype = Object.create(Phaser.Sprite.prototype);Objectron.prototype.constructor = Objectron;

Why angle does not work? when i call it via created object object.angle += 5; then it is working, but i do not like it, i want to do it this way....

 

I don't see anything wrong here. Angle shoud be incrementing by 5 on every update. It works just like in the example Tom Atom mentioned. 

 

Update: wait. There is something wrong. You are defining Objectrong.prototype.update and later you replace Objectron.protoype completely. 

 

Do 

Objectron.prototype = Object.create(Phaser.Sprite.prototype);

 before adding anything new to Objectron.prototype

Objectron = function Objectron(game, x, y) {Phaser.Sprite.call(this, game, x, y, 'character');game.add.existing(this);};Objectron.prototype = Object.create(Phaser.Sprite.prototype);Objectron.prototype.constructor = Objectron;Objectron.prototype.update = function(){this.angle += 5;};

Variables for objects in javascript contain just a reference to an object. At first you Objectron.prototype refers to an object that has an update property. 

After "Objectron.prototype = Object.create(Phaser.Sprite.prototype);" Objectron.prototype no longer holds a reference to the object with the update property you defined. It now instead holds a reference to the object that Object.create() returned. 

 

An easy example with arrays would be:

var a = []; //a refers to an object containing an empty arraya[3] = "hello"; //get the object a refers to and make the third position contain "hello"a = [3,4,5]; //a refers to a *new* object containing [3,4,5]console.log(a);

The output will be [3,4,5] and not [3,4,5,"hello"]. 

Link to comment
Share on other sites

Join the conversation

You can post now and register later. If you have an account, sign in now to post with your account.
Note: Your post will require moderator approval before it will be visible.

Guest
Reply to this topic...

×   Pasted as rich text.   Paste as plain text instead

  Only 75 emoji are allowed.

×   Your link has been automatically embedded.   Display as a link instead

×   Your previous content has been restored.   Clear editor

×   You cannot paste images directly. Upload or insert images from URL.

Loading...
 Share

  • Recently Browsing   0 members

    • No registered users viewing this page.
×
×
  • Create New...