diff --git a/common/src/main/scala/net/psforever/objects/GlobalDefinitions.scala b/common/src/main/scala/net/psforever/objects/GlobalDefinitions.scala index 2a05dc25e..c937e7c95 100644 --- a/common/src/main/scala/net/psforever/objects/GlobalDefinitions.scala +++ b/common/src/main/scala/net/psforever/objects/GlobalDefinitions.scala @@ -1530,7 +1530,8 @@ object GlobalDefinitions { Standard.ResistanceSplash = 15 Standard.ResistanceAggravated = 8 - Agile.Name = "agile" + Agile.Name = "lite_armor" + Agile.Descriptor = "agile" Agile.MaxArmor = 100 Agile.InventoryScale = InventoryTile.Tile99 Agile.InventoryOffset = 6 @@ -1542,7 +1543,8 @@ object GlobalDefinitions { Agile.ResistanceSplash = 25 Agile.ResistanceAggravated = 10 - Reinforced.Name = "reinforced" + Reinforced.Name = "med_armor" + Reinforced.Descriptor = "reinforced" Reinforced.Permissions = List(CertificationType.ReinforcedExoSuit) Reinforced.MaxArmor = 200 Reinforced.InventoryScale = InventoryTile.Tile1209 @@ -1580,18 +1582,21 @@ object GlobalDefinitions { } CommonMaxConfig(VSMAX) + VSMAX.Name = "vshev" VSMAX.MaxCapacitor = 50 VSMAX.CapacitorRechargeDelayMillis = 5000 VSMAX.CapacitorRechargePerSecond = 3 VSMAX.CapacitorDrainPerSecond = 20 CommonMaxConfig(TRMAX) + TRMAX.Name = "trhev" TRMAX.MaxCapacitor = 300 TRMAX.CapacitorRechargeDelayMillis = 10000 TRMAX.CapacitorRechargePerSecond = 10 TRMAX.CapacitorDrainPerSecond = 30 CommonMaxConfig(NCMAX) + NCMAX.Name = "nchev" NCMAX.MaxCapacitor = 400 NCMAX.CapacitorRechargeDelayMillis = 10000 NCMAX.CapacitorRechargePerSecond = 4 diff --git a/common/src/main/scala/net/psforever/objects/Player.scala b/common/src/main/scala/net/psforever/objects/Player.scala index 3c398d343..a0c84a0bf 100644 --- a/common/src/main/scala/net/psforever/objects/Player.scala +++ b/common/src/main/scala/net/psforever/objects/Player.scala @@ -52,7 +52,7 @@ class Player(private val core : Avatar) extends PlanetSideGameObject private var vehicleSeated : Option[PlanetSideGUID] = None private var vehicleOwned : Option[PlanetSideGUID] = None - private var continent : String = "home2" //the zone id + Continent = "home2" //the zone id var silenced : Boolean = false var firstLoad : Boolean = false @@ -612,13 +612,6 @@ class Player(private val core : Avatar) extends PlanetSideGameObject VehicleOwned } - def Continent : String = continent - - def Continent_=(zoneId : String) : String = { - continent = zoneId - Continent - } - def DamageModel = exosuit.asInstanceOf[DamageResistanceModel] def Definition : AvatarDefinition = core.Definition diff --git a/common/src/main/scala/net/psforever/objects/Vehicle.scala b/common/src/main/scala/net/psforever/objects/Vehicle.scala index 9a60f87a7..1330af045 100644 --- a/common/src/main/scala/net/psforever/objects/Vehicle.scala +++ b/common/src/main/scala/net/psforever/objects/Vehicle.scala @@ -12,7 +12,6 @@ import net.psforever.objects.serverobject.deploy.Deployment import net.psforever.objects.serverobject.structures.AmenityOwner import net.psforever.objects.vehicles._ import net.psforever.objects.vital.{DamageResistanceModel, StandardResistanceProfile, Vitality} -import net.psforever.objects.zones.{Zone, ZoneAware} import net.psforever.packet.game.PlanetSideGUID import net.psforever.types.PlanetSideEmpire @@ -66,15 +65,13 @@ import scala.annotation.tailrec * stores and unloads pertinent information about the `Vehicle`'s configuration; * used in the initialization process (`loadVehicleDefinition`) */ -class Vehicle(private val vehicleDef : VehicleDefinition) extends PlanetSideServerObject +class Vehicle(private val vehicleDef : VehicleDefinition) extends AmenityOwner with FactionAffinity - with ZoneAware with Mountable with MountedWeapons with Deployment with Vitality with OwnableByPlayer - with AmenityOwner with StandardResistanceProfile with Container { private var faction : PlanetSideEmpire.Value = PlanetSideEmpire.TR @@ -86,12 +83,6 @@ class Vehicle(private val vehicleDef : VehicleDefinition) extends PlanetSideServ private var cloaked : Boolean = false private var flying : Boolean = false private var capacitor : Int = 0 -/** - * Normally, the vehicle is the resident of a `Zone` object and that is what it considers its "continent." - * Since the `Vehicle` object can switch between `Zone` objects, however, - * it may become useful to allow the vehicle to identify as belonging to its future zone earlier than reference assignment. - */ - private var continent : Option[String] = None //the zone id /** * Permissions control who gets to access different parts of the vehicle; * the groups are Driver (seat), Gunner (seats), Passenger (seats), and the Trunk @@ -514,28 +505,6 @@ class Vehicle(private val vehicleDef : VehicleDefinition) extends PlanetSideServ */ def Definition : VehicleDefinition = vehicleDef - /** - * When assigning a new `Zone` object for the `Vehicle` object, eliminate - * @param zone a reference to the `Zone` object - * @return a reference to the `Zone` object - */ - override def Zone_=(zone : Zone) : Zone = { - continent = None - super.Zone_=(zone) - } - - override def Continent : String = continent.getOrElse(Zone.Id) - - /** - * Give the `Vehicle` object a custom `Zone` identifier. - * @param zoneId the custom identifier of the `Zone` object - * @return the identifier of the `Zone` object - */ - override def Continent_=(zoneId : String) : String = { - continent = Some(zoneId) - Continent - } - def canEqual(other: Any): Boolean = other.isInstanceOf[Vehicle] override def equals(other : Any) : Boolean = other match { @@ -645,7 +614,9 @@ object Vehicle { vehicle.utilities = vdef.Utilities.map({ case(num, util) => val obj = Utility(util, vehicle) - obj().LocationOffset = vdef.UtilityOffset.get(num) + val utilObj = obj() + vehicle.Amenities = utilObj + utilObj.LocationOffset = vdef.UtilityOffset.get(num) num -> obj }).toMap //trunk diff --git a/common/src/main/scala/net/psforever/objects/definition/ExoSuitDefinition.scala b/common/src/main/scala/net/psforever/objects/definition/ExoSuitDefinition.scala index a59f9b33a..44e1175f3 100644 --- a/common/src/main/scala/net/psforever/objects/definition/ExoSuitDefinition.scala +++ b/common/src/main/scala/net/psforever/objects/definition/ExoSuitDefinition.scala @@ -114,6 +114,7 @@ class ExoSuitDefinition(private val suitType : ExoSuitType.Value) extends BasicD class SpecialExoSuitDefinition(private val suitType : ExoSuitType.Value) extends ExoSuitDefinition(suitType) { Name = "heavy_armor" + Descriptor = "heavy_armor" private var activatedSpecial : SpecialExoSuitDefinition.Mode.Value = SpecialExoSuitDefinition.Mode.Normal diff --git a/common/src/main/scala/net/psforever/objects/serverobject/PlanetSideServerObject.scala b/common/src/main/scala/net/psforever/objects/serverobject/PlanetSideServerObject.scala index c8dcd4653..ab968aad8 100644 --- a/common/src/main/scala/net/psforever/objects/serverobject/PlanetSideServerObject.scala +++ b/common/src/main/scala/net/psforever/objects/serverobject/PlanetSideServerObject.scala @@ -33,8 +33,4 @@ abstract class PlanetSideServerObject extends PlanetSideGameObject } actor } - - def Continent : String = "nowhere" - - def Continent_=(zone : String) = Continent } diff --git a/common/src/main/scala/net/psforever/objects/serverobject/structures/Amenity.scala b/common/src/main/scala/net/psforever/objects/serverobject/structures/Amenity.scala index 9a3ea7f85..22ba8371b 100644 --- a/common/src/main/scala/net/psforever/objects/serverobject/structures/Amenity.scala +++ b/common/src/main/scala/net/psforever/objects/serverobject/structures/Amenity.scala @@ -1,29 +1,10 @@ // Copyright (c) 2017 PSForever package net.psforever.objects.serverobject.structures -import net.psforever.objects.Vehicle import net.psforever.objects.serverobject.PlanetSideServerObject -import net.psforever.objects.zones.{Zone => World } +import net.psforever.objects.zones.Zone import net.psforever.types.{PlanetSideEmpire, Vector3} -/** - * Amenities are elements of the game that belong to other elements of the game. - * Their owners are also elements of the game, ones that understand that they belong to a specific `Zone` object. - * @see `PlanetSideServerObject` - * @see `Zone` - * @see `ZoneAware` - */ -trait AmenityOwner extends PlanetSideServerObject { - private var zoneRef : World = World.Nowhere - - def Zone_=(zone : World) : World = { - zoneRef = zone - Zone - } - - def Zone : World = zoneRef -} - /** * Amenities are elements of the game that belong to other elements of the game.
*
@@ -31,7 +12,7 @@ trait AmenityOwner extends PlanetSideServerObject { * An `Amenity` is a server object that maintains a fixed association with another server object. * This association strips away at the internalization and redirects a reference to some properties somewhere else. * An `Amenity` object belongs to its `Owner` object; - * the `Amenity` objects looks to its `Owner` object for some of its properties. + * the `Amenity` objects look to its `Owner` object for some of its properties. * @see `FactionAffinity` */ abstract class Amenity extends PlanetSideServerObject { @@ -73,9 +54,11 @@ abstract class Amenity extends PlanetSideServerObject { LocationOffset } - override def Continent = Owner match { - case o : Building => o.Zone.Id - case o : Vehicle => o.Continent - case _ => super.Continent - } + override def Zone : Zone = Owner.Zone + + override def Zone_=(zone : Zone) = Owner.Zone + + override def Continent : String = Owner.Continent + + override def Continent_=(str : String) : String = Owner.Continent } diff --git a/common/src/main/scala/net/psforever/objects/serverobject/structures/AmenityOwner.scala b/common/src/main/scala/net/psforever/objects/serverobject/structures/AmenityOwner.scala new file mode 100644 index 000000000..2199da3e6 --- /dev/null +++ b/common/src/main/scala/net/psforever/objects/serverobject/structures/AmenityOwner.scala @@ -0,0 +1,21 @@ +// Copyright (c) 2019 PSForever +package net.psforever.objects.serverobject.structures + +import net.psforever.objects.serverobject.PlanetSideServerObject + +/** + * Amenities are elements of the game that belong to other elements of the game. + * Their owners are also elements of the game, ones that understand that they belong to a specific `Zone` object. + * @see `PlanetSideServerObject` + */ +abstract class AmenityOwner extends PlanetSideServerObject { + private var amenities : List[Amenity] = List.empty + + def Amenities : List[Amenity] = amenities + + def Amenities_=(obj : Amenity) : List[Amenity] = { + amenities = amenities :+ obj + obj.Owner = this + amenities + } +} diff --git a/common/src/main/scala/net/psforever/objects/serverobject/structures/Building.scala b/common/src/main/scala/net/psforever/objects/serverobject/structures/Building.scala index 537f04f79..bb9e40199 100644 --- a/common/src/main/scala/net/psforever/objects/serverobject/structures/Building.scala +++ b/common/src/main/scala/net/psforever/objects/serverobject/structures/Building.scala @@ -6,7 +6,6 @@ import java.util.concurrent.TimeUnit import akka.actor.ActorContext import net.psforever.objects.{GlobalDefinitions, Player} import net.psforever.objects.definition.ObjectDefinition -import net.psforever.objects.serverobject.PlanetSideServerObject import net.psforever.objects.serverobject.hackable.Hackable import net.psforever.objects.serverobject.resourcesilo.ResourceSilo import net.psforever.objects.serverobject.terminals.CaptureTerminal @@ -20,14 +19,12 @@ class Building(private val name: String, private val map_id : Int, private val zone : Zone, private val buildingType : StructureType.Value, - private val buildingDefinition : ObjectDefinition) extends PlanetSideServerObject { - with AmenityOwner { + private val buildingDefinition : ObjectDefinition) extends AmenityOwner { /** * The map_id is the identifier number used in BuildingInfoUpdateMessage. This is the index that the building appears in the MPO file starting from index 1 * The GUID is the identifier number used in SetEmpireMessage / Facility hacking / PlanetSideAttributeMessage. */ private var faction : PlanetSideEmpire.Value = PlanetSideEmpire.NEUTRAL - private var amenities : List[Amenity] = List.empty private var playersInSOI : List[Player] = List.empty super.Zone_=(zone) @@ -46,14 +43,6 @@ class Building(private val name: String, Faction } - def Amenities : List[Amenity] = amenities - - def Amenities_=(obj : Amenity) : List[Amenity] = { - amenities = amenities :+ obj - obj.Owner = this - amenities - } - def CaptureConsoleIsHacked : Boolean = { Amenities.find(x => x.Definition == GlobalDefinitions.capture_terminal).asInstanceOf[Option[CaptureTerminal]] match { case Some(obj: CaptureTerminal) => @@ -69,8 +58,6 @@ class Building(private val name: String, playersInSOI } - def Zone : Zone = zone - // Get all lattice neighbours def Neighbours: Option[Set[Building]] = { zone.Lattice find this match { @@ -82,10 +69,9 @@ class Building(private val name: String, // Get all lattice neighbours matching the specified faction def Neighbours(faction: PlanetSideEmpire.Value): Option[Set[Building]] = { this.Neighbours match { - case Some(x: Set[Building]) => { + case Some(x: Set[Building]) => val matching = x.filter(b => b.Faction == faction) if(matching.isEmpty) None else Some(matching) - } case None => None } } @@ -101,14 +87,14 @@ class Building(private val name: String, Boolean, Boolean ) = { //if we have a silo, get the NTU level - val ntuLevel : Int = amenities.find(_.Definition == GlobalDefinitions.resource_silo) match { + val ntuLevel : Int = Amenities.find(_.Definition == GlobalDefinitions.resource_silo) match { case Some(obj: ResourceSilo) => obj.CapacitorDisplay.toInt case _ => //we have no silo; we have unlimited power 10 } //if we have a capture terminal, get the hack status & time (in milliseconds) from control console if it exists - val (hacking, hackingFaction, hackTime) : (Boolean, PlanetSideEmpire.Value, Long) = amenities.find(_.Definition == GlobalDefinitions.capture_terminal) match { + val (hacking, hackingFaction, hackTime) : (Boolean, PlanetSideEmpire.Value, Long) = Amenities.find(_.Definition == GlobalDefinitions.capture_terminal) match { case Some(obj: CaptureTerminal with Hackable) => obj.HackedBy match { case Some(Hackable.HackInfo(_, _, hfaction, _, start, length)) => @@ -124,7 +110,7 @@ class Building(private val name: String, val (generatorState, bootGeneratorPain) = (PlanetSideGeneratorState.Normal, false) //if we have spawn tubes, determine if any of them are active val (spawnTubesNormal, boostSpawnPain) : (Boolean, Boolean) = { - val o = amenities.collect({ case _ : SpawnTube => true }) ///TODO obj.Health > 0 + val o = Amenities.collect({ case _ : SpawnTube => true }) ///TODO obj.Health > 0 if(o.nonEmpty) { (o.foldLeft(false)(_ || _), false) //TODO poll pain field strength } diff --git a/common/src/main/scala/net/psforever/objects/zones/ZoneAware.scala b/common/src/main/scala/net/psforever/objects/zones/ZoneAware.scala index 1c986fad6..b71c5ed00 100644 --- a/common/src/main/scala/net/psforever/objects/zones/ZoneAware.scala +++ b/common/src/main/scala/net/psforever/objects/zones/ZoneAware.scala @@ -1,8 +1,10 @@ // Copyright (c) 2017 PSForever package net.psforever.objects.zones +import net.psforever.objects.zones.{ Zone => World } + /** - * The object must be able to recall on which of the defined game worlds (zones) that it exists on command. + * The entity must be able to recall on which of the defined game worlds (zones) that it exists on command. * The game world identifier string produced should be equivalent to a `Zone.Id` string for some equivalent `Zone` object. * The identifier "nowhere" is recommended as the default invalid location. * @see `InterstellarCluster` @@ -10,7 +12,37 @@ package net.psforever.objects.zones * @see `Zone` */ trait ZoneAware { - def Continent : String + private var zoneRef : World = World.Nowhere + /** + * Normally, an entity is the resident of a `Zone` object and that is what it considers its "continent". + * Since the entity may switch between `Zone` objects, however, + * if the type of entity is allowed to do that, + * it may become useful to allow the entity to identify as belonging to its future zone earlier than reference assignment. + */ + private var continent : Option[String] = None - def Continent_=(zone : String) : String + def Zone : World = zoneRef + + /** + * When assigning a new `Zone` object for the `Vehicle` object, eliminate + * @param zone a reference to the `Zone` object + * @return a reference to the `Zone` object + */ + def Zone_=(zone : World) : World = { + continent = None + zoneRef = zone + Zone + } + + def Continent : String = continent.getOrElse(Zone.Id) + + /** + * Give the entity a custom `Zone` identifier. + * @param zoneId the custom identifier of the `Zone` object + * @return the identifier of the `Zone` object + */ + def Continent_=(zoneId : String) : String = { + continent = Some(zoneId) + Continent + } } diff --git a/common/src/test/scala/objects/BuildingTest.scala b/common/src/test/scala/objects/BuildingTest.scala index e0b0e779e..5ed03161f 100644 --- a/common/src/test/scala/objects/BuildingTest.scala +++ b/common/src/test/scala/objects/BuildingTest.scala @@ -104,7 +104,7 @@ class BuildingTest extends Specification { class WarpGateTest extends Specification { "WarpGate" should { "construct" in { - val bldg = WarpGate("Building", 0, 10, Zone.Nowhere, GlobalDefinitions.warpgate) + val bldg = WarpGate("WarpGate", 0, 10, Zone.Nowhere, GlobalDefinitions.warpgate) bldg.MapId mustEqual 10 bldg.Actor mustEqual ActorRef.noSender bldg.Amenities mustEqual Nil diff --git a/common/src/test/scala/objects/ResourceSiloTest.scala b/common/src/test/scala/objects/ResourceSiloTest.scala index a941771a3..c03ae79bc 100644 --- a/common/src/test/scala/objects/ResourceSiloTest.scala +++ b/common/src/test/scala/objects/ResourceSiloTest.scala @@ -13,7 +13,7 @@ import net.psforever.objects.zones.{Zone, ZoneMap} import net.psforever.packet.game.{PlanetSideGUID, UseItemMessage} import net.psforever.types.{CharacterGender, CharacterVoice, PlanetSideEmpire, Vector3} import org.specs2.mutable.Specification -import services.{Service, ServiceManager} +import services.ServiceManager import services.avatar.{AvatarAction, AvatarServiceMessage} import scala.concurrent.duration._ @@ -108,7 +108,7 @@ class ResourceSiloControlNtuWarningTest extends ActorTest { obj.Actor = system.actorOf(Props(classOf[ResourceSiloControl], obj), "test-silo") obj.Actor ! "startup" val zone = new Zone("nowhere", new ZoneMap("nowhere-map"), 0) - obj.Owner = new Building("Building", building_guid = 6, map_id = 0, Zone.Nowhere, StructureType.Building, GlobalDefinitions.building) + obj.Owner = new Building("Building", building_guid = 6, map_id = 0, zone, StructureType.Building, GlobalDefinitions.building) val zoneEvents = TestProbe("zone-events") "Resource silo" should { @@ -139,7 +139,7 @@ class ResourceSiloControlUpdate1Test extends ActorTest { obj.Actor = system.actorOf(Props(classOf[ResourceSiloControl], obj), "test-silo") obj.Actor ! "startup" val zone = new Zone("nowhere", new ZoneMap("nowhere-map"), 0) - val bldg = new Building("Building", building_guid = 6, map_id = 0, Zone.Nowhere, StructureType.Building, GlobalDefinitions.building) + val bldg = new Building("Building", building_guid = 6, map_id = 0, zone, StructureType.Building, GlobalDefinitions.building) obj.Owner = bldg val zoneEvents = TestProbe("zone-events") val buildingEvents = TestProbe("building-events") @@ -204,7 +204,7 @@ class ResourceSiloControlUpdate2Test extends ActorTest { obj.Actor = system.actorOf(Props(classOf[ResourceSiloControl], obj), "test-silo") obj.Actor ! "startup" val zone = new Zone("nowhere", new ZoneMap("nowhere-map"), 0) - val bldg = new Building("Building", building_guid = 6, map_id = 0, Zone.Nowhere, StructureType.Building, GlobalDefinitions.building) + val bldg = new Building("Building", building_guid = 6, map_id = 0, zone, StructureType.Building, GlobalDefinitions.building) obj.Owner = bldg val zoneEvents = TestProbe("zone-events") val buildingEvents = TestProbe("building-events") @@ -222,8 +222,8 @@ class ResourceSiloControlUpdate2Test extends ActorTest { assert(obj.LowNtuWarningOn) obj.Actor ! ResourceSilo.UpdateChargeLevel(105) - val reply1 = zoneEvents.receiveOne(500 milliseconds) - val reply2 = buildingEvents.receiveOne(500 milliseconds) + val reply1 = zoneEvents.receiveOne(1000 milliseconds) + val reply2 = buildingEvents.receiveOne(1000 milliseconds) assert(obj.ChargeLevel == 205) assert(obj.CapacitorDisplay == 3) assert(reply1.isInstanceOf[AvatarServiceMessage]) @@ -261,7 +261,7 @@ class ResourceSiloControlNoUpdateTest extends ActorTest { obj.Actor = system.actorOf(Props(classOf[ResourceSiloControl], obj), "test-silo") obj.Actor ! "startup" val zone = new Zone("nowhere", new ZoneMap("nowhere-map"), 0) - val bldg = new Building("Building", building_guid = 6, map_id = 0, Zone.Nowhere, StructureType.Building, GlobalDefinitions.building) + val bldg = new Building("Building", building_guid = 6, map_id = 0, zone, StructureType.Building, GlobalDefinitions.building) obj.Owner = bldg val zoneEvents = TestProbe("zone-events") val buildingEvents = TestProbe("building-events") diff --git a/common/src/test/scala/objects/ServerObjectBuilderTest.scala b/common/src/test/scala/objects/ServerObjectBuilderTest.scala index 43fdb1ba0..d4c97f554 100644 --- a/common/src/test/scala/objects/ServerObjectBuilderTest.scala +++ b/common/src/test/scala/objects/ServerObjectBuilderTest.scala @@ -18,7 +18,7 @@ class BuildingBuilderTest extends ActorTest { "Building object" should { "build" in { val structure : (String, Int,Int,Zone,ActorContext)=>Building = Building.Structure(StructureType.Building) - val actor = system.actorOf(Props(classOf[ServerObjectBuilderTest.BuildingTestActor], structure, 10, 10, Zone.Nowhere), "building") + val actor = system.actorOf(Props(classOf[ServerObjectBuilderTest.BuildingTestActor], structure, "Building", 10, 10, Zone.Nowhere), "building") actor ! "!" val reply = receiveOne(Duration.create(1000, "ms")) @@ -33,7 +33,7 @@ class WarpGateBuilderTest extends ActorTest { "WarpGate object" should { "build" in { val structure : (String,Int,Int,Zone,ActorContext)=>Building = WarpGate.Structure - val actor = system.actorOf(Props(classOf[ServerObjectBuilderTest.BuildingTestActor], structure, 10, 10, Zone.Nowhere), "wgate") + val actor = system.actorOf(Props(classOf[ServerObjectBuilderTest.BuildingTestActor], structure, "wgate", 10, 10, Zone.Nowhere), "wgate") actor ! "!" val reply = receiveOne(Duration.create(1000, "ms")) diff --git a/pslogin/src/main/scala/WorldSessionActor.scala b/pslogin/src/main/scala/WorldSessionActor.scala index 676d90550..4033f1dc7 100644 --- a/pslogin/src/main/scala/WorldSessionActor.scala +++ b/pslogin/src/main/scala/WorldSessionActor.scala @@ -1159,7 +1159,7 @@ class WorldSessionActor extends Actor with MDCContextAware { if(projectile.profile.ExistsOnRemoteClients) { //spawn projectile on other clients val definition = projectile.Definition - avatarService ! AvatarServiceMessage( + continent.AvatarEvents ! AvatarServiceMessage( continent.Id, AvatarAction.LoadProjectile(player.GUID, definition.ObjectId, projectile_guid, definition.Packet.ConstructorData(projectile).get) ) @@ -1172,7 +1172,7 @@ class WorldSessionActor extends Actor with MDCContextAware { case Some(obj : Projectile) if obj.profile.ExistsOnRemoteClients => //spawn projectile on other clients val definition = obj.Definition - avatarService ! AvatarServiceMessage( + continent.AvatarEvents ! AvatarServiceMessage( continent.Id, AvatarAction.LoadProjectile(player.GUID, definition.ObjectId, projectile_guid, definition.Packet.ConstructorData(obj).get) ) @@ -1282,12 +1282,12 @@ class WorldSessionActor extends Actor with MDCContextAware { val playerGUID = player.GUID if(damageToHealth > 0) { sendResponse(PlanetsideAttributeMessage(playerGUID, 0, health)) - avatarService ! AvatarServiceMessage(continent.Id, AvatarAction.PlanetsideAttribute(playerGUID, 0, health)) + continent.AvatarEvents ! AvatarServiceMessage(continent.Id, AvatarAction.PlanetsideAttribute(playerGUID, 0, health)) } if(damageToArmor > 0) { sendResponse(PlanetsideAttributeMessage(playerGUID, 4, armor)) - avatarService ! AvatarServiceMessage(continent.Id, AvatarAction.PlanetsideAttribute(playerGUID, 4, armor)) + continent.AvatarEvents ! AvatarServiceMessage(continent.Id, AvatarAction.PlanetsideAttribute(playerGUID, 4, armor)) } if(damageToCapacitor > 0) { @@ -1659,7 +1659,7 @@ class WorldSessionActor extends Actor with MDCContextAware { continent.GUID(player.VehicleSeated) match { case Some(mountable: Amenity with Mountable) => if(mountable.Owner.GUID == capture_terminal.Owner.GUID) { - vehicleService ! VehicleServiceMessage(continent.Id, VehicleAction.KickPassenger(player.GUID, mountable.Seats.head._1, true, mountable.GUID)) + continent.VehicleEvents ! VehicleServiceMessage(continent.Id, VehicleAction.KickPassenger(player.GUID, mountable.Seats.head._1, true, mountable.GUID)) } case _ => ; } @@ -3919,6 +3919,7 @@ class WorldSessionActor extends Actor with MDCContextAware { } } } + CapacitorTick(jump_thrust) //if the player lost all stamina this turn (had stamina at the start), do not renew 1 stamina if(!isMoving && (if(player.Stamina > 0) player.Stamina < player.MaxStamina else !hadStaminaBefore)) { player.Stamina = player.Stamina + 1 @@ -3927,8 +3928,6 @@ class WorldSessionActor extends Actor with MDCContextAware { else { player.Stamina > 0 } - - CapacitorTick(jump_thrust) } else { timeDL = 0 @@ -3941,13 +3940,13 @@ class WorldSessionActor extends Actor with MDCContextAware { if(implantsAreActive && !hasStaminaAfter) { //implants deactivated at 0 stamina if(avatar.Implants(0).Active) { avatar.Implants(0).Active = false - avatarService ! AvatarServiceMessage(continent.Id, AvatarAction.PlanetsideAttribute(player.GUID, 28, avatar.Implant(0).id * 2)) + continent.AvatarEvents ! AvatarServiceMessage(continent.Id, AvatarAction.PlanetsideAttribute(player.GUID, 28, avatar.Implant(0).id * 2)) sendResponse(AvatarImplantMessage(PlanetSideGUID(player.GUID.guid), ImplantAction.Activation, 0, 0)) timeDL = 0 } if(avatar.Implants(1).Active) { avatar.Implants(1).Active = false - avatarService ! AvatarServiceMessage(continent.Id, AvatarAction.PlanetsideAttribute(player.GUID, 28, avatar.Implant(1).id * 2)) + continent.AvatarEvents ! AvatarServiceMessage(continent.Id, AvatarAction.PlanetsideAttribute(player.GUID, 28, avatar.Implant(1).id * 2)) sendResponse(AvatarImplantMessage(PlanetSideGUID(player.GUID.guid), ImplantAction.Activation, 1, 0)) timeSurge = 0 } @@ -4063,7 +4062,7 @@ class WorldSessionActor extends Actor with MDCContextAware { projectile.Position = shot_pos projectile.Orientation = shot_orient projectile.Velocity = shot_vel - avatarService ! AvatarServiceMessage(continent.Id, AvatarAction.ProjectileState(player.GUID, projectileGlobalUID, shot_pos, shot_vel, shot_orient, seq, end, target_guid)) + continent.AvatarEvents ! AvatarServiceMessage(continent.Id, AvatarAction.ProjectileState(player.GUID, projectileGlobalUID, shot_pos, shot_vel, shot_orient, seq, end, target_guid)) case _ if seq == 0 => /* missing the first packet in the sequence is permissible */ case _ => @@ -4352,7 +4351,7 @@ class WorldSessionActor extends Actor with MDCContextAware { shooting = Some(item_guid) //special case - suppress the decimator's alternate fire mode, by projectile if(tool.Projectile != GlobalDefinitions.phoenix_missile_guided_projectile) { - avatarService ! AvatarServiceMessage(continent.Id, AvatarAction.ChangeFireState_Start(player.GUID, item_guid)) + continent.AvatarEvents ! AvatarServiceMessage(continent.Id, AvatarAction.ChangeFireState_Start(player.GUID, item_guid)) } } else { @@ -4383,12 +4382,12 @@ class WorldSessionActor extends Actor with MDCContextAware { if(tool.Definition == GlobalDefinitions.phoenix && tool.Projectile != GlobalDefinitions.phoenix_missile_guided_projectile) { //suppress the decimator's alternate fire mode, however - avatarService ! AvatarServiceMessage(continent.Id, AvatarAction.ChangeFireState_Start(player.GUID, item_guid)) + continent.AvatarEvents ! AvatarServiceMessage(continent.Id, AvatarAction.ChangeFireState_Start(player.GUID, item_guid)) } - avatarService ! AvatarServiceMessage(continent.Id, AvatarAction.ChangeFireState_Stop(player.GUID, item_guid)) + continent.AvatarEvents ! AvatarServiceMessage(continent.Id, AvatarAction.ChangeFireState_Stop(player.GUID, item_guid)) Some(tool) case Some(tool) => //permissible, for now - avatarService ! AvatarServiceMessage(continent.Id, AvatarAction.ChangeFireState_Stop(player.GUID, item_guid)) + continent.AvatarEvents ! AvatarServiceMessage(continent.Id, AvatarAction.ChangeFireState_Stop(player.GUID, item_guid)) Some(tool) case _ => log.warn(s"ChangeFireState_Stop: received an unexpected message about $item_guid") @@ -4606,7 +4605,7 @@ class WorldSessionActor extends Actor with MDCContextAware { else { projectile.Miss() if(projectile.profile.ExistsOnRemoteClients && projectile.HasGUID) { - avatarService ! AvatarServiceMessage(continent.Id, AvatarAction.ProjectileExplodes(player.GUID, projectile.GUID, projectile)) + continent.AvatarEvents ! AvatarServiceMessage(continent.Id, AvatarAction.ProjectileExplodes(player.GUID, projectile.GUID, projectile)) taskResolver ! UnregisterProjectile(projectile) } } @@ -5548,7 +5547,7 @@ class WorldSessionActor extends Actor with MDCContextAware { if(projectile_info.ExistsOnRemoteClients) { log.trace(s"WeaponFireMessage: ${projectile_info.Name} is a remote projectile") taskResolver ! (if(projectile.HasGUID) { - avatarService ! AvatarServiceMessage(continent.Id, AvatarAction.ProjectileExplodes(player.GUID, projectile.GUID, projectile)) + continent.AvatarEvents ! AvatarServiceMessage(continent.Id, AvatarAction.ProjectileExplodes(player.GUID, projectile.GUID, projectile)) ReregisterProjectile(projectile) } else { @@ -5576,7 +5575,7 @@ class WorldSessionActor extends Actor with MDCContextAware { if(detectedTargets.nonEmpty) { val mode = 7 + (weapon.Projectile == GlobalDefinitions.wasp_rocket_projectile) detectedTargets.foreach { target => - avatarService ! AvatarServiceMessage(target, AvatarAction.ProjectileAutoLockAwareness(mode)) + continent.AvatarEvents ! AvatarServiceMessage(target, AvatarAction.ProjectileAutoLockAwareness(mode)) } } case _ => ; @@ -6271,7 +6270,7 @@ class WorldSessionActor extends Actor with MDCContextAware { TaskResolver.GiveTask( new Task() { private val globalProjectile = obj - private val localAnnounce = avatarService + private val localAnnounce = continent.AvatarEvents private val localMsg = AvatarServiceMessage(continent.Id, AvatarAction.ObjectDelete(player.GUID, obj.GUID, 2)) override def isComplete : Task.Resolution.Value = { @@ -7792,7 +7791,7 @@ class WorldSessionActor extends Actor with MDCContextAware { sendResponse(PlanetsideAttributeMessage(amenityId, 47, if(silo.LowNtuWarningOn) 1 else 0)) if(silo.ChargeLevel == 0) { - sendResponse(PlanetsideAttributeMessage(silo.Owner.asInstanceOf[Building].GUID, 48, 1)) + sendResponse(PlanetsideAttributeMessage(silo.Owner.GUID, 48, 1)) } case _ => ; } @@ -10201,16 +10200,16 @@ class WorldSessionActor extends Actor with MDCContextAware { case PlanetSideEmpire.NC => if(player.Capacitor > 0) player.UsingSpecial = SpecialExoSuitDefinition.Mode.Shielded case _ => log.warn(s"Player ${player.Name} tried to use a MAX special ability but their faction doesn't have one") } - if(player.UsingSpecial == SpecialExoSuitDefinition.Mode.Overdrive || player.UsingSpecial == SpecialExoSuitDefinition.Mode.Shielded) { - avatarService ! AvatarServiceMessage(continent.Id, AvatarAction.PlanetsideAttributeToAll(player.GUID, 8, 1)) + continent.AvatarEvents ! AvatarServiceMessage(continent.Id, AvatarAction.PlanetsideAttributeToAll(player.GUID, 8, 1)) } } else { player.UsingSpecial = SpecialExoSuitDefinition.Mode.Normal - avatarService ! AvatarServiceMessage(continent.Id, AvatarAction.PlanetsideAttributeToAll(player.GUID, 8, 0)) + continent.AvatarEvents ! AvatarServiceMessage(continent.Id, AvatarAction.PlanetsideAttributeToAll(player.GUID, 8, 0)) } } + } /** * The main purpose of this method is to determine which targets will receive "locked on" warnings from remote projectiles. @@ -10267,7 +10266,7 @@ class WorldSessionActor extends Actor with MDCContextAware { * @param local_index an index of the absolute sequence of the projectile, for internal lists */ def CleanUpRemoteProjectile(projectile_guid : PlanetSideGUID, projectile : Projectile, local_index : Int) : Unit = { - avatarService ! AvatarServiceMessage(continent.Id, AvatarAction.ProjectileExplodes(player.GUID, projectile_guid, projectile)) + continent.AvatarEvents ! AvatarServiceMessage(continent.Id, AvatarAction.ProjectileExplodes(player.GUID, projectile_guid, projectile)) taskResolver ! UnregisterProjectile(projectile) projectiles(local_index) match { case Some(obj) if !obj.isResolved => obj.Miss