Initial commit.
This commit is contained in:
BIN
src/dk/itu/mario/engine/sprites/.DS_Store
vendored
Normal file
BIN
src/dk/itu/mario/engine/sprites/.DS_Store
vendored
Normal file
Binary file not shown.
152
src/dk/itu/mario/engine/sprites/BulletBill.java
Normal file
152
src/dk/itu/mario/engine/sprites/BulletBill.java
Normal file
@@ -0,0 +1,152 @@
|
||||
package dk.itu.mario.engine.sprites;
|
||||
|
||||
|
||||
import dk.itu.mario.engine.Art;
|
||||
import dk.itu.mario.scene.LevelScene;
|
||||
|
||||
|
||||
public class BulletBill extends Sprite
|
||||
{
|
||||
private int width = 4;
|
||||
int height = 24;
|
||||
|
||||
private LevelScene world;
|
||||
public int facing;
|
||||
|
||||
public boolean avoidCliffs = false;
|
||||
public int anim;
|
||||
|
||||
public boolean dead = false;
|
||||
private int deadTime = 0;
|
||||
|
||||
|
||||
public BulletBill(LevelScene world, float x, float y, int dir)
|
||||
{
|
||||
sheet = Art.enemies;
|
||||
|
||||
this.x = x;
|
||||
this.y = y;
|
||||
this.world = world;
|
||||
xPicO = 8;
|
||||
yPicO = 31;
|
||||
|
||||
height = 12;
|
||||
facing = 0;
|
||||
wPic = 16;
|
||||
yPic = 5;
|
||||
|
||||
xPic = 0;
|
||||
ya = -5;
|
||||
this.facing = dir;
|
||||
}
|
||||
|
||||
public void collideCheck()
|
||||
{
|
||||
if (dead) return;
|
||||
|
||||
float xMarioD = world.mario.x - x;
|
||||
float yMarioD = world.mario.y - y;
|
||||
float w = 16;
|
||||
if (xMarioD > -16 && xMarioD < 16)
|
||||
{
|
||||
if (yMarioD > -height && yMarioD < world.mario.height)
|
||||
{
|
||||
if (world.mario.ya > 0 && yMarioD <= 0 && (!world.mario.onGround || !world.mario.wasOnGround))
|
||||
{
|
||||
world.mario.stomp(this);
|
||||
dead = true;
|
||||
|
||||
xa = 0;
|
||||
ya = 1;
|
||||
deadTime = 100;
|
||||
}
|
||||
else
|
||||
{
|
||||
world.mario.getHurt(this);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public void move()
|
||||
{
|
||||
if (deadTime > 0)
|
||||
{
|
||||
deadTime--;
|
||||
|
||||
if (deadTime == 0)
|
||||
{
|
||||
deadTime = 1;
|
||||
for (int i = 0; i < 8; i++)
|
||||
{
|
||||
world.addSprite(new Sparkle((int) (x + Math.random() * 16 - 8) + 4, (int) (y - Math.random() * 8) + 4, (float) (Math.random() * 2 - 1), (float) Math.random() * -1, 0, 1, 5));
|
||||
}
|
||||
spriteContext.removeSprite(this);
|
||||
}
|
||||
|
||||
x += xa;
|
||||
y += ya;
|
||||
ya *= 0.95;
|
||||
ya += 1;
|
||||
|
||||
return;
|
||||
}
|
||||
|
||||
float sideWaysSpeed = 4f;
|
||||
|
||||
xa = facing * sideWaysSpeed;
|
||||
xFlipPic = facing == -1;
|
||||
move(xa, 0);
|
||||
}
|
||||
|
||||
private boolean move(float xa, float ya)
|
||||
{
|
||||
x += xa;
|
||||
return true;
|
||||
}
|
||||
|
||||
public boolean fireballCollideCheck(Fireball fireball)
|
||||
{
|
||||
if (deadTime != 0) return false;
|
||||
|
||||
float xD = fireball.x - x;
|
||||
float yD = fireball.y - y;
|
||||
|
||||
if (xD > -16 && xD < 16)
|
||||
{
|
||||
if (yD > -height && yD < fireball.height)
|
||||
{
|
||||
return true;
|
||||
}
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
public boolean shellCollideCheck(Shell shell)
|
||||
{
|
||||
if (deadTime != 0) return false;
|
||||
|
||||
float xD = shell.x - x;
|
||||
float yD = shell.y - y;
|
||||
|
||||
if (xD > -16 && xD < 16)
|
||||
{
|
||||
if (yD > -height && yD < shell.height)
|
||||
{
|
||||
world.sound.play(Art.samples[Art.SAMPLE_MARIO_KICK], this, 1, 1, 1);
|
||||
|
||||
dead = true;
|
||||
|
||||
xa = 0;
|
||||
ya = 1;
|
||||
deadTime = 100;
|
||||
|
||||
if(world.recorder != null)
|
||||
world.recorder.shellKillRecord(this);
|
||||
|
||||
return true;
|
||||
}
|
||||
}
|
||||
return false;
|
||||
}
|
||||
}
|
||||
41
src/dk/itu/mario/engine/sprites/CoinAnim.java
Normal file
41
src/dk/itu/mario/engine/sprites/CoinAnim.java
Normal file
@@ -0,0 +1,41 @@
|
||||
package dk.itu.mario.engine.sprites;
|
||||
|
||||
import dk.itu.mario.engine.Art;
|
||||
import dk.itu.mario.level.Level;
|
||||
|
||||
|
||||
|
||||
public class CoinAnim extends Sprite
|
||||
{
|
||||
private int life = 10;
|
||||
|
||||
public CoinAnim(int xTile, int yTile)
|
||||
{
|
||||
sheet = Art.level;
|
||||
wPic = hPic = 16;
|
||||
|
||||
x = xTile * 16;
|
||||
y = yTile * 16 - 16;
|
||||
xa = 0;
|
||||
ya = -6f;
|
||||
xPic = 0;
|
||||
yPic = 2;
|
||||
}
|
||||
|
||||
public void move()
|
||||
{
|
||||
if (life-- < 0)
|
||||
{
|
||||
Sprite.spriteContext.removeSprite(this);
|
||||
for (int xx = 0; xx < 2; xx++)
|
||||
for (int yy = 0; yy < 2; yy++)
|
||||
Sprite.spriteContext.addSprite(new Sparkle((int)x + xx * 8 + (int) (Math.random() * 8), (int)y + yy * 8 + (int) (Math.random() * 8), 0, 0, 0, 2, 5));
|
||||
}
|
||||
|
||||
xPic = life & 3;
|
||||
|
||||
x += xa;
|
||||
y += ya;
|
||||
ya += 1;
|
||||
}
|
||||
}
|
||||
443
src/dk/itu/mario/engine/sprites/Enemy.java
Normal file
443
src/dk/itu/mario/engine/sprites/Enemy.java
Normal file
@@ -0,0 +1,443 @@
|
||||
package dk.itu.mario.engine.sprites;
|
||||
|
||||
import java.awt.Graphics;
|
||||
|
||||
|
||||
import dk.itu.mario.engine.Art;
|
||||
import dk.itu.mario.level.Level;
|
||||
import dk.itu.mario.scene.LevelScene;
|
||||
|
||||
|
||||
|
||||
public class Enemy extends Sprite
|
||||
{
|
||||
public static final int ENEMY_RED_KOOPA = 0;
|
||||
public static final int ENEMY_GREEN_KOOPA = 1;
|
||||
public static final int ENEMY_GOOMBA = 2;
|
||||
public static final int ENEMY_SPIKY = 3;
|
||||
public static final int ENEMY_FLOWER = 4;
|
||||
|
||||
private static float GROUND_INERTIA = 0.89f;
|
||||
private static float AIR_INERTIA = 0.89f;
|
||||
|
||||
private float runTime;
|
||||
private boolean onGround = false;
|
||||
private boolean mayJump = false;
|
||||
private int jumpTime = 0;
|
||||
private float xJumpSpeed;
|
||||
private float yJumpSpeed;
|
||||
|
||||
int width = 4;
|
||||
int height = 24;
|
||||
|
||||
private LevelScene world;
|
||||
public int facing;
|
||||
public int deadTime = 0;
|
||||
public boolean flyDeath = false;
|
||||
|
||||
public boolean avoidCliffs = true;
|
||||
public int type;
|
||||
|
||||
public boolean winged = true;
|
||||
private int wingTime = 0;
|
||||
|
||||
public boolean noFireballDeath;
|
||||
|
||||
public Enemy(LevelScene world, int x, int y, int dir, int type, boolean winged)
|
||||
{
|
||||
this.type = type;
|
||||
sheet = Art.enemies;
|
||||
this.winged = winged;
|
||||
|
||||
|
||||
this.world = world;
|
||||
this.x = x;
|
||||
this.y = y;
|
||||
|
||||
xPicO = 8;
|
||||
yPicO = 31;
|
||||
|
||||
avoidCliffs = type == Enemy.ENEMY_RED_KOOPA;
|
||||
|
||||
noFireballDeath = type == Enemy.ENEMY_SPIKY;
|
||||
|
||||
yPic = type;
|
||||
if (yPic > 1) height = 12;
|
||||
facing = dir;
|
||||
if (facing == 0) facing = 1;
|
||||
this.wPic = 16;
|
||||
}
|
||||
|
||||
public void collideCheck()
|
||||
{
|
||||
if (deadTime != 0)
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
float xMarioD = world.mario.x - x;
|
||||
float yMarioD = world.mario.y - y;
|
||||
float w = 16;
|
||||
|
||||
//if the distance to mario is within the sprite (in x)
|
||||
if (xMarioD > -width*2-4 && xMarioD < width*2+4)
|
||||
{
|
||||
//if the distance to mario is within the sprite (in y)
|
||||
if (yMarioD > -height && yMarioD < world.mario.height)
|
||||
{
|
||||
if (type != Enemy.ENEMY_SPIKY && world.mario.ya > 0 && yMarioD <= 0 && (!world.mario.onGround || !world.mario.wasOnGround))
|
||||
{
|
||||
world.mario.stomp(this);
|
||||
|
||||
if (winged)
|
||||
{
|
||||
winged = false;
|
||||
ya = 0;
|
||||
}
|
||||
else
|
||||
{
|
||||
this.yPicO = 31 - (32 - 8);
|
||||
hPic = 8;
|
||||
if (spriteTemplate != null) spriteTemplate.isDead = true;
|
||||
deadTime = 10;
|
||||
winged = false;
|
||||
|
||||
if (type == Enemy.ENEMY_RED_KOOPA)
|
||||
{
|
||||
spriteContext.addSprite(new Shell(world, x, y, 0));
|
||||
}
|
||||
else if (type == Enemy.ENEMY_GREEN_KOOPA)
|
||||
{
|
||||
spriteContext.addSprite(new Shell(world, x, y, 1));
|
||||
}
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
world.mario.getHurt(this);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public void move()
|
||||
{
|
||||
//TODO: some kind of suicide error when one enemy is created
|
||||
if (y > world.level.getHeight() * 16 + 16 && deadTime <= 0)
|
||||
{
|
||||
if(world.recorder != null)
|
||||
world.recorder.killSuicideRecord(this);
|
||||
|
||||
deadTime = 1;
|
||||
}
|
||||
|
||||
wingTime++;
|
||||
if (deadTime > 0)
|
||||
{
|
||||
deadTime--;
|
||||
|
||||
if (deadTime == 0)
|
||||
{
|
||||
deadTime = 1;
|
||||
for (int i = 0; i < 8; i++)
|
||||
{
|
||||
world.addSprite(new Sparkle((int) (x + Math.random() * 16 - 8) + 4, (int) (y - Math.random() * 8) + 4, (float) (Math.random() * 2 - 1), (float) Math.random() * -1, 0, 1, 5));
|
||||
}
|
||||
spriteContext.removeSprite(this);
|
||||
}
|
||||
|
||||
if (flyDeath)
|
||||
{
|
||||
x += xa;
|
||||
y += ya;
|
||||
ya *= 0.95;
|
||||
ya += 1;
|
||||
}
|
||||
return;
|
||||
}
|
||||
|
||||
|
||||
float sideWaysSpeed = 1.75f;
|
||||
// float sideWaysSpeed = onGround ? 2.5f : 1.2f;
|
||||
|
||||
if (xa > 2)
|
||||
{
|
||||
facing = 1;
|
||||
}
|
||||
if (xa < -2)
|
||||
{
|
||||
facing = -1;
|
||||
}
|
||||
|
||||
xa = facing * sideWaysSpeed;
|
||||
|
||||
mayJump = (onGround);
|
||||
|
||||
xFlipPic = facing == -1;
|
||||
|
||||
runTime += (Math.abs(xa)) + 5;
|
||||
|
||||
int runFrame = ((int) (runTime / 20)) % 2;
|
||||
|
||||
if (!onGround)
|
||||
{
|
||||
runFrame = 1;
|
||||
}
|
||||
|
||||
|
||||
if (!move(xa, 0)) facing = -facing;
|
||||
onGround = false;
|
||||
move(0, ya);
|
||||
|
||||
ya *= winged ? 0.95f : 0.85f;
|
||||
if (onGround)
|
||||
{
|
||||
xa *= GROUND_INERTIA;
|
||||
}
|
||||
else
|
||||
{
|
||||
xa *= AIR_INERTIA;
|
||||
}
|
||||
|
||||
if (!onGround)
|
||||
{
|
||||
if (winged)
|
||||
{
|
||||
ya += 0.6f;
|
||||
}
|
||||
else
|
||||
{
|
||||
ya += 2;
|
||||
}
|
||||
}
|
||||
else if (winged)
|
||||
{
|
||||
ya = -10;
|
||||
}
|
||||
|
||||
if (winged) runFrame = wingTime / 4 % 2;
|
||||
|
||||
xPic = runFrame;
|
||||
}
|
||||
|
||||
private boolean move(float xa, float ya)
|
||||
{
|
||||
while (xa > 8)
|
||||
{
|
||||
if (!move(8, 0)) return false;
|
||||
xa -= 8;
|
||||
}
|
||||
while (xa < -8)
|
||||
{
|
||||
if (!move(-8, 0)) return false;
|
||||
xa += 8;
|
||||
}
|
||||
while (ya > 8)
|
||||
{
|
||||
if (!move(0, 8)) return false;
|
||||
ya -= 8;
|
||||
}
|
||||
while (ya < -8)
|
||||
{
|
||||
if (!move(0, -8)) return false;
|
||||
ya += 8;
|
||||
}
|
||||
|
||||
boolean collide = false;
|
||||
if (ya > 0)
|
||||
{
|
||||
if (isBlocking(x + xa - width, y + ya, xa, 0)) collide = true;
|
||||
else if (isBlocking(x + xa + width, y + ya, xa, 0)) collide = true;
|
||||
else if (isBlocking(x + xa - width, y + ya + 1, xa, ya)) collide = true;
|
||||
else if (isBlocking(x + xa + width, y + ya + 1, xa, ya)) collide = true;
|
||||
}
|
||||
if (ya < 0)
|
||||
{
|
||||
if (isBlocking(x + xa, y + ya - height, xa, ya)) collide = true;
|
||||
else if (collide || isBlocking(x + xa - width, y + ya - height, xa, ya)) collide = true;
|
||||
else if (collide || isBlocking(x + xa + width, y + ya - height, xa, ya)) collide = true;
|
||||
}
|
||||
if (xa > 0)
|
||||
{
|
||||
if (isBlocking(x + xa + width, y + ya - height, xa, ya)) collide = true;
|
||||
if (isBlocking(x + xa + width, y + ya - height / 2, xa, ya)) collide = true;
|
||||
if (isBlocking(x + xa + width, y + ya, xa, ya)) collide = true;
|
||||
|
||||
if (avoidCliffs && onGround && !world.level.isBlocking((int) ((x + xa + width) / 16), (int) ((y) / 16 + 1), xa, 1)) collide = true;
|
||||
}
|
||||
if (xa < 0)
|
||||
{
|
||||
if (isBlocking(x + xa - width, y + ya - height, xa, ya)) collide = true;
|
||||
if (isBlocking(x + xa - width, y + ya - height / 2, xa, ya)) collide = true;
|
||||
if (isBlocking(x + xa - width, y + ya, xa, ya)) collide = true;
|
||||
|
||||
if (avoidCliffs && onGround && !world.level.isBlocking((int) ((x + xa - width) / 16), (int) ((y) / 16 + 1), xa, 1)) collide = true;
|
||||
}
|
||||
|
||||
if (collide)
|
||||
{
|
||||
if (xa < 0)
|
||||
{
|
||||
x = (int) ((x - width) / 16) * 16 + width;
|
||||
this.xa = 0;
|
||||
}
|
||||
if (xa > 0)
|
||||
{
|
||||
x = (int) ((x + width) / 16 + 1) * 16 - width - 1;
|
||||
this.xa = 0;
|
||||
}
|
||||
if (ya < 0)
|
||||
{
|
||||
y = (int) ((y - height) / 16) * 16 + height;
|
||||
jumpTime = 0;
|
||||
this.ya = 0;
|
||||
}
|
||||
if (ya > 0)
|
||||
{
|
||||
y = (int) (y / 16 + 1) * 16 - 1;
|
||||
onGround = true;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
else
|
||||
{
|
||||
x += xa;
|
||||
y += ya;
|
||||
return true;
|
||||
}
|
||||
}
|
||||
|
||||
private boolean isBlocking(float _x, float _y, float xa, float ya)
|
||||
{
|
||||
int x = (int) (_x / 16);
|
||||
int y = (int) (_y / 16);
|
||||
if (x == (int) (this.x / 16) && y == (int) (this.y / 16)) return false;
|
||||
|
||||
boolean blocking = world.level.isBlocking(x, y, xa, ya);
|
||||
|
||||
byte block = world.level.getBlock(x, y);
|
||||
|
||||
return blocking;
|
||||
}
|
||||
|
||||
public boolean shellCollideCheck(Shell shell)
|
||||
{
|
||||
if (deadTime != 0) return false;
|
||||
|
||||
float xD = shell.x - x;
|
||||
float yD = shell.y - y;
|
||||
|
||||
if (xD > -16 && xD < 16)
|
||||
{
|
||||
if (yD > -height && yD < shell.height)
|
||||
{
|
||||
world.sound.play(Art.samples[Art.SAMPLE_MARIO_KICK], this, 1, 1, 1);
|
||||
|
||||
xa = shell.facing * 2;
|
||||
ya = -5;
|
||||
flyDeath = true;
|
||||
if (spriteTemplate != null) spriteTemplate.isDead = true;
|
||||
deadTime = 100;
|
||||
winged = false;
|
||||
hPic = -hPic;
|
||||
yPicO = -yPicO + 16;
|
||||
|
||||
if(world.recorder != null)
|
||||
world.recorder.shellKillRecord(this);
|
||||
|
||||
return true;
|
||||
}
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
public boolean fireballCollideCheck(Fireball fireball)
|
||||
{
|
||||
if (deadTime != 0) return false;
|
||||
|
||||
float xD = fireball.x - x;
|
||||
float yD = fireball.y - y;
|
||||
|
||||
if (xD > -16 && xD < 16)
|
||||
{
|
||||
if (yD > -height && yD < fireball.height)
|
||||
{
|
||||
if (noFireballDeath) return true;
|
||||
|
||||
world.sound.play(Art.samples[Art.SAMPLE_MARIO_KICK], this, 1, 1, 1);
|
||||
|
||||
xa = fireball.facing * 2;
|
||||
ya = -5;
|
||||
flyDeath = true;
|
||||
if (spriteTemplate != null) spriteTemplate.isDead = true;
|
||||
deadTime = 100;
|
||||
winged = false;
|
||||
hPic = -hPic;
|
||||
yPicO = -yPicO + 16;
|
||||
|
||||
|
||||
if(world.recorder != null)
|
||||
world.recorder.fireKillRecord(this);
|
||||
|
||||
return true;
|
||||
}
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
public void bumpCheck(int xTile, int yTile)
|
||||
{
|
||||
if (deadTime != 0) return;
|
||||
|
||||
if (x + width > xTile * 16 && x - width < xTile * 16 + 16 && yTile == (int) ((y - 1) / 16))
|
||||
{
|
||||
world.sound.play(Art.samples[Art.SAMPLE_MARIO_KICK], this, 1, 1, 1);
|
||||
|
||||
xa = -world.mario.facing * 2;
|
||||
ya = -5;
|
||||
flyDeath = true;
|
||||
if (spriteTemplate != null) spriteTemplate.isDead = true;
|
||||
deadTime = 100;
|
||||
winged = false;
|
||||
hPic = -hPic;
|
||||
yPicO = -yPicO + 16;
|
||||
|
||||
}
|
||||
}
|
||||
|
||||
public void render(Graphics og, float alpha)
|
||||
{
|
||||
if (winged)
|
||||
{
|
||||
int xPixel = (int) (xOld + (x - xOld) * alpha) - xPicO;
|
||||
int yPixel = (int) (yOld + (y - yOld) * alpha) - yPicO;
|
||||
|
||||
if (type == Enemy.ENEMY_GREEN_KOOPA || type == Enemy.ENEMY_RED_KOOPA)
|
||||
{
|
||||
}
|
||||
else
|
||||
{
|
||||
xFlipPic = !xFlipPic;
|
||||
og.drawImage(sheet[wingTime / 4 % 2][4], xPixel + (xFlipPic ? wPic : 0) + (xFlipPic ? 10 : -10), yPixel + (yFlipPic ? hPic : 0) - 8, xFlipPic ? -wPic : wPic, yFlipPic ? -hPic : hPic, null);
|
||||
xFlipPic = !xFlipPic;
|
||||
}
|
||||
}
|
||||
|
||||
super.render(og, alpha);
|
||||
|
||||
if (winged)
|
||||
{
|
||||
int xPixel = (int) (xOld + (x - xOld) * alpha) - xPicO;
|
||||
int yPixel = (int) (yOld + (y - yOld) * alpha) - yPicO;
|
||||
|
||||
if (type == Enemy.ENEMY_GREEN_KOOPA || type == Enemy.ENEMY_RED_KOOPA)
|
||||
{
|
||||
og.drawImage(sheet[wingTime / 4 % 2][4], xPixel + (xFlipPic ? wPic : 0) + (xFlipPic ? 10 : -10), yPixel + (yFlipPic ? hPic : 0) - 10, xFlipPic ? -wPic : wPic, yFlipPic ? -hPic : hPic, null);
|
||||
}
|
||||
else
|
||||
{
|
||||
og.drawImage(sheet[wingTime / 4 % 2][4], xPixel + (xFlipPic ? wPic : 0) + (xFlipPic ? 10 : -10), yPixel + (yFlipPic ? hPic : 0) - 8, xFlipPic ? -wPic : wPic, yFlipPic ? -hPic : hPic, null);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
63
src/dk/itu/mario/engine/sprites/FireFlower.java
Normal file
63
src/dk/itu/mario/engine/sprites/FireFlower.java
Normal file
@@ -0,0 +1,63 @@
|
||||
package dk.itu.mario.engine.sprites;
|
||||
|
||||
|
||||
import dk.itu.mario.engine.Art;
|
||||
import dk.itu.mario.scene.LevelScene;
|
||||
|
||||
|
||||
|
||||
public class FireFlower extends Sprite
|
||||
{
|
||||
private int width = 4;
|
||||
int height = 24;
|
||||
|
||||
private LevelScene world;
|
||||
public int facing;
|
||||
|
||||
public boolean avoidCliffs = false;
|
||||
private int life;
|
||||
|
||||
public FireFlower(LevelScene world, int x, int y)
|
||||
{
|
||||
sheet = Art.items;
|
||||
|
||||
this.x = x;
|
||||
this.y = y;
|
||||
this.world = world;
|
||||
xPicO = 8;
|
||||
yPicO = 15;
|
||||
|
||||
xPic = 1;
|
||||
yPic = 0;
|
||||
height = 12;
|
||||
facing = 1;
|
||||
wPic = hPic = 16;
|
||||
life = 0;
|
||||
}
|
||||
|
||||
public void collideCheck()
|
||||
{
|
||||
float xMarioD = world.mario.x - x;
|
||||
float yMarioD = world.mario.y - y;
|
||||
float w = 16;
|
||||
if (xMarioD > -16 && xMarioD < 16)
|
||||
{
|
||||
if (yMarioD > -height && yMarioD < world.mario.height)
|
||||
{
|
||||
world.mario.getFlower();
|
||||
spriteContext.removeSprite(this);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public void move()
|
||||
{
|
||||
if (life<9)
|
||||
{
|
||||
layer = 0;
|
||||
y--;
|
||||
life++;
|
||||
return;
|
||||
}
|
||||
}
|
||||
}
|
||||
220
src/dk/itu/mario/engine/sprites/Fireball.java
Normal file
220
src/dk/itu/mario/engine/sprites/Fireball.java
Normal file
@@ -0,0 +1,220 @@
|
||||
package dk.itu.mario.engine.sprites;
|
||||
|
||||
|
||||
import dk.itu.mario.engine.Art;
|
||||
import dk.itu.mario.scene.LevelScene;
|
||||
|
||||
|
||||
|
||||
public class Fireball extends Sprite
|
||||
{
|
||||
private static float GROUND_INERTIA = 0.89f;
|
||||
private static float AIR_INERTIA = 0.89f;
|
||||
|
||||
private float runTime;
|
||||
private boolean onGround = false;
|
||||
|
||||
private int width = 4;
|
||||
int height = 24;
|
||||
|
||||
private LevelScene world;
|
||||
public int facing;
|
||||
|
||||
public boolean avoidCliffs = false;
|
||||
public int anim;
|
||||
|
||||
public boolean dead = false;
|
||||
private int deadTime = 0;
|
||||
|
||||
public Fireball(LevelScene world, float x, float y, int facing)
|
||||
{
|
||||
sheet = Art.particles;
|
||||
|
||||
this.x = x;
|
||||
this.y = y;
|
||||
this.world = world;
|
||||
xPicO = 4;
|
||||
yPicO = 4;
|
||||
|
||||
yPic = 3;
|
||||
height = 8;
|
||||
this.facing = facing;
|
||||
wPic = 8;
|
||||
hPic = 8;
|
||||
|
||||
xPic = 4;
|
||||
ya = 4;
|
||||
}
|
||||
|
||||
public void move()
|
||||
{
|
||||
if (deadTime > 0)
|
||||
{
|
||||
for (int i = 0; i < 8; i++)
|
||||
{
|
||||
world.addSprite(new Sparkle((int) (x + Math.random() * 8 - 4)+4, (int) (y + Math.random() * 8-4)+2, (float) Math.random() * 2 - 1-facing, (float) Math.random() *2 -1, 0, 1, 5));
|
||||
}
|
||||
spriteContext.removeSprite(this);
|
||||
|
||||
return;
|
||||
}
|
||||
|
||||
if (facing != 0) anim++;
|
||||
|
||||
float sideWaysSpeed = 8f;
|
||||
// float sideWaysSpeed = onGround ? 2.5f : 1.2f;
|
||||
|
||||
if (xa > 2)
|
||||
{
|
||||
facing = 1;
|
||||
}
|
||||
if (xa < -2)
|
||||
{
|
||||
facing = -1;
|
||||
}
|
||||
|
||||
xa = facing * sideWaysSpeed;
|
||||
|
||||
world.checkFireballCollide(this);
|
||||
|
||||
xFlipPic = facing == -1;
|
||||
|
||||
runTime += (Math.abs(xa)) + 5;
|
||||
|
||||
xPic = (anim) % 4;
|
||||
|
||||
|
||||
|
||||
if (!move(xa, 0))
|
||||
{
|
||||
die();
|
||||
}
|
||||
|
||||
onGround = false;
|
||||
move(0, ya);
|
||||
if (onGround) ya = -10;
|
||||
|
||||
ya *= 0.95f;
|
||||
if (onGround)
|
||||
{
|
||||
xa *= GROUND_INERTIA;
|
||||
}
|
||||
else
|
||||
{
|
||||
xa *= AIR_INERTIA;
|
||||
}
|
||||
|
||||
if (!onGround)
|
||||
{
|
||||
ya += 1.5;
|
||||
}
|
||||
}
|
||||
|
||||
private boolean move(float xa, float ya)
|
||||
{
|
||||
while (xa > 8)
|
||||
{
|
||||
if (!move(8, 0)) return false;
|
||||
xa -= 8;
|
||||
}
|
||||
while (xa < -8)
|
||||
{
|
||||
if (!move(-8, 0)) return false;
|
||||
xa += 8;
|
||||
}
|
||||
while (ya > 8)
|
||||
{
|
||||
if (!move(0, 8)) return false;
|
||||
ya -= 8;
|
||||
}
|
||||
while (ya < -8)
|
||||
{
|
||||
if (!move(0, -8)) return false;
|
||||
ya += 8;
|
||||
}
|
||||
|
||||
boolean collide = false;
|
||||
if (ya > 0)
|
||||
{
|
||||
if (isBlocking(x + xa - width, y + ya, xa, 0)) collide = true;
|
||||
else if (isBlocking(x + xa + width, y + ya, xa, 0)) collide = true;
|
||||
else if (isBlocking(x + xa - width, y + ya + 1, xa, ya)) collide = true;
|
||||
else if (isBlocking(x + xa + width, y + ya + 1, xa, ya)) collide = true;
|
||||
}
|
||||
if (ya < 0)
|
||||
{
|
||||
if (isBlocking(x + xa, y + ya - height, xa, ya)) collide = true;
|
||||
else if (collide || isBlocking(x + xa - width, y + ya - height, xa, ya)) collide = true;
|
||||
else if (collide || isBlocking(x + xa + width, y + ya - height, xa, ya)) collide = true;
|
||||
}
|
||||
if (xa > 0)
|
||||
{
|
||||
if (isBlocking(x + xa + width, y + ya - height, xa, ya)) collide = true;
|
||||
if (isBlocking(x + xa + width, y + ya - height / 2, xa, ya)) collide = true;
|
||||
if (isBlocking(x + xa + width, y + ya, xa, ya)) collide = true;
|
||||
|
||||
if (avoidCliffs && onGround && !world.level.isBlocking((int) ((x + xa + width) / 16), (int) ((y) / 16 + 1), xa, 1)) collide = true;
|
||||
}
|
||||
if (xa < 0)
|
||||
{
|
||||
if (isBlocking(x + xa - width, y + ya - height, xa, ya)) collide = true;
|
||||
if (isBlocking(x + xa - width, y + ya - height / 2, xa, ya)) collide = true;
|
||||
if (isBlocking(x + xa - width, y + ya, xa, ya)) collide = true;
|
||||
|
||||
if (avoidCliffs && onGround && !world.level.isBlocking((int) ((x + xa - width) / 16), (int) ((y) / 16 + 1), xa, 1)) collide = true;
|
||||
}
|
||||
|
||||
if (collide)
|
||||
{
|
||||
if (xa < 0)
|
||||
{
|
||||
x = (int) ((x - width) / 16) * 16 + width;
|
||||
this.xa = 0;
|
||||
}
|
||||
if (xa > 0)
|
||||
{
|
||||
x = (int) ((x + width) / 16 + 1) * 16 - width - 1;
|
||||
this.xa = 0;
|
||||
}
|
||||
if (ya < 0)
|
||||
{
|
||||
y = (int) ((y - height) / 16) * 16 + height;
|
||||
this.ya = 0;
|
||||
}
|
||||
if (ya > 0)
|
||||
{
|
||||
y = (int) (y / 16 + 1) * 16 - 1;
|
||||
onGround = true;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
else
|
||||
{
|
||||
x += xa;
|
||||
y += ya;
|
||||
return true;
|
||||
}
|
||||
}
|
||||
|
||||
private boolean isBlocking(float _x, float _y, float xa, float ya)
|
||||
{
|
||||
int x = (int) (_x / 16);
|
||||
int y = (int) (_y / 16);
|
||||
if (x == (int) (this.x / 16) && y == (int) (this.y / 16)) return false;
|
||||
|
||||
boolean blocking = world.level.isBlocking(x, y, xa, ya);
|
||||
|
||||
byte block = world.level.getBlock(x, y);
|
||||
|
||||
return blocking;
|
||||
}
|
||||
|
||||
public void die()
|
||||
{
|
||||
dead = true;
|
||||
|
||||
xa = -facing * 2;
|
||||
ya = -5;
|
||||
deadTime = 100;
|
||||
}
|
||||
}
|
||||
103
src/dk/itu/mario/engine/sprites/FlowerEnemy.java
Normal file
103
src/dk/itu/mario/engine/sprites/FlowerEnemy.java
Normal file
@@ -0,0 +1,103 @@
|
||||
package dk.itu.mario.engine.sprites;
|
||||
|
||||
import dk.itu.mario.level.Level;
|
||||
import dk.itu.mario.scene.LevelScene;
|
||||
import dk.itu.mario.engine.sprites.*;
|
||||
|
||||
public class FlowerEnemy extends Enemy
|
||||
{
|
||||
private int tick;
|
||||
private int yStart;
|
||||
private int jumpTime = 0;
|
||||
private LevelScene world;
|
||||
|
||||
public FlowerEnemy(LevelScene world, int x, int y)
|
||||
{
|
||||
super(world, x, y, 1, ENEMY_SPIKY, false);
|
||||
|
||||
noFireballDeath = false;
|
||||
this.world = world;
|
||||
this.xPic = 0;
|
||||
this.yPic = 6;
|
||||
this.yPicO = 24;
|
||||
this.height = 12;
|
||||
this.width = 2;
|
||||
|
||||
yStart = y;
|
||||
ya = -8;
|
||||
|
||||
this.y-=1;
|
||||
|
||||
this.layer = 0;
|
||||
for (int i=0; i<4; i++)
|
||||
{
|
||||
move();
|
||||
}
|
||||
}
|
||||
|
||||
public void move()
|
||||
{
|
||||
if (deadTime > 0)
|
||||
{
|
||||
deadTime--;
|
||||
|
||||
if (deadTime == 0)
|
||||
{
|
||||
deadTime = 1;
|
||||
for (int i = 0; i < 8; i++)
|
||||
{
|
||||
world.addSprite(new Sparkle((int) (x + Math.random() * 16 - 8) + 4, (int) (y - Math.random() * 8) + 4, (float) (Math.random() * 2 - 1), (float) Math.random() * -1, 0, 1, 5));
|
||||
}
|
||||
spriteContext.removeSprite(this);
|
||||
}
|
||||
|
||||
x += xa;
|
||||
y += ya;
|
||||
ya *= 0.95;
|
||||
ya += 1;
|
||||
|
||||
return;
|
||||
}
|
||||
|
||||
tick++;
|
||||
|
||||
if (y>=yStart)
|
||||
{
|
||||
y = yStart;
|
||||
|
||||
int xd = (int)(Math.abs(world.mario.x-x));
|
||||
jumpTime++;
|
||||
if (jumpTime>40 && xd>24)
|
||||
{
|
||||
ya = -8;
|
||||
}
|
||||
else
|
||||
{
|
||||
ya = 0;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
jumpTime = 0;
|
||||
}
|
||||
|
||||
y+=ya;
|
||||
ya*=0.9;
|
||||
ya+=0.1f;
|
||||
|
||||
xPic = ((tick/2)&1)*2+((tick/6)&1);
|
||||
}
|
||||
|
||||
/* public void render(Graphics og, float alpha)
|
||||
{
|
||||
if (!visible) return;
|
||||
|
||||
int xPixel = (int)(xOld+(x-xOld)*alpha)-xPicO;
|
||||
int yPixel = (int)(yOld+(y-yOld)*alpha)-yPicO;
|
||||
|
||||
int a = ((tick/3)&1)*2;
|
||||
// a += ((tick/8)&1);
|
||||
og.drawImage(sheet[a*2+0][6], xPixel-8, yPixel+8, 16, 32, null);
|
||||
og.drawImage(sheet[a*2+1][6], xPixel+8, yPixel+8, 16, 32, null);
|
||||
}*/
|
||||
}
|
||||
918
src/dk/itu/mario/engine/sprites/Mario.java
Normal file
918
src/dk/itu/mario/engine/sprites/Mario.java
Normal file
@@ -0,0 +1,918 @@
|
||||
package dk.itu.mario.engine.sprites;
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
import dk.itu.mario.engine.Art;
|
||||
import dk.itu.mario.engine.DataRecorder;
|
||||
import dk.itu.mario.engine.sonar.FixedSoundSource;
|
||||
import dk.itu.mario.level.Level;
|
||||
import dk.itu.mario.scene.LevelScene;
|
||||
import dk.itu.mario.scene.Scene;
|
||||
|
||||
|
||||
|
||||
|
||||
public class Mario extends Sprite
|
||||
{
|
||||
public static boolean large = false;
|
||||
public static boolean fire = false;
|
||||
public static int coins = 0;
|
||||
public static int lives = 3;
|
||||
public static String levelString = "none";
|
||||
|
||||
public static void resetStatic()
|
||||
{
|
||||
large = false;
|
||||
fire = false;
|
||||
coins = 0;
|
||||
lives = 3;
|
||||
levelString = "none";
|
||||
}
|
||||
|
||||
public static final int KEY_LEFT = 0;
|
||||
public static final int KEY_RIGHT = 1;
|
||||
public static final int KEY_DOWN = 2;
|
||||
public static final int KEY_UP = 3;
|
||||
public static final int KEY_JUMP = 4;
|
||||
public static final int KEY_SPEED = 5;
|
||||
public static final int KEY_ENTER = 6;
|
||||
|
||||
private static float GROUND_INERTIA = 0.89f;
|
||||
private static float AIR_INERTIA = 0.89f;
|
||||
|
||||
public boolean[] keys;
|
||||
private float runTime;
|
||||
boolean wasOnGround = false;
|
||||
boolean onGround = false;
|
||||
private boolean mayJump = false;
|
||||
public boolean ducking = false;
|
||||
public boolean running = false;
|
||||
public int direction = 0;
|
||||
private boolean sliding = false;
|
||||
private int jumpTime = 0;
|
||||
private float xJumpSpeed;
|
||||
private float yJumpSpeed;
|
||||
private boolean canShoot = false;
|
||||
|
||||
int width = 4;
|
||||
int height = 24;
|
||||
|
||||
private LevelScene world;
|
||||
public int facing;
|
||||
private int powerUpTime = 0;
|
||||
|
||||
public int xDeathPos, yDeathPos;
|
||||
|
||||
public int deathTime = 0;
|
||||
public int winTime = 0;
|
||||
private int invulnerableTime = 0;
|
||||
|
||||
public Sprite carried = null;
|
||||
private static Mario instance;
|
||||
|
||||
public Mario(LevelScene world)
|
||||
{
|
||||
Mario.instance = this;
|
||||
this.world = world;
|
||||
keys = Scene.keys;
|
||||
x = 32;
|
||||
y = 0;
|
||||
|
||||
facing = 1;
|
||||
|
||||
//TODO: REMOVE THESE TEST VARIABLES
|
||||
// Mario.large = true;
|
||||
// Mario.fire = true;
|
||||
|
||||
setLarge(Mario.large, Mario.fire);
|
||||
}
|
||||
|
||||
private boolean lastLarge;
|
||||
private boolean lastFire;
|
||||
private boolean newLarge;
|
||||
private boolean newFire;
|
||||
|
||||
private void blink(boolean on)
|
||||
{
|
||||
Mario.large = on?newLarge:lastLarge;
|
||||
Mario.fire = on?newFire:lastFire;
|
||||
|
||||
if (large)
|
||||
{
|
||||
sheet = Art.mario;
|
||||
if (fire)
|
||||
sheet = Art.fireMario;
|
||||
|
||||
xPicO = 16;
|
||||
yPicO = 31;
|
||||
wPic = hPic = 32;
|
||||
}
|
||||
else
|
||||
{
|
||||
sheet = Art.smallMario;
|
||||
|
||||
xPicO = 8;
|
||||
yPicO = 15;
|
||||
wPic = hPic = 16;
|
||||
}
|
||||
|
||||
calcPic();
|
||||
}
|
||||
|
||||
void setLarge(boolean large, boolean fire)
|
||||
{
|
||||
if (fire) large = true;
|
||||
if (!large) fire = false;
|
||||
|
||||
lastLarge = Mario.large;
|
||||
lastFire = Mario.fire;
|
||||
|
||||
Mario.large = large;
|
||||
Mario.fire = fire;
|
||||
|
||||
newLarge = Mario.large;
|
||||
newFire = Mario.fire;
|
||||
|
||||
blink(true);
|
||||
}
|
||||
|
||||
public void move()
|
||||
{
|
||||
if(deathTime == 0 && winTime == 0){
|
||||
if (keys[KEY_DOWN] && large && ducking)
|
||||
{
|
||||
if(world.recorder != null && world.recorder.recording)
|
||||
world.recorder.startDuckRecord();
|
||||
}
|
||||
else
|
||||
{
|
||||
if(world.recorder != null && world.recorder.recording && !ducking)
|
||||
world.recorder.endDuckRecord();
|
||||
}
|
||||
}
|
||||
|
||||
if(deathTime == 0 && winTime == 0){
|
||||
if(keys[KEY_SPEED]){
|
||||
if(world.recorder!= null && world.recorder.recording){
|
||||
world.recorder.startRunningRecord();
|
||||
}
|
||||
|
||||
running = true;
|
||||
}
|
||||
else{
|
||||
if(world.recorder!= null && world.recorder.recording){
|
||||
world.recorder.endRunningRecord();
|
||||
}
|
||||
|
||||
running = false;
|
||||
}
|
||||
}
|
||||
|
||||
if (winTime > 0)
|
||||
{
|
||||
|
||||
winTime++;
|
||||
|
||||
xa = 0;
|
||||
ya = 0;
|
||||
return;
|
||||
}
|
||||
|
||||
if (deathTime > 0)
|
||||
{
|
||||
deathTime++;
|
||||
if (deathTime < 11)
|
||||
{
|
||||
xa = 0;
|
||||
ya = 0;
|
||||
}
|
||||
else if (deathTime == 11)
|
||||
{
|
||||
ya = -15;
|
||||
}
|
||||
else
|
||||
{
|
||||
ya += 2;
|
||||
}
|
||||
x += xa;
|
||||
y += ya;
|
||||
return;
|
||||
}
|
||||
|
||||
if (powerUpTime != 0)
|
||||
{
|
||||
if (powerUpTime > 0)
|
||||
{
|
||||
powerUpTime--;
|
||||
blink(((powerUpTime / 3) & 1) == 0);
|
||||
}
|
||||
else
|
||||
{
|
||||
powerUpTime++;
|
||||
blink(((-powerUpTime / 3) & 1) == 0);
|
||||
}
|
||||
|
||||
if (powerUpTime == 0) world.paused = false;
|
||||
|
||||
calcPic();
|
||||
return;
|
||||
}
|
||||
|
||||
if (invulnerableTime > 0) invulnerableTime--;
|
||||
visible = ((invulnerableTime / 2) & 1) == 0;
|
||||
|
||||
wasOnGround = onGround;
|
||||
float sideWaysSpeed = keys[KEY_SPEED] ? 1.2f : 0.6f;
|
||||
// float sideWaysSpeed = onGround ? 2.5f : 1.2f;
|
||||
|
||||
if (onGround)
|
||||
{
|
||||
if (keys[KEY_DOWN] && large)
|
||||
{
|
||||
if(world.recorder != null)
|
||||
world.recorder.startDuckRecord();
|
||||
|
||||
ducking = true;
|
||||
}
|
||||
else
|
||||
{
|
||||
if(world.recorder != null)
|
||||
world.recorder.endDuckRecord();
|
||||
|
||||
ducking = false;
|
||||
}
|
||||
|
||||
if(world.recorder != null)
|
||||
world.recorder.recordJumpLand();
|
||||
}
|
||||
|
||||
if (xa > 2)
|
||||
{
|
||||
facing = 1;
|
||||
}
|
||||
if (xa < -2)
|
||||
{
|
||||
facing = -1;
|
||||
}
|
||||
|
||||
if (keys[KEY_JUMP] || (jumpTime < 0 && !onGround && !sliding))
|
||||
{
|
||||
if (jumpTime < 0)
|
||||
{
|
||||
xa = xJumpSpeed;
|
||||
ya = -jumpTime * yJumpSpeed;
|
||||
jumpTime++;
|
||||
}
|
||||
else if (onGround && mayJump)
|
||||
{
|
||||
world.sound.play(Art.samples[Art.SAMPLE_MARIO_JUMP], this, 1, 1, 1);
|
||||
xJumpSpeed = 0;
|
||||
yJumpSpeed = -1.9f;
|
||||
jumpTime = 7;
|
||||
ya = jumpTime * yJumpSpeed;
|
||||
onGround = false;
|
||||
sliding = false;
|
||||
|
||||
if(world.recorder != null){
|
||||
world.recorder.isInAir = true;
|
||||
world.recorder.recordJump();
|
||||
}
|
||||
}
|
||||
else if (sliding && mayJump)
|
||||
{
|
||||
world.sound.play(Art.samples[Art.SAMPLE_MARIO_JUMP], this, 1, 1, 1);
|
||||
xJumpSpeed = -facing * 6.0f;
|
||||
yJumpSpeed = -2.0f;
|
||||
jumpTime = -6;
|
||||
xa = xJumpSpeed;
|
||||
ya = -jumpTime * yJumpSpeed;
|
||||
onGround = false;
|
||||
sliding = false;
|
||||
facing = -facing;
|
||||
}
|
||||
else if (jumpTime > 0)
|
||||
{
|
||||
xa += xJumpSpeed;
|
||||
ya = jumpTime * yJumpSpeed;
|
||||
jumpTime--;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
jumpTime = 0;
|
||||
}
|
||||
|
||||
if(world.mario.xa > 0){
|
||||
|
||||
if(direction != 1){
|
||||
direction = 1;
|
||||
if(world.recorder != null){
|
||||
// world.recorder.switchRecord();
|
||||
world.recorder.startRightMoveRecord();
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
else if(world.mario.xa < 0){
|
||||
if(direction != -1){
|
||||
direction = -1;
|
||||
if(world.recorder != null){
|
||||
// world.recorder.switchRecord();
|
||||
world.recorder.startLeftMoveRecord();
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
else{
|
||||
//was moving right
|
||||
if(direction == 1 && world.recorder!= null){
|
||||
world.recorder.endRightMoveRecord();
|
||||
}
|
||||
//was moving left
|
||||
else if(direction == -1 && world.recorder!= null){
|
||||
world.recorder.endLeftMoveRecord();
|
||||
}
|
||||
|
||||
direction = 0;
|
||||
}
|
||||
|
||||
if (keys[KEY_LEFT] && !ducking)
|
||||
{
|
||||
if (facing == 1) sliding = false;
|
||||
xa -= sideWaysSpeed;
|
||||
if (jumpTime >= 0) facing = -1;
|
||||
}
|
||||
|
||||
if (keys[KEY_RIGHT] && !ducking)
|
||||
{
|
||||
if (facing == -1) sliding = false;
|
||||
xa += sideWaysSpeed;
|
||||
if (jumpTime >= 0) facing = 1;
|
||||
}
|
||||
|
||||
if ((!keys[KEY_LEFT] && !keys[KEY_RIGHT]) || ducking || ya < 0 || onGround)
|
||||
{
|
||||
sliding = false;
|
||||
}
|
||||
|
||||
if (keys[KEY_SPEED] && canShoot && Mario.fire && world.fireballsOnScreen<2)
|
||||
{
|
||||
world.sound.play(Art.samples[Art.SAMPLE_MARIO_FIREBALL], this, 1, 1, 1);
|
||||
world.addSprite(new Fireball(world, x+facing*6, y-20, facing));
|
||||
}
|
||||
|
||||
canShoot = !keys[KEY_SPEED];
|
||||
|
||||
mayJump = (onGround || sliding) && !keys[KEY_JUMP];
|
||||
|
||||
xFlipPic = facing == -1;
|
||||
|
||||
runTime += (Math.abs(xa)) + 5;
|
||||
if (Math.abs(xa) < 0.5f)
|
||||
{
|
||||
runTime = 0;
|
||||
xa = 0;
|
||||
}
|
||||
|
||||
calcPic();
|
||||
|
||||
if (sliding)
|
||||
{
|
||||
for (int i = 0; i < 1; i++)
|
||||
{
|
||||
world.addSprite(new Sparkle((int) (x + Math.random() * 4 - 2) + facing * 8, (int) (y + Math.random() * 4) - 24, (float) (Math.random() * 2 - 1), (float) Math.random() * 1, 0, 1, 5));
|
||||
}
|
||||
ya *= 0.5f;
|
||||
}
|
||||
|
||||
onGround = false;
|
||||
move(xa, 0);
|
||||
move(0, ya);
|
||||
|
||||
if (y > world.level.getHeight() * 16 + 16)
|
||||
{
|
||||
dieJump();
|
||||
}
|
||||
|
||||
if (x < 0)
|
||||
{
|
||||
x = 0;
|
||||
xa = 0;
|
||||
}
|
||||
|
||||
// if(x > world.level.xExit * 16 && ! world.level.flipped || x < world.level.xExit * 16 && world.level.flipped )
|
||||
if(x > world.level.getxExit() * 16 )
|
||||
|
||||
{
|
||||
win();
|
||||
}
|
||||
|
||||
if (x > world.level.getWidth() * 16)
|
||||
{
|
||||
x = world.level.getWidth() * 16;
|
||||
xa = 0;
|
||||
}
|
||||
|
||||
ya *= 0.85f;
|
||||
if (onGround)
|
||||
{
|
||||
xa *= GROUND_INERTIA;
|
||||
}
|
||||
else
|
||||
{
|
||||
xa *= AIR_INERTIA;
|
||||
}
|
||||
|
||||
if (!onGround)
|
||||
{
|
||||
ya += 3;
|
||||
}
|
||||
|
||||
if (carried != null)
|
||||
{
|
||||
carried.x = x + facing * 8;
|
||||
carried.y = y - 2;
|
||||
if (!keys[KEY_SPEED])
|
||||
{
|
||||
carried.release(this);
|
||||
carried = null;
|
||||
|
||||
if(world.recorder != null){
|
||||
world.recorder.shellUnleashedRecord();
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private void calcPic()
|
||||
{
|
||||
int runFrame = 0;
|
||||
|
||||
if (large)
|
||||
{
|
||||
runFrame = ((int) (runTime / 20)) % 4;
|
||||
if (runFrame == 3) runFrame = 1;
|
||||
if (carried == null && Math.abs(xa) > 10) runFrame += 3;
|
||||
if (carried != null) runFrame += 10;
|
||||
if (!onGround)
|
||||
{
|
||||
if (carried != null) runFrame = 12;
|
||||
else if (Math.abs(xa) > 10) runFrame = 7;
|
||||
else runFrame = 6;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
runFrame = ((int) (runTime / 20)) % 2;
|
||||
if (carried == null && Math.abs(xa) > 10) runFrame += 2;
|
||||
if (carried != null) runFrame += 8;
|
||||
if (!onGround)
|
||||
{
|
||||
if (carried != null) runFrame = 9;
|
||||
else if (Math.abs(xa) > 10) runFrame = 5;
|
||||
else runFrame = 4;
|
||||
}
|
||||
}
|
||||
|
||||
if (onGround && ((facing == -1 && xa > 0) || (facing == 1 && xa < 0)))
|
||||
{
|
||||
if (xa > 1 || xa < -1) runFrame = large ? 9 : 7;
|
||||
|
||||
if (xa > 3 || xa < -3)
|
||||
{
|
||||
for (int i = 0; i < 3; i++)
|
||||
{
|
||||
world.addSprite(new Sparkle((int) (x + Math.random() * 8 - 4), (int) (y + Math.random() * 4), (float) (Math.random() * 2 - 1), (float) Math.random() * -1, 0, 1, 5));
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (large)
|
||||
{
|
||||
if (ducking) runFrame = 14;
|
||||
height = ducking ? 12 : 24;
|
||||
}
|
||||
else
|
||||
{
|
||||
height = 12;
|
||||
}
|
||||
|
||||
xPic = runFrame;
|
||||
}
|
||||
|
||||
private boolean move(float xa, float ya)
|
||||
{
|
||||
|
||||
while (xa > 8)
|
||||
{
|
||||
if (!move(8, 0)) return false;
|
||||
xa -= 8;
|
||||
}
|
||||
while (xa < -8)
|
||||
{
|
||||
if (!move(-8, 0)) return false;
|
||||
xa += 8;
|
||||
}
|
||||
while (ya > 8)
|
||||
{
|
||||
if (!move(0, 8)) return false;
|
||||
ya -= 8;
|
||||
}
|
||||
while (ya < -8)
|
||||
{
|
||||
if (!move(0, -8)) return false;
|
||||
ya += 8;
|
||||
}
|
||||
|
||||
boolean collide = false;
|
||||
if (ya > 0)
|
||||
{
|
||||
if (isBlocking(x + xa - width, y + ya, xa, 0)) collide = true;
|
||||
else if (isBlocking(x + xa + width, y + ya, xa, 0)) collide = true;
|
||||
else if (isBlocking(x + xa - width, y + ya + 1, xa, ya)) collide = true;
|
||||
else if (isBlocking(x + xa + width, y + ya + 1, xa, ya)) collide = true;
|
||||
}
|
||||
if (ya < 0)
|
||||
{
|
||||
if (isBlocking(x + xa, y + ya - height, xa, ya)) collide = true;
|
||||
else if (collide || isBlocking(x + xa - width, y + ya - height, xa, ya)) collide = true;
|
||||
else if (collide || isBlocking(x + xa + width, y + ya - height, xa, ya)) collide = true;
|
||||
}
|
||||
if (xa > 0)
|
||||
{
|
||||
sliding = true;
|
||||
if (isBlocking(x + xa + width, y + ya - height, xa, ya)) collide = true;
|
||||
else sliding = false;
|
||||
if (isBlocking(x + xa + width, y + ya - height / 2, xa, ya)) collide = true;
|
||||
else sliding = false;
|
||||
if (isBlocking(x + xa + width, y + ya, xa, ya)) collide = true;
|
||||
else sliding = false;
|
||||
}
|
||||
if (xa < 0)
|
||||
{
|
||||
sliding = true;
|
||||
if (isBlocking(x + xa - width, y + ya - height, xa, ya)) collide = true;
|
||||
else sliding = false;
|
||||
if (isBlocking(x + xa - width, y + ya - height / 2, xa, ya)) collide = true;
|
||||
else sliding = false;
|
||||
if (isBlocking(x + xa - width, y + ya, xa, ya)) collide = true;
|
||||
else sliding = false;
|
||||
}
|
||||
|
||||
if (collide)
|
||||
{
|
||||
if (xa < 0)
|
||||
{
|
||||
x = (int) ((x - width) / 16) * 16 + width;
|
||||
this.xa = 0;
|
||||
}
|
||||
if (xa > 0)
|
||||
{
|
||||
x = (int) ((x + width) / 16 + 1) * 16 - width - 1;
|
||||
this.xa = 0;
|
||||
}
|
||||
if (ya < 0)
|
||||
{
|
||||
y = (int) ((y - height) / 16) * 16 + height;
|
||||
jumpTime = 0;
|
||||
this.ya = 0;
|
||||
}
|
||||
if (ya > 0)
|
||||
{
|
||||
y = (int) ((y - 1) / 16 + 1) * 16 - 1;
|
||||
onGround = true;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
else
|
||||
{
|
||||
x += xa;
|
||||
y += ya;
|
||||
return true;
|
||||
}
|
||||
}
|
||||
|
||||
private boolean isBlocking(float _x, float _y, float xa, float ya)
|
||||
{
|
||||
//translate into block mode (since blocks are 16x16)
|
||||
int x = (int) (_x / 16);
|
||||
int y = (int) (_y / 16);
|
||||
|
||||
if (x==(int)(this.x/16) && y==(int)(this.y/16))
|
||||
return false;
|
||||
|
||||
boolean blocking = world.level.isBlocking(x, y, xa, ya);
|
||||
|
||||
byte block = world.level.getBlock(x, y);
|
||||
|
||||
if (((Level.TILE_BEHAVIORS[block & 0xff]) & Level.BIT_PICKUPABLE) > 0)
|
||||
{
|
||||
if(world.recorder != null)
|
||||
world.recorder.recordCoin();
|
||||
|
||||
Mario.getCoin();
|
||||
world.sound.play(Art.samples[Art.SAMPLE_GET_COIN], new FixedSoundSource(x * 16 + 8, y * 16 + 8), 1, 1, 1);
|
||||
world.level.setBlock(x, y, (byte) 0);
|
||||
for (int xx = 0; xx < 2; xx++)
|
||||
for (int yy = 0; yy < 2; yy++)
|
||||
world.addSprite(new Sparkle(x * 16 + xx * 8 + (int) (Math.random() * 8), y * 16 + yy * 8 + (int) (Math.random() * 8), 0, 0, 0, 2, 5));
|
||||
}
|
||||
|
||||
if (blocking && ya < 0)
|
||||
{
|
||||
world.bump(x, y, large);
|
||||
}
|
||||
|
||||
return blocking;
|
||||
}
|
||||
|
||||
public void stomp(Enemy enemy)
|
||||
{
|
||||
if (deathTime > 0 || world.paused) return;
|
||||
|
||||
float targetY = enemy.y - enemy.height / 2;
|
||||
move(0, targetY - y);
|
||||
|
||||
world.sound.play(Art.samples[Art.SAMPLE_MARIO_KICK], this, 1, 1, 1);
|
||||
xJumpSpeed = 0;
|
||||
yJumpSpeed = -1.9f;
|
||||
jumpTime = 8;
|
||||
ya = jumpTime * yJumpSpeed;
|
||||
onGround = false;
|
||||
sliding = false;
|
||||
invulnerableTime = 1;
|
||||
|
||||
if(world.recorder!=null)
|
||||
world.recorder.killStompRecord(enemy);
|
||||
}
|
||||
|
||||
public void stomp(Shell shell)
|
||||
{
|
||||
if (deathTime > 0 || world.paused) return;
|
||||
|
||||
if (keys[KEY_SPEED] && shell.facing == 0)
|
||||
{
|
||||
carried = shell;
|
||||
shell.carried = true;
|
||||
}
|
||||
else
|
||||
{
|
||||
float targetY = shell.y - shell.height / 2;
|
||||
move(0, targetY - y);
|
||||
|
||||
world.sound.play(Art.samples[Art.SAMPLE_MARIO_KICK], this, 1, 1, 1);
|
||||
xJumpSpeed = 0;
|
||||
yJumpSpeed = -1.9f;
|
||||
jumpTime = 8;
|
||||
ya = jumpTime * yJumpSpeed;
|
||||
onGround = false;
|
||||
sliding = false;
|
||||
invulnerableTime = 1;
|
||||
|
||||
if(shell.xa == 0 && world.recorder!= null){
|
||||
world.recorder.shellUnleashedRecord();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public void getHurt(Sprite sprite)
|
||||
{
|
||||
if (deathTime > 0 || world.paused) return;
|
||||
if (invulnerableTime > 0) return;
|
||||
|
||||
if (large)
|
||||
{
|
||||
world.paused = true;
|
||||
powerUpTime = -3 * 6;
|
||||
world.sound.play(Art.samples[Art.SAMPLE_MARIO_POWER_DOWN], this, 1, 1, 1);
|
||||
if (fire)
|
||||
{
|
||||
world.mario.setLarge(true, false);
|
||||
|
||||
if(world.recorder != null){
|
||||
world.recorder.endFireRecord();
|
||||
world.recorder.startLargeRecord();
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
world.mario.setLarge(false, false);
|
||||
|
||||
if(world.recorder != null){
|
||||
world.recorder.endLargeRecord();
|
||||
world.recorder.startLittleRecord();
|
||||
}
|
||||
}
|
||||
invulnerableTime = 32;
|
||||
}
|
||||
else
|
||||
{
|
||||
dieSprite(sprite);
|
||||
}
|
||||
}
|
||||
|
||||
private void win()
|
||||
{
|
||||
xDeathPos = (int) x;
|
||||
yDeathPos = (int) y;
|
||||
world.paused = true;
|
||||
winTime = 1;
|
||||
Art.stopMusic();
|
||||
world.sound.play(Art.samples[Art.SAMPLE_LEVEL_EXIT], this, 1, 1, 1);
|
||||
}
|
||||
|
||||
public void dieSprite(Sprite sprite){
|
||||
die();
|
||||
|
||||
if(world.recorder != null){
|
||||
world.recorder.dieRecord(sprite);
|
||||
}
|
||||
}
|
||||
|
||||
public void dieTime(){
|
||||
die();
|
||||
|
||||
if(world.recorder!=null){
|
||||
world.recorder.dieTimeRecord();
|
||||
}
|
||||
}
|
||||
|
||||
public void dieJump(){
|
||||
die();
|
||||
|
||||
if(world.recorder!=null){
|
||||
world.recorder.dieJumpRecord();
|
||||
}
|
||||
}
|
||||
|
||||
public void die()
|
||||
{
|
||||
xDeathPos = (int) x;
|
||||
yDeathPos = (int) y;
|
||||
world.paused = true;
|
||||
deathTime = 1;
|
||||
Art.stopMusic();
|
||||
world.sound.play(Art.samples[Art.SAMPLE_MARIO_DEATH], this, 1, 1, 1);
|
||||
|
||||
if(world.recorder != null){
|
||||
|
||||
|
||||
if(running)
|
||||
world.recorder.endRunningRecord();
|
||||
|
||||
if(large && !fire){
|
||||
world.recorder.endLargeRecord();
|
||||
}
|
||||
|
||||
if(fire){
|
||||
world.recorder.endFireRecord();
|
||||
}
|
||||
|
||||
if(!large && !fire)
|
||||
world.recorder.endLittleRecord();
|
||||
|
||||
if(ducking)
|
||||
world.recorder.endDuckRecord();
|
||||
|
||||
world.recorder.endTime();
|
||||
world.recorder.recordJumpLand();
|
||||
}
|
||||
|
||||
large = false;
|
||||
fire = false;
|
||||
}
|
||||
|
||||
|
||||
public void getFlower()
|
||||
{
|
||||
if (deathTime > 0 || world.paused) return;
|
||||
|
||||
if (!fire)
|
||||
{
|
||||
world.paused = true;
|
||||
powerUpTime = 3 * 6;
|
||||
world.sound.play(Art.samples[Art.SAMPLE_MARIO_POWER_UP], this, 1, 1, 1);
|
||||
world.mario.setLarge(true, true);
|
||||
|
||||
if(world.recorder != null){
|
||||
if(large){
|
||||
world.recorder.endLargeRecord();
|
||||
|
||||
}
|
||||
else{
|
||||
world.recorder.endLittleRecord();
|
||||
}
|
||||
|
||||
world.recorder.startFireRecord();
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
Mario.getCoin();
|
||||
world.sound.play(Art.samples[Art.SAMPLE_GET_COIN], this, 1, 1, 1);
|
||||
}
|
||||
}
|
||||
|
||||
public void getMushroom()
|
||||
{
|
||||
if (deathTime > 0 || world.paused) return;
|
||||
|
||||
if (!large)
|
||||
{
|
||||
world.paused = true;
|
||||
powerUpTime = 3 * 6;
|
||||
world.sound.play(Art.samples[Art.SAMPLE_MARIO_POWER_UP], this, 1, 1, 1);
|
||||
world.mario.setLarge(true, false);
|
||||
|
||||
if(world.recorder != null){
|
||||
world.recorder.endLittleRecord();
|
||||
world.recorder.startLargeRecord();
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
|
||||
Mario.getCoin();
|
||||
world.sound.play(Art.samples[Art.SAMPLE_GET_COIN], this, 1, 1, 1);
|
||||
}
|
||||
}
|
||||
|
||||
public void kick(Shell shell)
|
||||
{
|
||||
if (deathTime > 0 || world.paused) return;
|
||||
|
||||
if (keys[KEY_SPEED])
|
||||
{
|
||||
carried = shell;
|
||||
shell.carried = true;
|
||||
}
|
||||
else
|
||||
{
|
||||
world.sound.play(Art.samples[Art.SAMPLE_MARIO_KICK], this, 1, 1, 1);
|
||||
invulnerableTime = 1;
|
||||
|
||||
if(world.recorder!=null)
|
||||
world.recorder.shellUnleashedRecord();
|
||||
}
|
||||
}
|
||||
|
||||
public void stomp(BulletBill bill)
|
||||
{
|
||||
if (deathTime > 0 || world.paused) return;
|
||||
|
||||
float targetY = bill.y - bill.height / 2;
|
||||
move(0, targetY - y);
|
||||
|
||||
world.sound.play(Art.samples[Art.SAMPLE_MARIO_KICK], this, 1, 1, 1);
|
||||
xJumpSpeed = 0;
|
||||
yJumpSpeed = -1.9f;
|
||||
jumpTime = 8;
|
||||
ya = jumpTime * yJumpSpeed;
|
||||
onGround = false;
|
||||
sliding = false;
|
||||
invulnerableTime = 1;
|
||||
|
||||
if(world.recorder!=null)
|
||||
world.recorder.killStompRecord(bill);
|
||||
}
|
||||
|
||||
public byte getKeyMask()
|
||||
{
|
||||
int mask = 0;
|
||||
for (int i = 0; i < 7; i++)
|
||||
{
|
||||
if (keys[i]) mask |= (1 << i);
|
||||
}
|
||||
return (byte) mask;
|
||||
}
|
||||
|
||||
public void setKeys(byte mask)
|
||||
{
|
||||
for (int i = 0; i < 7; i++)
|
||||
{
|
||||
keys[i] = (mask & (1 << i)) > 0;
|
||||
}
|
||||
}
|
||||
|
||||
public static void get1Up()
|
||||
{
|
||||
instance.world.sound.play(Art.samples[Art.SAMPLE_MARIO_1UP], instance, 1, 1, 1);
|
||||
lives++;
|
||||
if (lives==99)
|
||||
{
|
||||
lives = 99;
|
||||
}
|
||||
}
|
||||
|
||||
public static void getCoin()
|
||||
{
|
||||
coins++;
|
||||
if (coins==100)
|
||||
{
|
||||
coins = 0;
|
||||
get1Up();
|
||||
}
|
||||
}
|
||||
}
|
||||
223
src/dk/itu/mario/engine/sprites/Mushroom.java
Normal file
223
src/dk/itu/mario/engine/sprites/Mushroom.java
Normal file
@@ -0,0 +1,223 @@
|
||||
package dk.itu.mario.engine.sprites;
|
||||
|
||||
|
||||
import dk.itu.mario.engine.Art;
|
||||
import dk.itu.mario.scene.LevelScene;
|
||||
|
||||
|
||||
|
||||
public class Mushroom extends Sprite
|
||||
{
|
||||
private static float GROUND_INERTIA = 0.89f;
|
||||
private static float AIR_INERTIA = 0.89f;
|
||||
|
||||
private float runTime;
|
||||
private boolean onGround = false;
|
||||
private boolean mayJump = false;
|
||||
private int jumpTime = 0;
|
||||
private float xJumpSpeed;
|
||||
private float yJumpSpeed;
|
||||
|
||||
private int width = 4;
|
||||
int height = 24;
|
||||
|
||||
private LevelScene world;
|
||||
public int facing;
|
||||
|
||||
public boolean avoidCliffs = false;
|
||||
private int life;
|
||||
|
||||
public Mushroom(LevelScene world, int x, int y)
|
||||
{
|
||||
sheet = Art.items;
|
||||
|
||||
this.x = x;
|
||||
this.y = y;
|
||||
this.world = world;
|
||||
xPicO = 8;
|
||||
yPicO = 15;
|
||||
|
||||
yPic = 0;
|
||||
height = 12;
|
||||
facing = 1;
|
||||
wPic = hPic = 16;
|
||||
life = 0;
|
||||
}
|
||||
|
||||
public void collideCheck()
|
||||
{
|
||||
float xMarioD = world.mario.x - x;
|
||||
float yMarioD = world.mario.y - y;
|
||||
float w = 16;
|
||||
if (xMarioD > -16 && xMarioD < 16)
|
||||
{
|
||||
if (yMarioD > -height && yMarioD < world.mario.height)
|
||||
{
|
||||
world.mario.getMushroom();
|
||||
spriteContext.removeSprite(this);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public void move()
|
||||
{
|
||||
if (life<9)
|
||||
{
|
||||
layer = 0;
|
||||
y--;
|
||||
life++;
|
||||
return;
|
||||
}
|
||||
float sideWaysSpeed = 1.75f;
|
||||
layer = 1;
|
||||
// float sideWaysSpeed = onGround ? 2.5f : 1.2f;
|
||||
|
||||
if (xa > 2)
|
||||
{
|
||||
facing = 1;
|
||||
}
|
||||
if (xa < -2)
|
||||
{
|
||||
facing = -1;
|
||||
}
|
||||
|
||||
xa = facing * sideWaysSpeed;
|
||||
|
||||
mayJump = (onGround);
|
||||
|
||||
xFlipPic = facing == -1;
|
||||
|
||||
runTime += (Math.abs(xa)) + 5;
|
||||
|
||||
|
||||
|
||||
if (!move(xa, 0)) facing = -facing;
|
||||
onGround = false;
|
||||
move(0, ya);
|
||||
|
||||
ya *= 0.85f;
|
||||
if (onGround)
|
||||
{
|
||||
xa *= GROUND_INERTIA;
|
||||
}
|
||||
else
|
||||
{
|
||||
xa *= AIR_INERTIA;
|
||||
}
|
||||
|
||||
if (!onGround)
|
||||
{
|
||||
ya += 2;
|
||||
}
|
||||
}
|
||||
|
||||
private boolean move(float xa, float ya)
|
||||
{
|
||||
while (xa > 8)
|
||||
{
|
||||
if (!move(8, 0)) return false;
|
||||
xa -= 8;
|
||||
}
|
||||
while (xa < -8)
|
||||
{
|
||||
if (!move(-8, 0)) return false;
|
||||
xa += 8;
|
||||
}
|
||||
while (ya > 8)
|
||||
{
|
||||
if (!move(0, 8)) return false;
|
||||
ya -= 8;
|
||||
}
|
||||
while (ya < -8)
|
||||
{
|
||||
if (!move(0, -8)) return false;
|
||||
ya += 8;
|
||||
}
|
||||
|
||||
boolean collide = false;
|
||||
if (ya > 0)
|
||||
{
|
||||
if (isBlocking(x + xa - width, y + ya, xa, 0)) collide = true;
|
||||
else if (isBlocking(x + xa + width, y + ya, xa, 0)) collide = true;
|
||||
else if (isBlocking(x + xa - width, y + ya + 1, xa, ya)) collide = true;
|
||||
else if (isBlocking(x + xa + width, y + ya + 1, xa, ya)) collide = true;
|
||||
}
|
||||
if (ya < 0)
|
||||
{
|
||||
if (isBlocking(x + xa, y + ya - height, xa, ya)) collide = true;
|
||||
else if (collide || isBlocking(x + xa - width, y + ya - height, xa, ya)) collide = true;
|
||||
else if (collide || isBlocking(x + xa + width, y + ya - height, xa, ya)) collide = true;
|
||||
}
|
||||
if (xa > 0)
|
||||
{
|
||||
if (isBlocking(x + xa + width, y + ya - height, xa, ya)) collide = true;
|
||||
if (isBlocking(x + xa + width, y + ya - height / 2, xa, ya)) collide = true;
|
||||
if (isBlocking(x + xa + width, y + ya, xa, ya)) collide = true;
|
||||
|
||||
if (avoidCliffs && onGround && !world.level.isBlocking((int) ((x + xa + width) / 16), (int) ((y) / 16 + 1), xa, 1)) collide = true;
|
||||
}
|
||||
if (xa < 0)
|
||||
{
|
||||
if (isBlocking(x + xa - width, y + ya - height, xa, ya)) collide = true;
|
||||
if (isBlocking(x + xa - width, y + ya - height / 2, xa, ya)) collide = true;
|
||||
if (isBlocking(x + xa - width, y + ya, xa, ya)) collide = true;
|
||||
|
||||
if (avoidCliffs && onGround && !world.level.isBlocking((int) ((x + xa - width) / 16), (int) ((y) / 16 + 1), xa, 1)) collide = true;
|
||||
}
|
||||
|
||||
if (collide)
|
||||
{
|
||||
if (xa < 0)
|
||||
{
|
||||
x = (int) ((x - width) / 16) * 16 + width;
|
||||
this.xa = 0;
|
||||
}
|
||||
if (xa > 0)
|
||||
{
|
||||
x = (int) ((x + width) / 16 + 1) * 16 - width - 1;
|
||||
this.xa = 0;
|
||||
}
|
||||
if (ya < 0)
|
||||
{
|
||||
y = (int) ((y - height) / 16) * 16 + height;
|
||||
jumpTime = 0;
|
||||
this.ya = 0;
|
||||
}
|
||||
if (ya > 0)
|
||||
{
|
||||
y = (int) (y / 16 + 1) * 16 - 1;
|
||||
onGround = true;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
else
|
||||
{
|
||||
x += xa;
|
||||
y += ya;
|
||||
return true;
|
||||
}
|
||||
}
|
||||
|
||||
private boolean isBlocking(float _x, float _y, float xa, float ya)
|
||||
{
|
||||
int x = (int) (_x / 16);
|
||||
int y = (int) (_y / 16);
|
||||
if (x == (int) (this.x / 16) && y == (int) (this.y / 16)) return false;
|
||||
|
||||
boolean blocking = world.level.isBlocking(x, y, xa, ya);
|
||||
|
||||
byte block = world.level.getBlock(x, y);
|
||||
|
||||
return blocking;
|
||||
}
|
||||
|
||||
public void bumpCheck(int xTile, int yTile)
|
||||
{
|
||||
if (x + width > xTile * 16 && x - width < xTile * 16 + 16 && yTile==(int)((y-1)/16))
|
||||
{
|
||||
facing = -world.mario.facing;
|
||||
ya = -10;
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
40
src/dk/itu/mario/engine/sprites/Particle.java
Normal file
40
src/dk/itu/mario/engine/sprites/Particle.java
Normal file
@@ -0,0 +1,40 @@
|
||||
package dk.itu.mario.engine.sprites;
|
||||
|
||||
import dk.itu.mario.engine.Art;
|
||||
|
||||
|
||||
public class Particle extends Sprite
|
||||
{
|
||||
public int life;
|
||||
|
||||
public Particle(int x, int y, float xa, float ya)
|
||||
{
|
||||
this(x, y, xa, ya, (int)(Math.random()*2), 0);
|
||||
}
|
||||
|
||||
public Particle(int x, int y, float xa, float ya, int xPic, int yPic)
|
||||
{
|
||||
sheet = Art.particles;
|
||||
this.x = x;
|
||||
this.y = y;
|
||||
this.xa = xa;
|
||||
this.ya = ya;
|
||||
this.xPic = xPic;
|
||||
this.yPic = yPic;
|
||||
this.xPicO = 4;
|
||||
this.yPicO = 4;
|
||||
|
||||
wPic = 8;
|
||||
hPic = 8;
|
||||
life = 10;
|
||||
}
|
||||
|
||||
public void move()
|
||||
{
|
||||
if (life--<0) Sprite.spriteContext.removeSprite(this);
|
||||
x+=xa;
|
||||
y+=ya;
|
||||
ya*=0.95f;
|
||||
ya+=3;
|
||||
}
|
||||
}
|
||||
370
src/dk/itu/mario/engine/sprites/Shell.java
Normal file
370
src/dk/itu/mario/engine/sprites/Shell.java
Normal file
@@ -0,0 +1,370 @@
|
||||
package dk.itu.mario.engine.sprites;
|
||||
|
||||
|
||||
import dk.itu.mario.engine.Art;
|
||||
import dk.itu.mario.scene.LevelScene;
|
||||
|
||||
|
||||
|
||||
|
||||
public class Shell extends Sprite
|
||||
{
|
||||
private static float GROUND_INERTIA = 0.89f;
|
||||
private static float AIR_INERTIA = 0.89f;
|
||||
|
||||
private float runTime;
|
||||
private boolean onGround = false;
|
||||
|
||||
private int width = 4;
|
||||
int height = 24;
|
||||
|
||||
private LevelScene world;
|
||||
public int facing;
|
||||
|
||||
public boolean avoidCliffs = false;
|
||||
public int anim;
|
||||
|
||||
public boolean dead = false;
|
||||
private int deadTime = 0;
|
||||
public boolean carried;
|
||||
|
||||
|
||||
public Shell(LevelScene world, float x, float y, int type)
|
||||
{
|
||||
sheet = Art.enemies;
|
||||
|
||||
this.x = x;
|
||||
this.y = y;
|
||||
this.world = world;
|
||||
xPicO = 8;
|
||||
yPicO = 31;
|
||||
|
||||
yPic = type;
|
||||
height = 12;
|
||||
facing = 0;
|
||||
wPic = 16;
|
||||
|
||||
xPic = 4;
|
||||
ya = -5;
|
||||
}
|
||||
|
||||
public boolean fireballCollideCheck(Fireball fireball)
|
||||
{
|
||||
if (deadTime != 0) return false;
|
||||
|
||||
float xD = fireball.x - x;
|
||||
float yD = fireball.y - y;
|
||||
|
||||
if (xD > -16 && xD < 16)
|
||||
{
|
||||
if (yD > -height && yD < fireball.height)
|
||||
{
|
||||
if (facing!=0) return true;
|
||||
|
||||
world.sound.play(Art.samples[Art.SAMPLE_MARIO_KICK], this, 1, 1, 1);
|
||||
|
||||
xa = fireball.facing * 2;
|
||||
ya = -5;
|
||||
if (spriteTemplate != null) spriteTemplate.isDead = true;
|
||||
deadTime = 100;
|
||||
hPic = -hPic;
|
||||
yPicO = -yPicO + 16;
|
||||
return true;
|
||||
}
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
public void collideCheck()
|
||||
{
|
||||
if (carried || dead || deadTime>0) return;
|
||||
|
||||
float xMarioD = world.mario.x - x;
|
||||
float yMarioD = world.mario.y - y;
|
||||
float w = 16;
|
||||
if (xMarioD > -16 && xMarioD < 16)
|
||||
{
|
||||
if (yMarioD > -height && yMarioD < world.mario.height)
|
||||
{
|
||||
if (world.mario.ya > 0 && yMarioD <= 0 && (!world.mario.onGround || !world.mario.wasOnGround))
|
||||
{
|
||||
world.mario.stomp(this);
|
||||
if (facing != 0)
|
||||
{
|
||||
xa = 0;
|
||||
facing = 0;
|
||||
}
|
||||
else
|
||||
{
|
||||
facing = world.mario.facing;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
if (facing != 0)
|
||||
{
|
||||
world.mario.getHurt(this);
|
||||
}
|
||||
else
|
||||
{
|
||||
world.mario.kick(this);
|
||||
facing = world.mario.facing;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public void move()
|
||||
{
|
||||
if (y > world.level.getHeight() * 16 + 16 && deadTime == 0)
|
||||
{
|
||||
die();
|
||||
spriteContext.removeSprite(this);
|
||||
return;
|
||||
}
|
||||
|
||||
if (carried)
|
||||
{
|
||||
world.checkShellCollide(this);
|
||||
return;
|
||||
}
|
||||
|
||||
if (deadTime > 0)
|
||||
{
|
||||
deadTime--;
|
||||
|
||||
if (deadTime == 0)
|
||||
{
|
||||
deadTime = 1;
|
||||
for (int i = 0; i < 8; i++)
|
||||
{
|
||||
world.addSprite(new Sparkle((int) (x + Math.random() * 16 - 8) + 4, (int) (y - Math.random() * 8) + 4, (float) (Math.random() * 2 - 1), (float) Math.random() * -1, 0, 1, 5));
|
||||
}
|
||||
spriteContext.removeSprite(this);
|
||||
}
|
||||
|
||||
x += xa;
|
||||
y += ya;
|
||||
ya *= 0.95;
|
||||
ya += 1;
|
||||
|
||||
return;
|
||||
}
|
||||
|
||||
if (facing != 0) anim++;
|
||||
|
||||
float sideWaysSpeed = 11f;
|
||||
// float sideWaysSpeed = onGround ? 2.5f : 1.2f;
|
||||
|
||||
if (xa > 2)
|
||||
{
|
||||
facing = 1;
|
||||
}
|
||||
if (xa < -2)
|
||||
{
|
||||
facing = -1;
|
||||
}
|
||||
|
||||
xa = facing * sideWaysSpeed;
|
||||
|
||||
if (facing != 0)
|
||||
{
|
||||
world.checkShellCollide(this);
|
||||
}
|
||||
|
||||
xFlipPic = facing == -1;
|
||||
|
||||
runTime += (Math.abs(xa)) + 5;
|
||||
|
||||
xPic = (anim / 2) % 4 + 3;
|
||||
|
||||
|
||||
|
||||
if (!move(xa, 0))
|
||||
{
|
||||
world.sound.play(Art.samples[Art.SAMPLE_SHELL_BUMP], this, 1, 1, 1);
|
||||
|
||||
facing = -facing;
|
||||
}
|
||||
onGround = false;
|
||||
move(0, ya);
|
||||
|
||||
ya *= 0.85f;
|
||||
if (onGround)
|
||||
{
|
||||
xa *= GROUND_INERTIA;
|
||||
}
|
||||
else
|
||||
{
|
||||
xa *= AIR_INERTIA;
|
||||
}
|
||||
|
||||
if (!onGround)
|
||||
{
|
||||
ya += 2;
|
||||
}
|
||||
}
|
||||
|
||||
private boolean move(float xa, float ya)
|
||||
{
|
||||
while (xa > 8)
|
||||
{
|
||||
if (!move(8, 0)) return false;
|
||||
xa -= 8;
|
||||
}
|
||||
while (xa < -8)
|
||||
{
|
||||
if (!move(-8, 0)) return false;
|
||||
xa += 8;
|
||||
}
|
||||
while (ya > 8)
|
||||
{
|
||||
if (!move(0, 8)) return false;
|
||||
ya -= 8;
|
||||
}
|
||||
while (ya < -8)
|
||||
{
|
||||
if (!move(0, -8)) return false;
|
||||
ya += 8;
|
||||
}
|
||||
|
||||
boolean collide = false;
|
||||
if (ya > 0)
|
||||
{
|
||||
if (isBlocking(x + xa - width, y + ya, xa, 0)) collide = true;
|
||||
else if (isBlocking(x + xa + width, y + ya, xa, 0)) collide = true;
|
||||
else if (isBlocking(x + xa - width, y + ya + 1, xa, ya)) collide = true;
|
||||
else if (isBlocking(x + xa + width, y + ya + 1, xa, ya)) collide = true;
|
||||
}
|
||||
if (ya < 0)
|
||||
{
|
||||
if (isBlocking(x + xa, y + ya - height, xa, ya)) collide = true;
|
||||
else if (collide || isBlocking(x + xa - width, y + ya - height, xa, ya)) collide = true;
|
||||
else if (collide || isBlocking(x + xa + width, y + ya - height, xa, ya)) collide = true;
|
||||
}
|
||||
if (xa > 0)
|
||||
{
|
||||
if (isBlocking(x + xa + width, y + ya - height, xa, ya)) collide = true;
|
||||
if (isBlocking(x + xa + width, y + ya - height / 2, xa, ya)) collide = true;
|
||||
if (isBlocking(x + xa + width, y + ya, xa, ya)) collide = true;
|
||||
|
||||
if (avoidCliffs && onGround && !world.level.isBlocking((int) ((x + xa + width) / 16), (int) ((y) / 16 + 1), xa, 1)) collide = true;
|
||||
}
|
||||
if (xa < 0)
|
||||
{
|
||||
if (isBlocking(x + xa - width, y + ya - height, xa, ya)) collide = true;
|
||||
if (isBlocking(x + xa - width, y + ya - height / 2, xa, ya)) collide = true;
|
||||
if (isBlocking(x + xa - width, y + ya, xa, ya)) collide = true;
|
||||
|
||||
if (avoidCliffs && onGround && !world.level.isBlocking((int) ((x + xa - width) / 16), (int) ((y) / 16 + 1), xa, 1)) collide = true;
|
||||
}
|
||||
|
||||
if (collide)
|
||||
{
|
||||
if (xa < 0)
|
||||
{
|
||||
x = (int) ((x - width) / 16) * 16 + width;
|
||||
this.xa = 0;
|
||||
}
|
||||
if (xa > 0)
|
||||
{
|
||||
x = (int) ((x + width) / 16 + 1) * 16 - width - 1;
|
||||
this.xa = 0;
|
||||
}
|
||||
if (ya < 0)
|
||||
{
|
||||
y = (int) ((y - height) / 16) * 16 + height;
|
||||
this.ya = 0;
|
||||
}
|
||||
if (ya > 0)
|
||||
{
|
||||
y = (int) (y / 16 + 1) * 16 - 1;
|
||||
onGround = true;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
else
|
||||
{
|
||||
x += xa;
|
||||
y += ya;
|
||||
return true;
|
||||
}
|
||||
}
|
||||
|
||||
private boolean isBlocking(float _x, float _y, float xa, float ya)
|
||||
{
|
||||
int x = (int) (_x / 16);
|
||||
int y = (int) (_y / 16);
|
||||
if (x == (int) (this.x / 16) && y == (int) (this.y / 16)) return false;
|
||||
|
||||
boolean blocking = world.level.isBlocking(x, y, xa, ya);
|
||||
|
||||
byte block = world.level.getBlock(x, y);
|
||||
|
||||
if (blocking && ya == 0 && xa!=0)
|
||||
{
|
||||
world.bump(x, y, true);
|
||||
}
|
||||
|
||||
return blocking;
|
||||
}
|
||||
|
||||
public void bumpCheck(int xTile, int yTile)
|
||||
{
|
||||
if (x + width > xTile * 16 && x - width < xTile * 16 + 16 && yTile == (int) ((y - 1) / 16))
|
||||
{
|
||||
facing = -world.mario.facing;
|
||||
ya = -10;
|
||||
}
|
||||
}
|
||||
|
||||
public void die()
|
||||
{
|
||||
dead = true;
|
||||
|
||||
carried = false;
|
||||
|
||||
xa = -facing * 2;
|
||||
ya = -5;
|
||||
deadTime = 100;
|
||||
|
||||
if(world.recorder != null)
|
||||
world.recorder.killRecord(this);
|
||||
}
|
||||
|
||||
public boolean shellCollideCheck(Shell shell)
|
||||
{
|
||||
if (deadTime != 0) return false;
|
||||
|
||||
float xD = shell.x - x;
|
||||
float yD = shell.y - y;
|
||||
|
||||
if (xD > -16 && xD < 16)
|
||||
{
|
||||
if (yD > -height && yD < shell.height)
|
||||
{
|
||||
world.sound.play(Art.samples[Art.SAMPLE_MARIO_KICK], this, 1, 1, 1);
|
||||
|
||||
if (world.mario.carried == shell || world.mario.carried == this)
|
||||
{
|
||||
world.mario.carried = null;
|
||||
}
|
||||
|
||||
die();
|
||||
shell.die();
|
||||
|
||||
return true;
|
||||
}
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
|
||||
public void release(Mario mario)
|
||||
{
|
||||
carried = false;
|
||||
facing = mario.facing;
|
||||
x += facing * 8;
|
||||
}
|
||||
}
|
||||
46
src/dk/itu/mario/engine/sprites/Sparkle.java
Normal file
46
src/dk/itu/mario/engine/sprites/Sparkle.java
Normal file
@@ -0,0 +1,46 @@
|
||||
package dk.itu.mario.engine.sprites;
|
||||
|
||||
import dk.itu.mario.engine.Art;
|
||||
|
||||
|
||||
public class Sparkle extends Sprite
|
||||
{
|
||||
public int life;
|
||||
public int xPicStart;
|
||||
|
||||
public Sparkle(int x, int y, float xa, float ya)
|
||||
{
|
||||
this(x, y, xa, ya, (int)(Math.random()*2), 0, 5);
|
||||
}
|
||||
|
||||
public Sparkle(int x, int y, float xa, float ya, int xPic, int yPic, int timeSpan)
|
||||
{
|
||||
sheet = Art.particles;
|
||||
this.x = x;
|
||||
this.y = y;
|
||||
this.xa = xa;
|
||||
this.ya = ya;
|
||||
this.xPic = xPic;
|
||||
xPicStart = xPic;
|
||||
this.yPic = yPic;
|
||||
this.xPicO = 4;
|
||||
this.yPicO = 4;
|
||||
|
||||
wPic = 8;
|
||||
hPic = 8;
|
||||
life = 10+(int)(Math.random()*timeSpan);
|
||||
}
|
||||
|
||||
public void move()
|
||||
{
|
||||
if (life>10)
|
||||
xPic = 7;
|
||||
else
|
||||
xPic = xPicStart+(10-life)*4/10;
|
||||
|
||||
if (life--<0) Sprite.spriteContext.removeSprite(this);
|
||||
|
||||
x+=xa;
|
||||
y+=ya;
|
||||
}
|
||||
}
|
||||
117
src/dk/itu/mario/engine/sprites/Sprite.java
Normal file
117
src/dk/itu/mario/engine/sprites/Sprite.java
Normal file
@@ -0,0 +1,117 @@
|
||||
package dk.itu.mario.engine.sprites;
|
||||
|
||||
import java.awt.Graphics;
|
||||
import java.awt.Image;
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
import dk.itu.mario.engine.sonar.SoundSource;
|
||||
|
||||
public class Sprite implements SoundSource
|
||||
{
|
||||
public static SpriteContext spriteContext;
|
||||
|
||||
public float xOld, yOld, x, y, xa, ya;
|
||||
|
||||
public int xPic, yPic;
|
||||
public int wPic = 32;
|
||||
public int hPic = 32;
|
||||
public int xPicO, yPicO;
|
||||
public boolean xFlipPic = false;
|
||||
public boolean yFlipPic = false;
|
||||
public Image[][] sheet;
|
||||
public boolean visible = true;
|
||||
|
||||
public int layer = 1;
|
||||
|
||||
public SpriteTemplate spriteTemplate;
|
||||
|
||||
public void move()
|
||||
{
|
||||
x+=xa;
|
||||
y+=ya;
|
||||
}
|
||||
|
||||
public void render(Graphics og, float alpha)
|
||||
{
|
||||
if (!visible) return;
|
||||
|
||||
int xPixel = (int)(xOld+(x-xOld)*alpha)-xPicO;
|
||||
int yPixel = (int)(yOld+(y-yOld)*alpha)-yPicO;
|
||||
|
||||
og.drawImage(sheet[xPic][yPic], xPixel+(xFlipPic?wPic:0), yPixel+(yFlipPic?hPic:0), xFlipPic?-wPic:wPic, yFlipPic?-hPic:hPic, null);
|
||||
}
|
||||
|
||||
/* private void blit(Graphics og, Image bitmap, int x0, int y0, int x1, int y1, int w, int h)
|
||||
{
|
||||
if (!xFlipPic)
|
||||
{
|
||||
if (!yFlipPic)
|
||||
{
|
||||
og.drawImage(bitmap, x0, y0, x0+w, y0+h, x1, y1, x1+w, y1+h, null);
|
||||
}
|
||||
else
|
||||
{
|
||||
og.drawImage(bitmap, x0, y0, x0+w, y0+h, x1, y1+h, x1+w, y1, null);
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
if (!yFlipPic)
|
||||
{
|
||||
og.drawImage(bitmap, x0, y0, x0+w, y0+h, x1+w, y1, x1, y1+h, null);
|
||||
}
|
||||
else
|
||||
{
|
||||
og.drawImage(bitmap, x0, y0, x0+w, y0+h, x1+w, y1+h, x1, y1, null);
|
||||
}
|
||||
}
|
||||
}*/
|
||||
|
||||
public final void tick()
|
||||
{
|
||||
xOld = x;
|
||||
yOld = y;
|
||||
move();
|
||||
}
|
||||
|
||||
public final void tickNoMove()
|
||||
{
|
||||
xOld = x;
|
||||
yOld = y;
|
||||
}
|
||||
|
||||
public float getX(float alpha)
|
||||
{
|
||||
return (xOld+(x-xOld)*alpha)-xPicO;
|
||||
}
|
||||
|
||||
public float getY(float alpha)
|
||||
{
|
||||
return (yOld+(y-yOld)*alpha)-yPicO;
|
||||
}
|
||||
|
||||
public void collideCheck()
|
||||
{
|
||||
}
|
||||
|
||||
public void bumpCheck(int xTile, int yTile)
|
||||
{
|
||||
}
|
||||
|
||||
public boolean shellCollideCheck(Shell shell)
|
||||
{
|
||||
return false;
|
||||
}
|
||||
|
||||
public void release(Mario mario)
|
||||
{
|
||||
}
|
||||
|
||||
public boolean fireballCollideCheck(Fireball fireball)
|
||||
{
|
||||
return false;
|
||||
}
|
||||
}
|
||||
18
src/dk/itu/mario/engine/sprites/SpriteContext.java
Normal file
18
src/dk/itu/mario/engine/sprites/SpriteContext.java
Normal file
@@ -0,0 +1,18 @@
|
||||
package dk.itu.mario.engine.sprites;
|
||||
|
||||
/**
|
||||
* <p>Title: </p>
|
||||
*
|
||||
* <p>Description: </p>
|
||||
*
|
||||
* <p>Copyright: Copyright (c) 2010</p>
|
||||
*
|
||||
* <p>Company: </p>
|
||||
*
|
||||
* @author not attributable
|
||||
* @version 1.0
|
||||
*/
|
||||
public interface SpriteContext {
|
||||
public void addSprite(Sprite sprite);
|
||||
public void removeSprite(Sprite sprite);
|
||||
}
|
||||
60
src/dk/itu/mario/engine/sprites/SpriteTemplate.java
Normal file
60
src/dk/itu/mario/engine/sprites/SpriteTemplate.java
Normal file
@@ -0,0 +1,60 @@
|
||||
package dk.itu.mario.engine.sprites;
|
||||
|
||||
import dk.itu.mario.scene.LevelScene;
|
||||
|
||||
public class SpriteTemplate
|
||||
{
|
||||
public static final int RED_TURTLE = 0;
|
||||
public static final int GREEN_TURTLE = 1;
|
||||
public static final int GOOMPA = 2;
|
||||
public static final int ARMORED_TURTLE = 3;
|
||||
public static final int JUMP_FLOWER = 4;
|
||||
public static final int CANNON_BALL = 5;
|
||||
public static final int CHOMP_FLOWER = 6;
|
||||
|
||||
public static int enemiesSpawned = 0;
|
||||
public static int enemiesMax = 1000;
|
||||
|
||||
public boolean hasSpawned = false;
|
||||
|
||||
public int lastVisibleTick = -1;
|
||||
public Sprite sprite;
|
||||
public boolean isDead = false;
|
||||
private boolean winged;
|
||||
|
||||
public int type;
|
||||
public int direction = 1;
|
||||
|
||||
public SpriteTemplate(int type, boolean winged)
|
||||
{
|
||||
this.type = type;
|
||||
this.winged = winged;
|
||||
}
|
||||
|
||||
public void spawn(LevelScene world, int x, int y, int dir)
|
||||
{
|
||||
if (isDead || enemiesSpawned >= enemiesMax) return;
|
||||
|
||||
if (type==Enemy.ENEMY_FLOWER)
|
||||
{
|
||||
sprite = new FlowerEnemy(world, x*16+15, y*16+24);
|
||||
}
|
||||
else
|
||||
{
|
||||
sprite = new Enemy(world, x*16+8, y*16+15, dir, type, winged);
|
||||
}
|
||||
|
||||
//correct for flipping
|
||||
if(direction == -1){
|
||||
sprite.x -= 14;
|
||||
}
|
||||
|
||||
sprite.spriteTemplate = this;
|
||||
world.addSprite(sprite);
|
||||
|
||||
if(!hasSpawned)
|
||||
enemiesSpawned++;
|
||||
|
||||
hasSpawned = true;
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user