From 73bef32efb6b1f11175f73b31cd65d59fdb4823c Mon Sep 17 00:00:00 2001 From: Treeku Date: Sat, 29 Mar 2014 03:15:04 +0000 Subject: [PATCH 01/15] Player flag is set when you align to a faction -> When you join a faction, #16 is set to true. When you go combatant, #32 is set to true. The resulting flag: 48 When you go SF, #1, #2 and #4 are set to true. The resulting flag: 55 When you go back to combatant, #1, #2 and #4 are set to false. The resulting flag: 48 The error was either in the Player flag not being set anywhere, or setPvpStatus setting it instead of doing OR/XOR operations. (The result of this would be bit #16 wouldn't be set to true, meaning SF would be 39 instead of 55) We could still set all of the flags to true for SF without harm for safety, it just wasn't theoretically necessary. Additionally any players that login automatically were getting #16 sent to the client by sendBaselines() regardless of if they had a faction, which should now be fixed. --- scripts/commands/pvp.py | 7 +++++++ 1 file changed, 7 insertions(+) diff --git a/scripts/commands/pvp.py b/scripts/commands/pvp.py index 54f1a40c..a42ea0dd 100644 --- a/scripts/commands/pvp.py +++ b/scripts/commands/pvp.py @@ -31,9 +31,16 @@ def run(core, actor, target, commandString): actor.setFaction('') actor.sendSystemMessage('@faction_recruiter:resign_complete', 0) + if commandString == 'neutral': + time.sleep(1) + actor.setFaction('') + actor.setPvpStatus(PvpStatus.Player, False) + actor.sendSystemMessage('@faction_recruiter:resign_complete', 0) + return time.sleep(1) actor.setFaction(commandString) + actor.setPvpStatus(PvpStatus.Player, True) return if faction == 'neutral' or faction == '': From e39b6b498dd611e866c1fc74662807936aee8568 Mon Sep 17 00:00:00 2001 From: Ziggeh Date: Sat, 29 Mar 2014 06:52:03 +0100 Subject: [PATCH 02/15] CombatService - Added method for drain heals run() in the combat ability scripts now take the damage done post mitigation etc as an argument instead of null. --- src/services/combat/CombatService.java | 14 +++++++++++--- 1 file changed, 11 insertions(+), 3 deletions(-) diff --git a/src/services/combat/CombatService.java b/src/services/combat/CombatService.java index 7d318859..eb815e7a 100644 --- a/src/services/combat/CombatService.java +++ b/src/services/combat/CombatService.java @@ -264,7 +264,7 @@ public class CombatService implements INetworkDispatch { sendCombatPackets(attacker, target, weapon, command, actionCounter, damage, 0, HitType.HIT); if(FileUtilities.doesFileExist("scripts/commands/combat/" + command.getCommandName() + ".py")) - core.scriptService.callScript("scripts/commands/combat/", command.getCommandName(), "run", core, attacker, target, null); + core.scriptService.callScript("scripts/commands/combat/", command.getCommandName(), "run", core, attacker, target, damage); } @@ -379,7 +379,7 @@ public class CombatService implements INetworkDispatch { } if(FileUtilities.doesFileExist("scripts/commands/combat/" + command.getCommandName() + ".py")) - core.scriptService.callScript("scripts/commands/combat/", command.getCommandName(), "run", core, attacker, target, null); + core.scriptService.callScript("scripts/commands/combat/", command.getCommandName(), "run", core, attacker, target, damage); return; @@ -812,6 +812,14 @@ public class CombatService implements INetworkDispatch { target.getEventBus().publish(event); } + @SuppressWarnings("unused") + public void doDrainHeal(CreatureObject receiver, int drainAmount) { + synchronized(receiver.getMutex()) { + receiver.setHealth(receiver.getHealth() + drainAmount); + } + + } + private boolean isInConeAngle(CreatureObject attacker, SWGObject target, int coneLength, int coneWidth, float directionX, float directionZ) { float radius = coneWidth / 2; @@ -830,7 +838,7 @@ public class CombatService implements INetworkDispatch { return true; - } + } public boolean attemptHeal(CreatureObject healer, CreatureObject target) { From 9ff669832b81e4388b20fbda88f8dcb5a2353c01 Mon Sep 17 00:00:00 2001 From: Treeku Date: Sat, 29 Mar 2014 09:29:34 +0000 Subject: [PATCH 03/15] calculatePvpStatus() used for everything, more... This ensures nothing is ever missed out of the pvpStatus calculation, such as faction standing. It should calculate the following: On Leave/neutral players should be #16 Combatant players should be #35 Opposing faction SF players should be #55 Opposing Combatant NPCs should be #19 Ally SF NPCs (ie.; hoth commandos) should be #4 Enemy SF NPCs (ie. hoth resistance) should be #7 Same faction NPCs should be #0 (pink) Attackable NPCs should be #1 Aggressive NPCs should be #2 or #3 NPCs you have negative faction standing with should be #2 or #3 --- scripts/commands/pvp.py | 8 ++--- .../objects/creature/CreatureObject.java | 3 +- .../objects/tangible/TangibleObject.java | 22 +++++++++++++- src/services/combat/CombatService.java | 8 ++--- src/services/gcw/FactionService.java | 30 +++++++++++++++---- src/services/object/DuplicateId.java | 21 +++++++++++++ 6 files changed, 74 insertions(+), 18 deletions(-) diff --git a/scripts/commands/pvp.py b/scripts/commands/pvp.py index a42ea0dd..7750b2e6 100644 --- a/scripts/commands/pvp.py +++ b/scripts/commands/pvp.py @@ -31,16 +31,14 @@ def run(core, actor, target, commandString): actor.setFaction('') actor.sendSystemMessage('@faction_recruiter:resign_complete', 0) - if commandString == 'neutral': + if commandString == 'neutral' or commandString == 'resign': time.sleep(1) actor.setFaction('') - actor.setPvpStatus(PvpStatus.Player, False) actor.sendSystemMessage('@faction_recruiter:resign_complete', 0) return time.sleep(1) actor.setFaction(commandString) - actor.setPvpStatus(PvpStatus.Player, True) return if faction == 'neutral' or faction == '': @@ -53,7 +51,6 @@ def run(core, actor, target, commandString): time.sleep(1) actor.setFactionStatus(FactionStatus.Combatant) actor.setPvpStatus(PvpStatus.GoingCovert, False) - actor.setPvpStatus(PvpStatus.Enemy, True) actor.sendSystemMessage('@faction_recruiter:covert_complete', 0) return @@ -63,7 +60,6 @@ def run(core, actor, target, commandString): time.sleep(30) actor.setFactionStatus(FactionStatus.SpecialForces) actor.setPvpStatus(PvpStatus.GoingOvert, False) - actor.setPvpStatus(PvpStatus.Overt | PvpStatus.Attackable | PvpStatus.Aggressive, True) actor.sendSystemMessage('@faction_recruiter:overt_complete', 0) return @@ -72,7 +68,7 @@ def run(core, actor, target, commandString): actor.setPvpStatus(PvpStatus.GoingCovert, True) time.sleep(300) actor.setFactionStatus(FactionStatus.Combatant) - actor.setPvpStatus(PvpStatus.GoingCovert | PvpStatus.Overt | PvpStatus.Attackable | PvpStatus.Aggressive, False) + actor.setPvpStatus(PvpStatus.GoingCovert, False) actor.sendSystemMessage('@faction_recruiter:covert_complete', 0) return diff --git a/src/resources/objects/creature/CreatureObject.java b/src/resources/objects/creature/CreatureObject.java index ecf161ef..c615d628 100644 --- a/src/resources/objects/creature/CreatureObject.java +++ b/src/resources/objects/creature/CreatureObject.java @@ -458,7 +458,7 @@ public class CreatureObject extends TangibleObject implements IPersistent { } notifyObservers(messageBuilder.buildFactionDelta(faction), true); - setPvpStatus(0, true); + updatePvpStatus(); } public int getFactionStatus() { @@ -473,6 +473,7 @@ public class CreatureObject extends TangibleObject implements IPersistent { } notifyObservers(messageBuilder.buildFactionStatusDelta(factionStatus), true); + updatePvpStatus(); } public float getHeight() { diff --git a/src/resources/objects/tangible/TangibleObject.java b/src/resources/objects/tangible/TangibleObject.java index 9207eed0..de8bf1d3 100644 --- a/src/resources/objects/tangible/TangibleObject.java +++ b/src/resources/objects/tangible/TangibleObject.java @@ -22,10 +22,14 @@ package resources.objects.tangible; import java.util.ArrayList; +import java.util.HashSet; +import java.util.Iterator; import java.util.List; import java.util.Set; import java.util.Vector; +import main.NGECore; + import protocol.swg.ObjControllerMessage; import protocol.swg.PlayClientEffectObjectMessage; import protocol.swg.StopClientEffectObjectByLabel; @@ -58,7 +62,7 @@ public class TangibleObject extends SWGObject { protected int optionsBitmask = 0; private int maxDamage = 1000; private boolean staticObject = true; - protected String faction = "neutral"; // Says you're "Imperial Special Forces" if it's 0 for some reason + protected String faction = ""; // Says you're "Imperial Special Forces" if it's 0 for some reason @NotPersistent private Vector defendersList = new Vector(); // unused in packets but useful for the server @NotPersistent @@ -218,6 +222,20 @@ public class TangibleObject extends SWGObject { } } } + + updatePvpStatus(); + } + + public void updatePvpStatus() { + HashSet observers = new HashSet(getObservers()); + + for (Iterator it = observers.iterator(); it.hasNext();) { + Client observer = it.next(); + + if (observer.getParent() != null) { + observer.getSession().write(new UpdatePVPStatusMessage(this.getObjectID(), NGECore.getInstance().factionService.calculatePvpStatus(observer, this), getFaction()).serialize()); + } + } } public String getFaction() { @@ -230,6 +248,8 @@ public class TangibleObject extends SWGObject { synchronized(objectMutex) { this.faction = faction; } + + updatePvpStatus(); } public Vector getDefendersList() { diff --git a/src/services/combat/CombatService.java b/src/services/combat/CombatService.java index 7d318859..01387ffb 100644 --- a/src/services/combat/CombatService.java +++ b/src/services/combat/CombatService.java @@ -997,8 +997,8 @@ public class CombatService implements INetworkDispatch { requester.getDuelList().add(target); requester.sendSystemMessage("You accept " + target.getCustomName() + "'s challenge.", (byte) 0); target.sendSystemMessage(requester.getCustomName() + " accepts your challenge.", (byte) 0); - target.getClient().getSession().write(new UpdatePVPStatusMessage(requester.getObjectID(), 55, requester.getFaction()).serialize()); - requester.getClient().getSession().write(new UpdatePVPStatusMessage(target.getObjectID(), 55, target.getFaction()).serialize()); + target.updatePvpStatus(); + requester.updatePvpStatus(); } @@ -1013,8 +1013,8 @@ public class CombatService implements INetworkDispatch { target.removeDefender(requester); requester.removeDefender(target); - target.getClient().getSession().write(new UpdatePVPStatusMessage(requester.getObjectID(), 0x16, requester.getFaction()).serialize()); - requester.getClient().getSession().write(new UpdatePVPStatusMessage(target.getObjectID(), 0x16, target.getFaction()).serialize()); + target.updatePvpStatus(); + requester.updatePvpStatus(); if(announce) { diff --git a/src/services/gcw/FactionService.java b/src/services/gcw/FactionService.java index 5f985b54..f774e934 100644 --- a/src/services/gcw/FactionService.java +++ b/src/services/gcw/FactionService.java @@ -203,18 +203,36 @@ public class FactionService implements INetworkDispatch { int pvpBitmask = target.getPvPBitmask(); - if (target.getSlottedObject("ghost") != null) { - if (target.getFaction() == null || (!target.getFaction().equals("rebel") && !target.getFaction().equals("imperial"))) { - return 0; - } + if (target.getFactionStatus() == FactionStatus.Combatant) { + pvpBitmask |= PvpStatus.Enemy; + } + + if (target.getFactionStatus() == FactionStatus.SpecialForces) { + pvpBitmask |= PvpStatus.Overt; + if (target.getSlottedObject("ghost") != null) { + pvpBitmask |= PvpStatus.Enemy; + } + } + + if (target.getSlottedObject("ghost") != null) { pvpBitmask |= PvpStatus.Player; - if (player.getFactionStatus() == FactionStatus.SpecialForces && - ((CreatureObject) target).getFactionStatus() == FactionStatus.SpecialForces) { + if ((!player.getFaction().equals(target.getFaction()) && + player.getFactionStatus() == FactionStatus.SpecialForces && + ((CreatureObject) target).getFactionStatus() == FactionStatus.SpecialForces) || + core.combatService.areInDuel(player, (CreatureObject) target)) { pvpBitmask |= (PvpStatus.Attackable | PvpStatus.Aggressive); } + if (core.combatService.areInDuel(player, (CreatureObject) target)) { + //pvpBitmask |= PvpStatus.Dueling; + } + + return pvpBitmask; + } + + if (player.getFaction().equals(target.getFaction()) { return pvpBitmask; } diff --git a/src/services/object/DuplicateId.java b/src/services/object/DuplicateId.java index 57b52cea..db618527 100644 --- a/src/services/object/DuplicateId.java +++ b/src/services/object/DuplicateId.java @@ -1,3 +1,24 @@ +/******************************************************************************* + * Copyright (c) 2013 + * + * This File is part of NGECore2. + * + * This program is free software: you can redistribute it and/or modify + * it under the terms of the GNU Lesser General Public License as published by + * the Free Software Foundation, either version 3 of the License, or + * (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public License + * along with this program. If not, see . + * + * Using NGEngine to work with NGECore2 is making a combined work based on NGEngine. + * Therefore all terms and conditions of the GNU Lesser General Public License cover the combination. + ******************************************************************************/ package services.object; import com.sleepycat.persist.model.Entity; From 01ffdb3c422cb7a063364207764fabe5cd6df727 Mon Sep 17 00:00:00 2001 From: Seefo Date: Sat, 29 Mar 2014 11:59:19 -0400 Subject: [PATCH 04/15] Fixed healing of AI, temp fix for faction error --- src/resources/objects/tangible/TangibleObject.java | 2 +- src/services/combat/CombatService.java | 2 ++ src/services/gcw/FactionService.java | 7 ++++--- 3 files changed, 7 insertions(+), 4 deletions(-) diff --git a/src/resources/objects/tangible/TangibleObject.java b/src/resources/objects/tangible/TangibleObject.java index de8bf1d3..b6d9517f 100644 --- a/src/resources/objects/tangible/TangibleObject.java +++ b/src/resources/objects/tangible/TangibleObject.java @@ -233,7 +233,7 @@ public class TangibleObject extends SWGObject { Client observer = it.next(); if (observer.getParent() != null) { - observer.getSession().write(new UpdatePVPStatusMessage(this.getObjectID(), NGECore.getInstance().factionService.calculatePvpStatus(observer, this), getFaction()).serialize()); + observer.getSession().write(new UpdatePVPStatusMessage(this.getObjectID(), NGECore.getInstance().factionService.calculatePvpStatus((CreatureObject) observer.getParent(), this), getFaction()).serialize()); } } } diff --git a/src/services/combat/CombatService.java b/src/services/combat/CombatService.java index 01387ffb..25d8517d 100644 --- a/src/services/combat/CombatService.java +++ b/src/services/combat/CombatService.java @@ -847,6 +847,8 @@ public class CombatService implements INetworkDispatch { return false; } + if(target.getAttachment("AI") != null) return false; + if(healer.getFaction().equals(target.getFaction())) { if(healer.getFactionStatus() < target.getFactionStatus()) diff --git a/src/services/gcw/FactionService.java b/src/services/gcw/FactionService.java index f774e934..3a604f9a 100644 --- a/src/services/gcw/FactionService.java +++ b/src/services/gcw/FactionService.java @@ -203,11 +203,12 @@ public class FactionService implements INetworkDispatch { int pvpBitmask = target.getPvPBitmask(); - if (target.getFactionStatus() == FactionStatus.Combatant) { + // Seefo: Casting target to type CreatureObject as temporary fix. I am unsure whether or not we want to put a factionStatus member inside of TangibleObject. + if (((CreatureObject) target).getFactionStatus() == FactionStatus.Combatant) { pvpBitmask |= PvpStatus.Enemy; } - if (target.getFactionStatus() == FactionStatus.SpecialForces) { + if (((CreatureObject) target).getFactionStatus() == FactionStatus.SpecialForces) { pvpBitmask |= PvpStatus.Overt; if (target.getSlottedObject("ghost") != null) { @@ -232,7 +233,7 @@ public class FactionService implements INetworkDispatch { return pvpBitmask; } - if (player.getFaction().equals(target.getFaction()) { + if (player.getFaction().equals(target.getFaction())) { return pvpBitmask; } From d7784f4d25b739fb188319d3a9df0450b72beb36 Mon Sep 17 00:00:00 2001 From: Light2 Date: Sat, 29 Mar 2014 17:35:31 +0100 Subject: [PATCH 05/15] Added exception handling for AI --- src/services/ai/AIActor.java | 33 +++++++++++++++++++++-------- src/services/ai/states/AIState.java | 8 +++---- 2 files changed, 28 insertions(+), 13 deletions(-) diff --git a/src/services/ai/AIActor.java b/src/services/ai/AIActor.java index 1f2247c0..fcaf3e7d 100644 --- a/src/services/ai/AIActor.java +++ b/src/services/ai/AIActor.java @@ -30,7 +30,6 @@ import java.util.concurrent.TimeUnit; import main.NGECore; import net.engio.mbassy.listener.Handler; - import engine.resources.objects.SWGObject; import engine.resources.scene.Point3D; import engine.resources.scene.Quaternion; @@ -120,12 +119,16 @@ public class AIActor { } public void setCurrentState(AIState currentState) { - if(currentState.getClass() == this.currentState.getClass()) - return; - if(this.currentState != null) - doStateAction(this.currentState.onExit(this)); - this.currentState = currentState; - doStateAction(currentState.onEnter(this)); + try { + if(currentState.getClass() == this.currentState.getClass()) + return; + if(this.currentState != null) + doStateAction(this.currentState.onExit(this)); + this.currentState = currentState; + doStateAction(currentState.onEnter(this)); + } catch (Exception e) { + e.printStackTrace(); + } } public CreatureObject getFollowObject() { @@ -153,11 +156,23 @@ public class AIActor { } public void scheduleMovement() { - scheduler.schedule(() -> doStateAction(currentState.move(AIActor.this)), 500, TimeUnit.MILLISECONDS); + scheduler.schedule(() -> { + try { + doStateAction(currentState.move(AIActor.this)); + } catch (Exception e) { + e.printStackTrace(); + } + }, 500, TimeUnit.MILLISECONDS); } public void scheduleRecovery() { - scheduler.schedule(() -> doStateAction(currentState.recover(AIActor.this)), 2000, TimeUnit.MILLISECONDS); + scheduler.schedule(() -> { + try { + doStateAction(currentState.recover(AIActor.this)); + } catch (Exception e) { + e.printStackTrace(); + } + }, 2000, TimeUnit.MILLISECONDS); } public void setNextPosition(Point3D position) { diff --git a/src/services/ai/states/AIState.java b/src/services/ai/states/AIState.java index 0aa18891..16cd8a68 100644 --- a/src/services/ai/states/AIState.java +++ b/src/services/ai/states/AIState.java @@ -34,10 +34,10 @@ import services.ai.AIActor; public abstract class AIState { - public abstract byte onEnter(AIActor actor); - public abstract byte onExit(AIActor actor); - public abstract byte move(AIActor actor); - public abstract byte recover(AIActor actor); + public abstract byte onEnter(AIActor actor) throws Exception; + public abstract byte onExit(AIActor actor) throws Exception; + public abstract byte move(AIActor actor) throws Exception; + public abstract byte recover(AIActor actor) throws Exception; public enum StateResult {; From 7878e2a589cfa29f87841e3ea0eb635a740b953b Mon Sep 17 00:00:00 2001 From: Light2 Date: Sat, 29 Mar 2014 18:19:59 +0100 Subject: [PATCH 06/15] fixed bug where revive window was showing up for the medic --- src/services/combat/CombatService.java | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/services/combat/CombatService.java b/src/services/combat/CombatService.java index 25d8517d..eed3b5cf 100644 --- a/src/services/combat/CombatService.java +++ b/src/services/combat/CombatService.java @@ -1034,7 +1034,7 @@ public class CombatService implements INetworkDispatch { success = false; if((command.getAttackType() == 0 || command.getAttackType() == 1 || command.getAttackType() == 3) && !attemptHeal(medic, target)) - target = medic; + success = false; if(!success) { IoSession session = medic.getClient().getSession(); From c8600fe6e193e2668cb4d5125227b0244288cbad Mon Sep 17 00:00:00 2001 From: Light2 Date: Sat, 29 Mar 2014 18:21:05 +0100 Subject: [PATCH 07/15] fixed concurrency error --- src/services/PlayerService.java | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/services/PlayerService.java b/src/services/PlayerService.java index 764e4c7e..600d77dd 100644 --- a/src/services/PlayerService.java +++ b/src/services/PlayerService.java @@ -598,7 +598,7 @@ public class PlayerService implements INetworkDispatch { core.buffService.clearBuffs(creature); - for (String skill : creature.getSkills()) { + for (String skill : new ArrayList(creature.getSkills())) { core.skillService.removeSkill(creature, skill); } From dfd7f1e9a92622db620889b7e88f1d9402df4191 Mon Sep 17 00:00:00 2001 From: Light2 Date: Sat, 29 Mar 2014 18:32:29 +0100 Subject: [PATCH 08/15] Fixed bug where group wouldnt show up when player loaded a new scene --- src/services/SimulationService.java | 7 +++++-- 1 file changed, 5 insertions(+), 2 deletions(-) diff --git a/src/services/SimulationService.java b/src/services/SimulationService.java index bb495850..35e1c3f4 100644 --- a/src/services/SimulationService.java +++ b/src/services/SimulationService.java @@ -75,6 +75,7 @@ import protocol.swg.objectControllerObjects.TargetUpdate; import resources.objects.building.BuildingObject; import resources.objects.cell.CellObject; import resources.objects.creature.CreatureObject; +import resources.objects.group.GroupObject; import resources.objects.player.PlayerObject; import resources.objects.tangible.TangibleObject; import resources.common.*; @@ -811,6 +812,10 @@ public class SimulationService implements INetworkDispatch { object.playMusic("sound/music_acq_bountyhunter.snd"); core.skillService.addSkill(object, ghost.getProfessionWheelPosition()); } + + if(object.getGroupId() != 0 && core.objectService.getObject(object.getGroupId()) instanceof GroupObject) + object.makeAware(core.objectService.getObject(object.getGroupId())); + } public void transferToPlanet(SWGObject object, Planet planet, Point3D newPos, Quaternion newOrientation, SWGObject newParent) { @@ -843,9 +848,7 @@ public class SimulationService implements INetworkDispatch { synchronized(object.getMutex()) { - object.getAwareObjects().removeAll(object.getAwareObjects()); - } object.setPlanet(planet); From 7376be7b954ba702e9904ff4e1df319cfadd0ec1 Mon Sep 17 00:00:00 2001 From: Light2 Date: Sat, 29 Mar 2014 18:42:24 +0100 Subject: [PATCH 09/15] fixed bug where character wouldnt gain any abilities on using the frog to get lvl 90 --- src/services/PlayerService.java | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/services/PlayerService.java b/src/services/PlayerService.java index 600d77dd..27cc7eaf 100644 --- a/src/services/PlayerService.java +++ b/src/services/PlayerService.java @@ -598,7 +598,7 @@ public class PlayerService implements INetworkDispatch { core.buffService.clearBuffs(creature); - for (String skill : new ArrayList(creature.getSkills())) { + for (String skill : new ArrayList(creature.getSkills().get())) { core.skillService.removeSkill(creature, skill); } From dce91cc2d21552f71853fb0551ab359ae8033d1c Mon Sep 17 00:00:00 2001 From: Light2 Date: Sat, 29 Mar 2014 18:56:59 +0100 Subject: [PATCH 10/15] reverted fix --- src/services/PlayerService.java | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/services/PlayerService.java b/src/services/PlayerService.java index 27cc7eaf..764e4c7e 100644 --- a/src/services/PlayerService.java +++ b/src/services/PlayerService.java @@ -598,7 +598,7 @@ public class PlayerService implements INetworkDispatch { core.buffService.clearBuffs(creature); - for (String skill : new ArrayList(creature.getSkills().get())) { + for (String skill : creature.getSkills()) { core.skillService.removeSkill(creature, skill); } From 68ebfae1450d3c611dc84f04ea90a0f81f587fb0 Mon Sep 17 00:00:00 2001 From: Seefo Date: Sat, 29 Mar 2014 14:01:00 -0400 Subject: [PATCH 11/15] Fixed expertise exploit --- src/services/SkillService.java | 46 ++++++++++++++++++++++++++++++++-- 1 file changed, 44 insertions(+), 2 deletions(-) diff --git a/src/services/SkillService.java b/src/services/SkillService.java index d4127119..9eb13852 100644 --- a/src/services/SkillService.java +++ b/src/services/SkillService.java @@ -30,7 +30,6 @@ import org.python.core.Py; import org.python.core.PyObject; import protocol.swg.ExpertiseRequestMessage; - import resources.common.Console; import resources.common.FileUtilities; import resources.common.Opcodes; @@ -303,7 +302,7 @@ public class SkillService implements INetworkDispatch { return; for(String expertiseName : expertise.getExpertiseSkills()) { - if(expertiseName.startsWith("expertise_") && ((caluclateExpertisePoints(creature) - 1) >= 0)) { // Prevent possible glitches/exploits + if(expertiseName.startsWith("expertise_") && ((caluclateExpertisePoints(creature) - 1) >= 0) && validExpertiseSkill(player, expertiseName)) { // Prevent possible glitches/exploits addSkill(creature, expertiseName); } } @@ -325,6 +324,49 @@ public class SkillService implements INetworkDispatch { return expertisePoints; } + public boolean validExpertiseSkill(PlayerObject player, String skill) + { + try + { + DatatableVisitor table = ClientFileManager.loadFile("datatables/expertise/expertise.iff", DatatableVisitor.class); + String profession; + + switch(player.getProfession()) + { + case "trader_0a": + profession = "trader_dom"; + break; + + case "trader_0b": + profession = "trader_struct"; + break; + + case "trader_0c": + profession = "trader_mun"; + break; + + case "trader_0d": + profession = "trader_eng"; + break; + + default: + profession = player.getProfession().replace("_1a", ""); + break; + } + + for (int s = 0; s < table.getRowCount(); s++) + { + if (table.getObject(s, 0) != null && ((String) table.getObject(s, 0)).equals(skill)) + { + if(((String)table.getObject(s, 7)).equals(profession) || ((String)table.getObject(s, 7)).equals("all")) return true; + else return false; + } + } + } + catch (Exception e) { e.printStackTrace(); } + return false; + } + @Override public void shutdown() { From 8268359ec24dd2fd54b03816690d81a16ad475b8 Mon Sep 17 00:00:00 2001 From: Seefo Date: Sat, 29 Mar 2014 14:09:54 -0400 Subject: [PATCH 12/15] Reverted temporary fix for #295 b/c #295 is fixed --- src/services/ConnectionService.java | 2 +- src/services/SimulationService.java | 2 -- 2 files changed, 1 insertion(+), 3 deletions(-) diff --git a/src/services/ConnectionService.java b/src/services/ConnectionService.java index 1930f474..75470eae 100644 --- a/src/services/ConnectionService.java +++ b/src/services/ConnectionService.java @@ -210,7 +210,7 @@ public class ConnectionService implements INetworkDispatch { object.setSpectatorTask(null); } - //core.groupService.handleGroupDisband(object); // Seefo: Temporarily moved to simulationService.handleDisconnect as a temporary fix for issue #295 + core.groupService.handleGroupDisband(object); if (core.instanceService.isInInstance(object)) { core.instanceService.remove(core.instanceService.getActiveInstance(object), object); diff --git a/src/services/SimulationService.java b/src/services/SimulationService.java index 35e1c3f4..215491ea 100644 --- a/src/services/SimulationService.java +++ b/src/services/SimulationService.java @@ -755,8 +755,6 @@ public class SimulationService implements INetworkDispatch { } } - core.groupService.handleGroupDisband(object); // Seefo: Temporarily moved from connectionService.disconnect as a temporary fix for issue #295 - /* object.createTransaction(core.getCreatureODB().getEnvironment()); core.getCreatureODB().put(object, Long.class, CreatureObject.class, object.getTransaction()); From 3ad4aad96d7d2d021074363ed014227faf810cf2 Mon Sep 17 00:00:00 2001 From: Ziggeh Date: Sat, 29 Mar 2014 19:48:07 +0100 Subject: [PATCH 13/15] Armor - Protection is added to character sheet --- scripts/equipment/slot_protection.py | 23 +++++++++++++ src/services/EquipmentService.java | 51 ++++++++++++++++++++++++---- 2 files changed, 68 insertions(+), 6 deletions(-) create mode 100644 scripts/equipment/slot_protection.py diff --git a/scripts/equipment/slot_protection.py b/scripts/equipment/slot_protection.py new file mode 100644 index 00000000..3e16a86c --- /dev/null +++ b/scripts/equipment/slot_protection.py @@ -0,0 +1,23 @@ +import sys + +def chest2(): + return "35.71" + +def pants1(): + return "21.43" + +def hat(): + return "14.27" + +def bracer_upper_l(): + return "7.15" + +def bracer_upper_r(): + return "7.15" + +def bicep_l(): + return "7.15" + +def bicep_r(): + return "7.15" + \ No newline at end of file diff --git a/src/services/EquipmentService.java b/src/services/EquipmentService.java index c130d46d..afe5b694 100644 --- a/src/services/EquipmentService.java +++ b/src/services/EquipmentService.java @@ -56,7 +56,7 @@ public class EquipmentService implements INetworkDispatch { private int getWeaponCriticalChance(CreatureObject actor, SWGObject item) { int weaponCriticalChance = 0; - String weaponCriticalSkillMod = (core.scriptService.getMethod("scripts/equipment/", "weapon_critical", item.getStringAttribute("cat_wpn_damage.wpn_category")/*.replace(" ", "").replace("-", "") + "_" */).__call__().asString()); + String weaponCriticalSkillMod = (core.scriptService.getMethod("scripts/equipment/", "weapon_critical", item.getStringAttribute("cat_wpn_damage.wpn_category")).__call__().asString()); if(weaponCriticalSkillMod.contains(" ")) weaponCriticalSkillMod.replace(" ", ""); @@ -65,7 +65,7 @@ public class EquipmentService implements INetworkDispatch { weaponCriticalSkillMod.replace("-", ""); if(actor.getSkillMod(weaponCriticalSkillMod) != null) - weaponCriticalChance = actor.getSkillModBase((core.scriptService.getMethod("scripts/equipment/", "weapon_critical", item.getStringAttribute("cat_wpn_damage.wpn_category").replace(" ", "").replace("-", "") + "_" ).__call__().asString())); + weaponCriticalChance = actor.getSkillModBase(weaponCriticalSkillMod); return weaponCriticalChance; } @@ -132,12 +132,34 @@ public class EquipmentService implements INetworkDispatch { return result; } + private float calculateArmorProtection (float protection, String slotName) { + return protection *= (Float.parseFloat(core.scriptService.getMethod("scripts/equipment/", "slot_protection", slotName).__call__().asString()) / 100); + } + + private void addArmorProtection(CreatureObject actor, String protectionType, float protection, String slotName) { + actor.addSkillMod(protectionType, (int) (calculateArmorProtection(protection, slotName))); + } + + private void deductArmorProtection(CreatureObject actor, String protectionType, float protection, String slotName) { + actor.deductSkillMod(protectionType, (int) calculateArmorProtection(protection, slotName)); + } + private void addForceProtection(CreatureObject actor, SWGObject item) { - actor.addSkillMod("expertise_innate_protection_all", getForceProtection(item)); + actor.addSkillMod("kinetic", getForceProtection(item)); + actor.addSkillMod("energy", getForceProtection(item)); + actor.addSkillMod("heat", getForceProtection(item)); + actor.addSkillMod("cold", getForceProtection(item)); + actor.addSkillMod("acid", getForceProtection(item)); + actor.addSkillMod("electricity", getForceProtection(item)); } private void deductForceProtection(CreatureObject actor, SWGObject item) { - actor.deductSkillMod("expertise_innate_protection_all", getForceProtection(item)); + actor.deductSkillMod("kinetic", getForceProtection(item)); + actor.deductSkillMod("energy", getForceProtection(item)); + actor.deductSkillMod("heat", getForceProtection(item)); + actor.deductSkillMod("cold", getForceProtection(item)); + actor.deductSkillMod("acid", getForceProtection(item)); + actor.deductSkillMod("electricity", getForceProtection(item)); } private int getForceProtection(SWGObject item) { @@ -163,8 +185,7 @@ public class EquipmentService implements INetworkDispatch { // TODO: bio-link (assign it by objectID with setAttachment and then just display the customName for that objectID). if(item.getStringAttribute("cat_wpn_damage.wpn_category") != null) - if (actor.getSlotNameForObject(item).contentEquals("hold_r") == true) - addWeaponCriticalChance(actor, item); + addWeaponCriticalChance(actor, item); Map attributes = new TreeMap(item.getAttributes()); @@ -177,6 +198,14 @@ public class EquipmentService implements INetworkDispatch { core.skillModService.addSkillMod(actor, e.getKey().replace("cat_stat_mod_bonus.@stat_n:", ""), Integer.parseInt((String) e.getValue())); } + if(e.getKey().startsWith("cat_armor_standard_protection")) { + addArmorProtection(actor, e.getKey().replace("cat_armor_standard_protection.armor_eff_", ""), Float.parseFloat((String) e.getValue()), actor.getSlotNameForObject(item)); + } + + if(e.getKey().startsWith("cat_armor_special_protection")) { + addArmorProtection(actor, e.getKey().replace("cat_armor_special_protection.special_protection_type_", ""), Float.parseFloat((String) e.getValue()), actor.getSlotNameForObject(item)); + } + if(e.getKey().startsWith("cat_attrib_mod_bonus.attr_health")) { actor.setMaxHealth(actor.getMaxHealth() + Integer.parseInt((String) e.getValue())); } @@ -184,6 +213,7 @@ public class EquipmentService implements INetworkDispatch { if(e.getKey().startsWith("cat_attrib_mod_bonus.attr_action")) { actor.setMaxAction(actor.getMaxAction() + Integer.parseInt((String) e.getValue())); } + } if(!actor.getEquipmentList().contains(item)) @@ -215,6 +245,15 @@ public class EquipmentService implements INetworkDispatch { if(e.getKey().startsWith("cat_stat_mod_bonus.@stat_n:")) { core.skillModService.deductSkillMod(actor, e.getKey().replace("cat_stat_mod_bonus.@stat_n:", ""), Integer.parseInt((String) e.getValue())); } + + if(e.getKey().startsWith("cat_armor_standard_protection")) { + deductArmorProtection(actor, e.getKey().replace("cat_armor_standard_protection.armor_eff_", ""), Float.parseFloat((String) e.getValue()), actor.getSlotNameForObject(item)); + } + + if(e.getKey().startsWith("cat_armor_special_protection")) { + deductArmorProtection(actor, e.getKey().replace("cat_armor_special_protection.special_protection_type_", ""), Float.parseFloat((String) e.getValue()), actor.getSlotNameForObject(item)); + } + if(e.getKey().startsWith("cat_attrib_mod_bonus.attr_health")) { actor.setMaxHealth(actor.getMaxHealth() - Integer.parseInt((String) e.getValue())); } From 4fe5e6614e603b415e390741d4afb348a444c2dd Mon Sep 17 00:00:00 2001 From: Light2 Date: Sat, 29 Mar 2014 21:00:51 +0100 Subject: [PATCH 14/15] temp fix for /pvp --- scripts/commands/pvp.py | 3 +++ .../objects/creature/CreatureObject.java | 4 ++-- .../objects/tangible/TangibleObject.java | 5 +++- src/services/gcw/FactionService.java | 23 ++++++++++++++++++- 4 files changed, 31 insertions(+), 4 deletions(-) diff --git a/scripts/commands/pvp.py b/scripts/commands/pvp.py index 7750b2e6..e7c27d07 100644 --- a/scripts/commands/pvp.py +++ b/scripts/commands/pvp.py @@ -52,6 +52,7 @@ def run(core, actor, target, commandString): actor.setFactionStatus(FactionStatus.Combatant) actor.setPvpStatus(PvpStatus.GoingCovert, False) actor.sendSystemMessage('@faction_recruiter:covert_complete', 0) + actor.updatePvpStatus() return if factionStatus == FactionStatus.Combatant: @@ -61,6 +62,7 @@ def run(core, actor, target, commandString): actor.setFactionStatus(FactionStatus.SpecialForces) actor.setPvpStatus(PvpStatus.GoingOvert, False) actor.sendSystemMessage('@faction_recruiter:overt_complete', 0) + actor.updatePvpStatus() return if factionStatus == FactionStatus.SpecialForces: @@ -70,6 +72,7 @@ def run(core, actor, target, commandString): actor.setFactionStatus(FactionStatus.Combatant) actor.setPvpStatus(PvpStatus.GoingCovert, False) actor.sendSystemMessage('@faction_recruiter:covert_complete', 0) + actor.updatePvpStatus() return return diff --git a/src/resources/objects/creature/CreatureObject.java b/src/resources/objects/creature/CreatureObject.java index c615d628..bfc09120 100644 --- a/src/resources/objects/creature/CreatureObject.java +++ b/src/resources/objects/creature/CreatureObject.java @@ -458,7 +458,7 @@ public class CreatureObject extends TangibleObject implements IPersistent { } notifyObservers(messageBuilder.buildFactionDelta(faction), true); - updatePvpStatus(); + //updatePvpStatus(); } public int getFactionStatus() { @@ -473,7 +473,7 @@ public class CreatureObject extends TangibleObject implements IPersistent { } notifyObservers(messageBuilder.buildFactionStatusDelta(factionStatus), true); - updatePvpStatus(); + //updatePvpStatus(); } public float getHeight() { diff --git a/src/resources/objects/tangible/TangibleObject.java b/src/resources/objects/tangible/TangibleObject.java index b6d9517f..b00537a1 100644 --- a/src/resources/objects/tangible/TangibleObject.java +++ b/src/resources/objects/tangible/TangibleObject.java @@ -223,7 +223,7 @@ public class TangibleObject extends SWGObject { } } - updatePvpStatus(); + //updatePvpStatus(); } public void updatePvpStatus() { @@ -234,7 +234,10 @@ public class TangibleObject extends SWGObject { if (observer.getParent() != null) { observer.getSession().write(new UpdatePVPStatusMessage(this.getObjectID(), NGECore.getInstance().factionService.calculatePvpStatus((CreatureObject) observer.getParent(), this), getFaction()).serialize()); + if(getClient() != null) + getClient().getSession().write(new UpdatePVPStatusMessage(observer.getParent().getObjectID(), NGECore.getInstance().factionService.calculatePvpStatus((CreatureObject) this, (CreatureObject) observer.getParent()), getFaction()).serialize()); } + } } diff --git a/src/services/gcw/FactionService.java b/src/services/gcw/FactionService.java index 3a604f9a..afe73fd5 100644 --- a/src/services/gcw/FactionService.java +++ b/src/services/gcw/FactionService.java @@ -198,7 +198,7 @@ public class FactionService implements INetworkDispatch { * This should be used instead of getPvPBitmask where possible, but * should not be used in setPvPBitmask. */ - public int calculatePvpStatus(CreatureObject player, TangibleObject target) { + /*public int calculatePvpStatus(CreatureObject player, TangibleObject target) { PlayerObject ghost = (PlayerObject) player.getSlottedObject("ghost"); int pvpBitmask = target.getPvPBitmask(); @@ -254,6 +254,27 @@ public class FactionService implements INetworkDispatch { } return pvpBitmask; + }*/ + + // temp fix until calculatePvpStatus is fixed + public int calculatePvpStatus(CreatureObject player, TangibleObject target) { + + if(target.getSlottedObject("ghost") != null) { + + if(!player.getFaction().equals(target.getFaction()) && player.getFactionStatus() == FactionStatus.SpecialForces && ((CreatureObject) target).getFactionStatus() == FactionStatus.SpecialForces) + return 55; + else if(core.combatService.areInDuel(player, (CreatureObject) target)) + return 55; + else + return 0x14; + + } else { + if(target.getAttachment("AI") != null) + return PvpStatus.Attackable; + else + return 0; + } + } public Map getFactionMap() { From 85582bdd29d00d2758a90f82cccd84ff83161cc0 Mon Sep 17 00:00:00 2001 From: Seefo Date: Sat, 29 Mar 2014 16:11:10 -0400 Subject: [PATCH 15/15] Fixed a trade bug and a /open bug --- src/services/SimulationService.java | 2 +- src/services/trade/TradeService.java | 3 ++- 2 files changed, 3 insertions(+), 2 deletions(-) diff --git a/src/services/SimulationService.java b/src/services/SimulationService.java index 215491ea..f3f8d86f 100644 --- a/src/services/SimulationService.java +++ b/src/services/SimulationService.java @@ -872,7 +872,7 @@ public class SimulationService implements INetworkDispatch { if(container.getPermissions().canView(requester, container)) { OpenedContainerMessage opm = new OpenedContainerMessage(container.getObjectID()); - if(requester.getClient() != null && requester.getClient().getSession() != null) + if(requester.getClient() != null && requester.getClient().getSession() != null && !(container instanceof CreatureObject)) requester.getClient().getSession().write(opm.serialize()); } diff --git a/src/services/trade/TradeService.java b/src/services/trade/TradeService.java index 5b22471c..08201aab 100644 --- a/src/services/trade/TradeService.java +++ b/src/services/trade/TradeService.java @@ -25,6 +25,7 @@ import resources.objects.creature.CreatureObject; import engine.clients.Client; import engine.resources.container.AllPermissions; import engine.resources.container.CreatureContainerPermissions; +import engine.resources.container.CreaturePermissions; import engine.resources.objects.SWGObject; import engine.resources.service.INetworkDispatch; import engine.resources.service.INetworkRemoteEvent; @@ -205,7 +206,7 @@ public class TradeService implements INetworkDispatch{ } else { - if(objectToTrade.getAttributes().containsKey("no_trade")) { + if(objectToTrade.getAttributes().containsKey("no_trade") || !objectToTrade.getPermissions().canRemove(client.getParent(), objectToTrade.getContainer()) || (objectToTrade.getContainer() instanceof CreatureObject)) { return; }