mirror of
https://github.com/2006-Scape/2006Scape.git
synced 2026-07-03 00:31:51 +00:00
8af938548b
- Dwarf cannon can now be seen by anyone and not just the person who sets it down (they can also see the rotation now) - Fixed doors being removed when clicking them - Removed banking command for regular players - Fixed nulodion now only gives if you have space - Updated nulodion message so it doesnt say to find him at home - Npcs wont follow you if you turn on the cantAttack comamand (for admins - Fixed gate at KBD - Fixed the gates at Ice giants in wildy #closes 132 #closes 203 #closes 211 #closes 6 also this one should be closed from previous patch #closes 219
524 lines
14 KiB
Java
524 lines
14 KiB
Java
package com.rebotted.game.content.combat.range;
|
|
|
|
import com.rebotted.GameEngine;
|
|
import com.rebotted.event.CycleEvent;
|
|
import com.rebotted.event.CycleEventContainer;
|
|
import com.rebotted.event.CycleEventHandler;
|
|
import com.rebotted.game.content.combat.CombatConstants;
|
|
import com.rebotted.game.npcs.Npc;
|
|
import com.rebotted.game.npcs.NpcHandler;
|
|
import com.rebotted.game.objects.Objects;
|
|
import com.rebotted.game.players.Client;
|
|
import com.rebotted.game.players.Player;
|
|
import com.rebotted.game.players.PlayerHandler;
|
|
import com.rebotted.util.Misc;
|
|
import com.rebotted.world.clip.Region;
|
|
|
|
/**
|
|
* Cannon
|
|
* @author Andrew (Mr Extremez)
|
|
*/
|
|
|
|
public class DwarfCannon {
|
|
|
|
public DwarfCannon(Player player2) {
|
|
this.player = player2;
|
|
}
|
|
|
|
private Player player;
|
|
|
|
public final int[] ITEM_PARTS = {6, 8, 10, 12};
|
|
|
|
private final int[] OBJECT_PARTS = {7, 8, 9, 6};
|
|
|
|
private final int ballsID = 2;
|
|
|
|
public boolean settingUp = false;
|
|
|
|
private int setUpStage = 0;
|
|
|
|
private int maxBalls = 30;
|
|
|
|
public int myBalls = 0;
|
|
|
|
private boolean rotating = false;
|
|
|
|
private int rotation = 0;
|
|
|
|
private int maxHit = 30;
|
|
|
|
private final int maxDistance = 20;
|
|
|
|
private int totalRotations = 0;
|
|
|
|
private boolean justClicked = false;
|
|
|
|
public void placeCannon() {
|
|
if (settingUp == true) {
|
|
return;
|
|
}
|
|
if (noSetUpArea()) {
|
|
player.getPacketSender().sendMessage("You are not allowed to set up a cannon here!");
|
|
return;
|
|
}
|
|
if (hasCannon()) {
|
|
player.getPacketSender().sendMessage("You already have a cannon placed!");
|
|
return;
|
|
}
|
|
if (nearCannon()) {
|
|
player.getPacketSender().sendMessage("You must be farther away from an existing cannon to set a new one up!");
|
|
return;
|
|
}
|
|
if (!canSetUp()) {
|
|
player.getPacketSender().sendMessage("You need all the parts of the cannon to set a cannon up.");
|
|
return;
|
|
}
|
|
for (int i = 0; i < 50; i++) {
|
|
if (GameEngine.cannonsX[i] == 0 && GameEngine.cannonsY[i] == 0) {
|
|
GameEngine.cannonsX[i] = player.absX;
|
|
GameEngine.cannonsY[i] = player.absY;
|
|
break;
|
|
}
|
|
}
|
|
CycleEventHandler.getSingleton().addEvent(player, new CycleEvent() {
|
|
@Override
|
|
public void execute(CycleEventContainer container) {
|
|
if (setUpStage >= 4) {
|
|
container.stop();
|
|
setUpStage = 0;
|
|
settingUp = false;
|
|
return;
|
|
}
|
|
if (!canSetUp()) {
|
|
player.getPacketSender().sendMessage("You need all the parts of the cannon to set a cannon up.");
|
|
container.stop();
|
|
return;
|
|
}
|
|
settingUp = true;
|
|
player.startAnimation(827);
|
|
player.turnPlayerTo(player.absX, player.absY);
|
|
player.cannonX = player.absX;
|
|
player.cannonY = player.absY;
|
|
placeObject(OBJECT_PARTS[setUpStage], player.absX, player.absY, true);
|
|
player.getItemAssistant().deleteItem(ITEM_PARTS[setUpStage], 1);
|
|
setUpStage ++;
|
|
}
|
|
@Override
|
|
public void stop() {
|
|
/**
|
|
* Balls
|
|
*/
|
|
int cballs = getBalls();
|
|
int amount = cballs - myBalls;
|
|
player.getItemAssistant().deleteItem(ballsID, player.getItemAssistant().getItemSlot(ballsID), amount);
|
|
myBalls = cballs;
|
|
}
|
|
}, 2);
|
|
}
|
|
|
|
public boolean needsCannon() {
|
|
return (player.lostCannon == true);
|
|
}
|
|
|
|
public void loginCheck() {
|
|
if (needsCannon()) {
|
|
player.getPacketSender().sendMessage("@red@You can collect your cannon from Nulodion.");
|
|
}
|
|
}
|
|
|
|
private boolean canSetUp() {
|
|
if (setUpStage == 0) {
|
|
if (player.getItemAssistant().playerHasItem(ITEM_PARTS[0]) && player.getItemAssistant().playerHasItem(ITEM_PARTS[1]) && player.getItemAssistant().playerHasItem(ITEM_PARTS[2]) && player.getItemAssistant().playerHasItem(ITEM_PARTS[3])) {
|
|
return true;
|
|
}
|
|
} else if (setUpStage == 1) {
|
|
if (player.getItemAssistant().playerHasItem(ITEM_PARTS[1]) && player.getItemAssistant().playerHasItem(ITEM_PARTS[2]) && player.getItemAssistant().playerHasItem(ITEM_PARTS[3])) {
|
|
return true;
|
|
}
|
|
} else if (setUpStage == 2) {
|
|
if (player.getItemAssistant().playerHasItem(ITEM_PARTS[2]) && player.getItemAssistant().playerHasItem(ITEM_PARTS[3])) {
|
|
return true;
|
|
}
|
|
} else if (setUpStage == 3) {
|
|
if (player.getItemAssistant().playerHasItem(ITEM_PARTS[3])) {
|
|
return true;
|
|
}
|
|
}
|
|
return false;
|
|
}
|
|
|
|
public boolean hasCannon() {
|
|
return (player.cannonX > 0) && (player.cannonY > 0) || (player.cannonX > 0 && player.cannonY > 0);
|
|
}
|
|
|
|
private boolean myCannon(int x, int y) {
|
|
return (player.cannonX == x) && (player.cannonY == y);
|
|
}
|
|
|
|
public int getBalls() {
|
|
int cannonBalls = player.getItemAssistant().getItemAmount(ballsID);
|
|
if (cannonBalls >= maxBalls) {
|
|
return maxBalls;
|
|
}
|
|
return cannonBalls;
|
|
}
|
|
|
|
public boolean nearCannon() {
|
|
for(int i = 0; i < GameEngine.cannonsX.length; i++) {
|
|
if ((player.absX >= GameEngine.cannonsX[i] - 1) && (player.absX <= GameEngine.cannonsX[i] + 1) && (player.absY >= GameEngine.cannonsY[i] - 2) && (player.absY <= GameEngine.cannonsY[i] + 1)) {
|
|
return true;
|
|
}
|
|
}
|
|
return false;
|
|
}
|
|
|
|
public void loadCannons() {
|
|
for(int i = 0; i < GameEngine.cannonsX.length; i++) {
|
|
if (GameEngine.cannonsX[i] != 0) {
|
|
player.getPacketSender().checkObjectSpawn(6, GameEngine.cannonsX[i], GameEngine.cannonsY[i], 0, 10);
|
|
}
|
|
}
|
|
}
|
|
|
|
public void loadCannon(int x, int y) {
|
|
int cballs = getBalls();
|
|
if (!myCannon(x, y)) {
|
|
player.getPacketSender().sendMessage("You can't load somebody else's cannon!");
|
|
return;
|
|
}
|
|
if (myBalls <= 29) {
|
|
int amount = cballs - myBalls;
|
|
player.getItemAssistant().deleteItem(ballsID, player.getItemAssistant().getItemSlot(ballsID), amount);
|
|
myBalls = cballs;
|
|
if (player.getItemAssistant().playerHasItem(ballsID)) {
|
|
player.getPacketSender().sendMessage(amount > 1 ? "You load the cannon with " + amount + " cannonballs." : "You load the cannon with 1 cannonball.");
|
|
} else {
|
|
player.getPacketSender().sendMessage("You have no cannonballs to load into the cannon.");
|
|
}
|
|
}
|
|
}
|
|
|
|
public void clickCannon(int x, int y) {
|
|
if (!myCannon(x, y)) {
|
|
player.getPacketSender().sendMessage("You can't fire somebody else's cannon!");
|
|
return;
|
|
}
|
|
if (myBalls == 0) {
|
|
player.getPacketSender().sendMessage("Your cannon has run out of cannonballs.");
|
|
return;
|
|
}
|
|
if (myBalls >= 1 && rotating == false) {
|
|
shoot();
|
|
} else if (myBalls >= 1 && rotating == true) {
|
|
player.getPacketSender().sendMessage("Your cannon is already shooting.");
|
|
}
|
|
}
|
|
|
|
public void handleDisconnect() {
|
|
removeObject(player.cannonX, player.cannonY);
|
|
for(int i = 0; i < GameEngine.cannonsX.length; i++) {
|
|
if (GameEngine.cannonsX[i] == player.cannonX && GameEngine.cannonsY[i] == player.cannonY) {
|
|
GameEngine.cannonsX[i] = 0;
|
|
GameEngine.cannonsY[i] = 0;
|
|
GameEngine.cannonsO[i] = null;
|
|
}
|
|
}
|
|
}
|
|
|
|
public void handleDeath() {
|
|
if (hasCannon()) {
|
|
player.lostCannon = true;
|
|
removeObject(player.cannonX, player.cannonY);
|
|
for(int i = 0; i < GameEngine.cannonsX.length; i++) {
|
|
if (GameEngine.cannonsX[i] == player.cannonX && GameEngine.cannonsY[i] == player.cannonY) {
|
|
GameEngine.cannonsX[i] = 0;
|
|
GameEngine.cannonsY[i] = 0;
|
|
GameEngine.cannonsO[i] = null;
|
|
}
|
|
}
|
|
player.cannonX = 0;
|
|
player.cannonY = 0;
|
|
}
|
|
}
|
|
|
|
public void shoot() {
|
|
if (justClicked == true) {
|
|
return;
|
|
}
|
|
rotating = true;
|
|
justClicked = true;
|
|
CycleEventHandler.getSingleton().addEvent(player, new CycleEvent() {
|
|
@Override
|
|
public void execute(CycleEventContainer e) {
|
|
totalRotations += 1;
|
|
if (totalRotations >= 2) {
|
|
justClicked = false;
|
|
}
|
|
if(rotating == false) {
|
|
e.stop();
|
|
}
|
|
if (myBalls < 1) {
|
|
rotating = false;
|
|
e.stop();
|
|
}
|
|
if (rotating == true) {
|
|
rotation += 1;
|
|
rotateCannon();
|
|
shootNpcs();
|
|
}
|
|
}
|
|
@Override
|
|
public void stop() {
|
|
|
|
}
|
|
}, 2);
|
|
}
|
|
|
|
private void rotateCannon() {
|
|
switch (rotation) {
|
|
case 1: //north
|
|
player.getPlayerAssistant().objectAnim(player.cannonX, player.cannonY, 516, 10, -1);
|
|
break;
|
|
case 2: //north-east
|
|
player.getPlayerAssistant().objectAnim(player.cannonX, player.cannonY, 517, 10, -1);
|
|
break;
|
|
case 3: //east
|
|
player.getPlayerAssistant().objectAnim(player.cannonX, player.cannonY, 518, 10, -1);
|
|
break;
|
|
case 4: //south-east
|
|
player.getPlayerAssistant().objectAnim(player.cannonX, player.cannonY, 519, 10, -1);
|
|
break;
|
|
case 5: //south
|
|
player.getPlayerAssistant().objectAnim(player.cannonX, player.cannonY, 520, 10, -1);
|
|
break;
|
|
case 6: //south-west
|
|
player.getPlayerAssistant().objectAnim(player.cannonX, player.cannonY, 521, 10, -1);
|
|
break;
|
|
case 7: //west
|
|
player.getPlayerAssistant().objectAnim(player.cannonX, player.cannonY, 514, 10, -1);
|
|
break;
|
|
case 8: //north-west
|
|
player.getPlayerAssistant().objectAnim(player.cannonX, player.cannonY, 515, 10, -1);
|
|
rotation = 0;
|
|
break;
|
|
}
|
|
}
|
|
|
|
public void removeCannon(int x, int y) {
|
|
for (int i = 0; i < GameEngine.cannonsX.length; i++) {
|
|
if (GameEngine.cannonsX[i] == x && GameEngine.cannonsY[i] == y) {
|
|
GameEngine.cannonsX[i] = 0;
|
|
GameEngine.cannonsY[i] = 0;
|
|
break;
|
|
}
|
|
}
|
|
}
|
|
|
|
public void pickup(int x, int y) {
|
|
if (!myCannon(x, y)) {
|
|
player.getPacketSender().sendMessage("You can't pick up somebody else's cannon!");
|
|
return;
|
|
}
|
|
if (rotating == true) {
|
|
rotating = false;
|
|
}
|
|
if (player.getItemAssistant().freeSlots() > 3) {
|
|
player.startAnimation(827);
|
|
player.getPacketSender().sendMessage("You pick up the cannon. It's really heavy.");
|
|
removeCannon(player.cannonX, player.cannonY);
|
|
player.getItemAssistant().addItem(ITEM_PARTS[0], 1);
|
|
player.getItemAssistant().addItem(ITEM_PARTS[1], 1);
|
|
player.getItemAssistant().addItem(ITEM_PARTS[2], 1);
|
|
player.getItemAssistant().addItem(ITEM_PARTS[3], 1);
|
|
} else {
|
|
player.getPacketSender().sendMessage("You don't have enough free inventory slots to do that.");
|
|
}
|
|
if (myBalls > 0) {
|
|
player.getItemAssistant().addItem(ballsID, myBalls);
|
|
myBalls = 0;
|
|
}
|
|
removeObject(player.cannonX, player.cannonY);
|
|
player.cannonX = 0;
|
|
player.cannonY = 0;
|
|
player.cannonX = 0;
|
|
player.cannonY = 0;
|
|
}
|
|
|
|
public void placeObject(int id, int x, int y, boolean add) {
|
|
GameEngine.objectHandler.placeObject(new Objects(id, x, y, 0, 516, 10, 0));
|
|
if (add)
|
|
Region.addObject(id, x, y, 0, 10, 516, true);
|
|
}
|
|
|
|
public void removeObject(int x, int y) {
|
|
placeObject(-1, x, y, false);
|
|
}
|
|
|
|
public boolean noSetUpArea() {
|
|
return player.inBank() || player.inFightCaves();
|
|
}
|
|
|
|
private int getHit() {
|
|
int hits = Misc.random(2);
|
|
switch (hits) {
|
|
case 0:
|
|
return Misc.random(maxHit);
|
|
case 1:
|
|
return 15+Misc.random(maxHit-15);
|
|
case 2:
|
|
return 10+Misc.random(maxHit-10);
|
|
}
|
|
return 0;
|
|
}
|
|
|
|
public void shootNpcs() {
|
|
int damage = getHit();
|
|
Npc target = targetNpc();
|
|
if (target != null) {
|
|
if (damage > target.HP) {
|
|
damage = target.HP;
|
|
}
|
|
if (!player.inMulti()) {
|
|
if (target.underAttackBy > 0 && target.underAttackBy != player.playerId) {
|
|
return;
|
|
}
|
|
if (player.underAttackBy2 > 0 && player.underAttackBy2 != target.npcId) {
|
|
return;
|
|
}
|
|
}
|
|
cannonProjectile(target);
|
|
target.hitDiff2 = damage;
|
|
target.HP -= damage;
|
|
player.globalDamageDealt += damage;
|
|
target.killerId = player.playerId;
|
|
target.killedBy = player.playerId;
|
|
target.facePlayer(player.playerId);
|
|
target.hitUpdateRequired2 = true;
|
|
target.updateRequired = true;
|
|
myBalls -= 1;
|
|
player.getPlayerAssistant().addSkillXP(damage * CombatConstants.RANGE_EXP_RATE, player.playerRanged);
|
|
}
|
|
}
|
|
|
|
|
|
private Npc targetNpc() {
|
|
for (int i = 0; i < NpcHandler.MAX_NPCS; i++) {
|
|
Npc npc = NpcHandler.npcs[i];
|
|
if (npc == null || npc.heightLevel != player.heightLevel || !canAttackSlayer(i)) {
|
|
continue;
|
|
}
|
|
int myX = player.cannonX;
|
|
int myY = player.cannonY;
|
|
int theirX = npc.absX;
|
|
int theirY = npc.absY;
|
|
|
|
|
|
|
|
if (!npc.isDead && !npc.isDead && npc.HP != 0 && npc.npcType != 1266 && npc.npcType != 1268 && inDistance(theirX, theirY)) {
|
|
switch (rotation) {
|
|
case 1:
|
|
if (theirY > myY && theirX >= myX - 1 && theirX <= myX + 1) {
|
|
return npc;
|
|
}
|
|
break;
|
|
case 2:
|
|
if (theirX >= myX + 1 && theirY >= myY + 1) {
|
|
return npc;
|
|
}
|
|
break;
|
|
case 3:
|
|
if (theirX > myX && theirY >= myY - 1 && theirY <= myY + 1) {
|
|
return npc;
|
|
}
|
|
break;
|
|
case 4:
|
|
if (theirY <= myY - 1 && theirX >= myX + 1) {
|
|
return npc;
|
|
}
|
|
break;
|
|
case 5:
|
|
if (theirY < myY && theirX >= myX - 1 && theirX <= myX + 1) {
|
|
return npc;
|
|
}
|
|
break;
|
|
case 6:
|
|
if (theirX <= myX - 1 && theirY <= myY - 1) {
|
|
return npc;
|
|
}
|
|
break;
|
|
case 7:
|
|
if (theirX < myX && theirY >= myY - 1 && theirY <= myY + 1) {
|
|
return npc;
|
|
}
|
|
break;
|
|
case 8:
|
|
if (theirX <= myX - 1 && theirY >= myY + 1) {
|
|
return npc;
|
|
}
|
|
break;
|
|
}
|
|
}
|
|
}
|
|
return null;
|
|
}
|
|
|
|
public boolean inDistance(int npcX, int npcY) {
|
|
return (npcX >= player.cannonX - maxDistance && npcX <= player.cannonX + maxDistance && npcY >= player.cannonY - maxDistance && npcY <= player.cannonY + maxDistance);
|
|
}
|
|
|
|
public boolean canAttackSlayer(int i){
|
|
return player.playerLevel[player.playerSlayer] >= player.getSlayer().getRequiredLevel(NpcHandler.npcs[i].npcType);
|
|
}
|
|
|
|
private void cannonProjectile(Npc n) {
|
|
int oX = player.cannonX+getShootXPos();
|
|
int oY = player.cannonY+getShootYPos();
|
|
int offX = ((oX - n.absX) * -1);
|
|
int offY = ((oY - n.absY) * -1);
|
|
player.getPlayerAssistant().createPlayersProjectile(oX, oY, offY, offX, 50, 60, 53, 20, 20, -player.oldNpcIndex + 1, 30);
|
|
}
|
|
|
|
public int getShootXPos() {
|
|
switch(rotation) {
|
|
case 1:
|
|
return 1;
|
|
case 2:
|
|
return 2;
|
|
case 3:
|
|
return 2;
|
|
case 4:
|
|
return 2;
|
|
case 5:
|
|
return 1;
|
|
case 6:
|
|
return 0;
|
|
case 7:
|
|
return 0;
|
|
case 8:
|
|
return 0;
|
|
}
|
|
return 0;
|
|
}
|
|
|
|
public int getShootYPos() {
|
|
switch(rotation) {
|
|
case 1:
|
|
return 2;
|
|
case 2:
|
|
return 2;
|
|
case 3:
|
|
return 1;
|
|
case 4:
|
|
return 0;
|
|
case 5:
|
|
return 0;
|
|
case 6:
|
|
return 0;
|
|
case 7:
|
|
return 1;
|
|
case 8:
|
|
return 2;
|
|
}
|
|
return 0;
|
|
}
|
|
} |