Jump to content

Extending Sprite with abstract classes?


Tilde
 Share

Recommended Posts

Hi! So I'm working on a game right now, despite not being all too savvy with javascript. Its current progress can be monitored here whenever I push a new update: http://www.hardmodeorders.com/slapspark/slapspark.html

 

First of all, sorry in advance if this isn't the appropriate place to ask for help.

 

Thanks to some helpful guides, I've already successfully made a player.js file that extends Phaser.Sprite and can be used in the game state. So right now, I'm trying to do the same with Enemy.js. The difference is, I want to have an abstract Enemy class that handles what most enemies have in common. So here is my attempt at that:

Enemy = function(game, x, y, enemyType) {  Phaser.Sprite.call(this, game, x, y, enemyType);  var hp = 1;  var followTarget = false;  var target;  var aggroRange;  var idleAnimation = false;  var idlePeriod = 4000;  var nextIdle = 0;  // AND THE REST    alert(enemyType);}Enemy.prototype = Object.create(Phaser.Sprite.prototype);Enemy.prototype.constructor = Enemy;Enemy.prototype.update = function() {  if (idleAnimation) {    if (this.game.time.time > nextIdle) {      sprite.animations.play('idle'), 14, false;      nextIdle = this.game.time.time + idlePeriod;    }  }  if (followTarget && target) {    this.rotation = game.physics.arcade.angleBetween(this, target);  }  Phaser.Sprite.prototype.update.call(this);}Enemy.prototype.setTarget = function(t) {  target = t;}Enemy.prototype.damage = function() {}Blaad = function(gameS, xS, yS) {  Object.create(Enemy.prototype);  Enemy.apply(this, [gameS, xS, yS, 'blaad']);  this.game = gameS;  this.x = xS;  this.y = yS;  this.idleAnimation = true;  this.animations.add('idle');}WallEnemy = function(gameS, xS, yS) {  Object.create(Enemy.prototype);  Enemy.apply(this, [gameS, xS, yS, 'wallEnemy']);  this.game = gameS;  this.x = xS;  this.y = yS;  this.followTarget = true;}

This doesn't work, and when used like such in the Level game state,

wallEnemy = new WallEnemy(this, 200, 60);wallEnemy.setTarget(player);this.add.existing(wallEnemy);

I get the error "Uncaught TypeError: this.onTextureUpdate is not a function" from phaser.js:1454. Is what I'm trying to do feasible/appropriate?

Link to comment
Share on other sites

Maybe I'm about to say something stupid but I think you shouldn't override the update() function... This is the base update function of the sprite object, I can't quite see how Phaser will update it if you overwrite it.

 

What I would do, for the rest, is create the Enemy class like it is not 'abstract', and have childs of it. I get that you might want to prevent the instantiation of an Enemy, and maybe there are mechanisms to throw an exception if that happens, but making your Enemy a very normal class might make things easier.

 

But I'm no pro at JS. :(

Link to comment
Share on other sites

Ignore my previous comment. I didn't read your code carefully.

 

try this:

var wallEnemy = function(gameS, xS, yS){	Enemy.call(this, gameS, xS, yS, 'wallEnemy');	this.game = gameS;	this.x = xS;	this.y = yS;	this.followTarget = true;};wallEnemy.prototype = Object.create(Enemy.prototype);wallEnemy.prototype.constructor = wallEnemy;
Link to comment
Share on other sites

You've almost got this, you just need to change a couple of things. This line:

Phaser.Sprite.call(this, game, x, y, enemyType);

... should be the first line in your constructor. It allows Phaser to set up all of its properties first. Then, immediately after your constructor function you need a couple of lines like this:

Enemy.prototype = Object.create(Phaser.Sprite.prototype);Enemy.prototype.constructor = Enemy;

This sets up the prototype chain in JS for your objects. This is *kind of* like virtual methods in C++. You'll need the same setup for your own derived classes, except they will call "Object.create(Enemy.prototype);" instead.

 

If you override the update method you'll need a line that looks like this in there:

Phaser.Sprite.prototype.update.call(this);

That will call the "parent" method on Sprite. For the record, Phaser doesn't do anything in the Sprite's "update" method but it's an okay habit to get into when setting up inheritance chains in JS.

Link to comment
Share on other sites

Hey guys, thanks for the replies. I did what you said, but as you can see, I've already got the prototype lines set up after the constructor. I rearranged the stuff you told me to, but I've still got the same error. Interestingly, I didn't think to have that parent updater in the Player class either, but it still works without calling it. From what I can tell (and I'm not totally sure about this but it seems to be the case), Update is called on onscreen Sprites automatically despite them having nothing in that function, implying that they're meant to be overridden with whatever behavior you want. But I could be totally wrong about that. Either way, it's not making the Enemy class work.

 

Original post has been edited to reflect current code.

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...