mirror of
https://github.com/2revoemag/PSF-BotServer.git
synced 2026-01-26 13:24:45 +00:00
more tests for the proximity amenities; added the other silo in Anguta, Ceryshen and the terminal-facing silo in home3; initial work on FacilityBenefitShieldCharge packet and tests
This commit is contained in:
parent
a513f4996e
commit
e9aac5514a
|
|
@ -29,3 +29,74 @@ final case class InfantryLoadout(label : String,
|
|||
inventory : List[Loadout.SimplifiedEntry],
|
||||
exosuit : ExoSuitType.Value,
|
||||
subtype : Int) extends Loadout(label, visible_slots, inventory)
|
||||
|
||||
object InfantryLoadout {
|
||||
import net.psforever.objects.Player
|
||||
import net.psforever.objects.GlobalDefinitions
|
||||
import net.psforever.objects.equipment.Equipment
|
||||
|
||||
/**
|
||||
* The sub-type of the player's uniform.
|
||||
* Applicable to mechanized assault units, mainly.
|
||||
* The subtype is reported as a number but indicates the specialization - anti-infantry, ani-vehicular, anti-air - of the suit
|
||||
* as indicated by the arm weapon(s).
|
||||
* @param player the player
|
||||
* @return the numeric subtype
|
||||
*/
|
||||
def DetermineSubtype(player : Player) : Int = {
|
||||
DetermineSubtypeA(player.ExoSuit, player.Slot(0).Equipment)
|
||||
}
|
||||
|
||||
/**
|
||||
* The sub-type of the player's uniform.
|
||||
* Applicable to mechanized assault units, mainly.
|
||||
* The subtype is reported as a number but indicates the specialization - anti-infantry, ani-vehicular, anti-air - of the suit
|
||||
* as indicated by the arm weapon(s).
|
||||
* @param suit the player's uniform;
|
||||
* the target is for MAX armors
|
||||
* @param weapon any weapon the player may have it his "first pistol slot;"
|
||||
* to a MAX, that is its "primary weapon slot"
|
||||
* @return the numeric subtype
|
||||
*/
|
||||
def DetermineSubtypeA(suit : ExoSuitType.Value, weapon : Option[Equipment]) : Int = {
|
||||
if(suit == ExoSuitType.MAX) {
|
||||
weapon match {
|
||||
case Some(item) =>
|
||||
item.Definition match {
|
||||
case GlobalDefinitions.trhev_dualcycler | GlobalDefinitions.nchev_scattercannon | GlobalDefinitions.vshev_quasar =>
|
||||
1
|
||||
case GlobalDefinitions.trhev_pounder | GlobalDefinitions.nchev_falcon | GlobalDefinitions.vshev_comet =>
|
||||
2
|
||||
case GlobalDefinitions.trhev_burster | GlobalDefinitions.nchev_sparrow | GlobalDefinitions.vshev_starfire =>
|
||||
3
|
||||
case _ =>
|
||||
0
|
||||
}
|
||||
case None =>
|
||||
0
|
||||
}
|
||||
}
|
||||
else {
|
||||
0
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* The sub-type of the player's uniform, as used in `FavoritesMessage`.<br>
|
||||
* <br>
|
||||
* The values for `Standard`, `Infiltration`, and the generic `MAX` are not perfectly known.
|
||||
* The latter-most exo-suit option is presumed.
|
||||
* @param suit the player's uniform
|
||||
* @param subtype the mechanized assault exo-suit subtype as determined by their arm weapons
|
||||
* @return the numeric subtype
|
||||
*/
|
||||
def DetermineSubtypeB(suit : ExoSuitType.Value, subtype : Int) : Int = {
|
||||
suit match {
|
||||
case ExoSuitType.Standard => 0
|
||||
case ExoSuitType.Agile => 1
|
||||
case ExoSuitType.Reinforced => 2
|
||||
case ExoSuitType.MAX => 3 + subtype //4, 5, 6
|
||||
case ExoSuitType.Infiltration => 7
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -5,7 +5,6 @@ import net.psforever.objects._
|
|||
import net.psforever.objects.definition._
|
||||
import net.psforever.objects.equipment.Equipment
|
||||
import net.psforever.objects.inventory.InventoryItem
|
||||
import net.psforever.types.ExoSuitType
|
||||
|
||||
import scala.annotation.tailrec
|
||||
|
||||
|
|
@ -120,42 +119,16 @@ object Loadout {
|
|||
* @return the numeric subtype
|
||||
*/
|
||||
def DetermineSubtype(player : Player) : Int = {
|
||||
DetermineSubtype(player.ExoSuit, player.Slot(0).Equipment)
|
||||
InfantryLoadout.DetermineSubtype(player)
|
||||
}
|
||||
|
||||
/**
|
||||
* The sub-type of the player's uniform.
|
||||
* Applicable to mechanized assault units, mainly.
|
||||
* The subtype is reported as a number but indicates the specialization - anti-infantry, ani-vehicular, anti-air - of the suit
|
||||
* as indicated by the arm weapon(s).
|
||||
* @param suit the player's uniform;
|
||||
* the target is for MAX armors
|
||||
* @param weapon any weapon the player may have it his "first pistol slot;"
|
||||
* to a MAX, that is its "primary weapon slot"
|
||||
* @return the numeric subtype
|
||||
* The sub-type of the vehicle.
|
||||
* Vehicle's have no subtype.
|
||||
* @param vehicle the vehicle
|
||||
* @return the numeric subtype, always 0
|
||||
*/
|
||||
def DetermineSubtype(suit : ExoSuitType.Value, weapon : Option[Equipment]) : Int = {
|
||||
if(suit == ExoSuitType.MAX) {
|
||||
weapon match {
|
||||
case Some(item) =>
|
||||
item.Definition match {
|
||||
case GlobalDefinitions.trhev_dualcycler | GlobalDefinitions.nchev_scattercannon | GlobalDefinitions.vshev_quasar =>
|
||||
1
|
||||
case GlobalDefinitions.trhev_pounder | GlobalDefinitions.nchev_falcon | GlobalDefinitions.vshev_comet =>
|
||||
2
|
||||
case GlobalDefinitions.trhev_burster | GlobalDefinitions.nchev_sparrow | GlobalDefinitions.vshev_starfire =>
|
||||
3
|
||||
case _ =>
|
||||
0
|
||||
}
|
||||
case None =>
|
||||
0
|
||||
}
|
||||
}
|
||||
else {
|
||||
0
|
||||
}
|
||||
}
|
||||
def DetermineSubtype(vehicle : Vehicle) : Int = 0
|
||||
|
||||
/**
|
||||
* Overloaded entry point for constructing simplified blueprints from holster slot equipment.
|
||||
|
|
|
|||
|
|
@ -1,18 +1,12 @@
|
|||
// Copyright (c) 2017 PSForever
|
||||
package net.psforever.objects.serverobject.terminals
|
||||
|
||||
import net.psforever.objects.Player
|
||||
import net.psforever.packet.game.ItemTransactionMessage
|
||||
|
||||
/**
|
||||
* The definition for any `Terminal` that is of a type "medical_terminal".
|
||||
* This includes the limited proximity-based functionality of the formal medical terminals
|
||||
* and the actual proximity-based functionality of the cavern crystals.<br>
|
||||
* <br>
|
||||
* Do not confuse the "medical_terminal" category and the actual `medical_terminal` object (529).
|
||||
* Objects created by this definition being linked by their use of `ProximityTerminalUseMessage` is more accurate.
|
||||
* This includes the functionality of the formal medical terminals and some of the cavern crystals.
|
||||
* Do not confuse the game's internal "medical_terminal" object category and the actual `medical_terminal` object (529).
|
||||
*/
|
||||
class MedicalTerminalDefinition(objectId : Int) extends TerminalDefinition(objectId) {
|
||||
class MedicalTerminalDefinition(objectId : Int) extends TerminalDefinition(objectId) with ProximityDefinition {
|
||||
Name = if(objectId == 38) {
|
||||
"adv_med_terminal"
|
||||
}
|
||||
|
|
@ -31,6 +25,4 @@ class MedicalTerminalDefinition(objectId : Int) extends TerminalDefinition(objec
|
|||
else {
|
||||
throw new IllegalArgumentException("medical terminal must be either object id 38, 225, 226, 529, or 689")
|
||||
}
|
||||
|
||||
def Buy(player : Player, msg : ItemTransactionMessage) : Terminal.Exchange = Terminal.NoDeal()
|
||||
}
|
||||
|
|
|
|||
|
|
@ -0,0 +1,15 @@
|
|||
// Copyright (c) 2017 PSForever
|
||||
package net.psforever.objects.serverobject.terminals
|
||||
|
||||
import net.psforever.objects.Player
|
||||
import net.psforever.packet.game.ItemTransactionMessage
|
||||
|
||||
/**
|
||||
* The definition for any `Terminal` that possesses a proximity-based effect.
|
||||
* This includes the limited proximity-based functionality of the formal medical terminals
|
||||
* and the actual proximity-based functionality of the cavern crystals.
|
||||
* Objects created by this definition being linked by their use of `ProximityTerminalUseMessage`.
|
||||
*/
|
||||
trait ProximityDefinition {
|
||||
def Buy(player : Player, msg : ItemTransactionMessage) : Terminal.Exchange = Terminal.NoDeal()
|
||||
}
|
||||
|
|
@ -9,14 +9,14 @@ package net.psforever.objects.serverobject.terminals
|
|||
* For example, the cavern crystals are considered owner-neutral elements that are not attached to a `Building` object.
|
||||
* @param tdef the `ObjectDefinition` that constructs this object and maintains some of its immutable fields
|
||||
*/
|
||||
class ProximityTerminal(tdef : MedicalTerminalDefinition) extends Terminal(tdef) with ProximityUnit
|
||||
class ProximityTerminal(tdef : TerminalDefinition with ProximityDefinition) extends Terminal(tdef) with ProximityUnit
|
||||
|
||||
object ProximityTerminal {
|
||||
/**
|
||||
* Overloaded constructor.
|
||||
* @param tdef the `ObjectDefinition` that constructs this object and maintains some of its immutable fields
|
||||
*/
|
||||
def apply(tdef : MedicalTerminalDefinition) : ProximityTerminal = {
|
||||
def apply(tdef : TerminalDefinition with ProximityDefinition) : ProximityTerminal = {
|
||||
new ProximityTerminal(tdef)
|
||||
}
|
||||
|
||||
|
|
@ -29,7 +29,7 @@ object ProximityTerminal {
|
|||
* @param context a context to allow the object to properly set up `ActorSystem` functionality
|
||||
* @return the `Terminal` object
|
||||
*/
|
||||
def Constructor(tdef : MedicalTerminalDefinition)(id : Int, context : ActorContext) : Terminal = {
|
||||
def Constructor(tdef : TerminalDefinition with ProximityDefinition)(id : Int, context : ActorContext) : Terminal = {
|
||||
import akka.actor.Props
|
||||
val obj = ProximityTerminal(tdef)
|
||||
obj.Actor = context.actorOf(Props(classOf[ProximityTerminalControl], obj), s"${tdef.Name}_$id")
|
||||
|
|
|
|||
|
|
@ -1,27 +0,0 @@
|
|||
// Copyright (c) 2017 PSForever
|
||||
package net.psforever.objects.serverobject.terminals
|
||||
|
||||
import akka.actor.Actor
|
||||
import net.psforever.objects.serverobject.affinity.{FactionAffinity, FactionAffinityBehavior}
|
||||
|
||||
/**
|
||||
* An `Actor` that handles messages being dispatched to a specific `IFFLock`.
|
||||
* @param term the `RepairRearmSilo` object being governed
|
||||
* @see `CommonMessages`
|
||||
*/
|
||||
class RepairRearmControl(term : RepairRearmSilo) extends Actor with FactionAffinityBehavior.Check with ProximityUnit.Use {
|
||||
def FactionObject : FactionAffinity = term
|
||||
|
||||
def TerminalObject : Terminal with ProximityUnit = term
|
||||
|
||||
def receive : Receive = checkBehavior
|
||||
.orElse(proximityBehavior)
|
||||
.orElse {
|
||||
case Terminal.Request(player, msg) =>
|
||||
sender ! Terminal.TerminalMessage(player, msg, term.Request(player, msg))
|
||||
|
||||
case _ => ;
|
||||
}
|
||||
|
||||
override def toString : String = term.Definition.Name
|
||||
}
|
||||
|
|
@ -1,41 +0,0 @@
|
|||
// Copyright (c) 2017 PSForever
|
||||
package net.psforever.objects.serverobject.terminals
|
||||
|
||||
/**
|
||||
* A structure-owned server object for preserving vehicle loadouts,
|
||||
* obtaining vehicle weapon ammunition,
|
||||
* and, with proper perks, automatically repairing damage doen to allied vehicles.
|
||||
* A server object that is a "terminal" that can be accessed for amenities and services,
|
||||
* triggered when a certain distance from the unit itself (proximity-based).<br>
|
||||
* <br>
|
||||
* Unlike conventional terminals, this structure is not necessarily structure-owned.
|
||||
* For example, the cavern crystals are considered owner-neutral elements that are not attached to a `Building` object.
|
||||
* @param tdef the `ObjectDefinition` that constructs this object and maintains some of its immutable fields
|
||||
*/
|
||||
class RepairRearmSilo(tdef : RepairRearmSiloDefinition) extends Terminal(tdef) with ProximityUnit
|
||||
|
||||
object RepairRearmSilo {
|
||||
/**
|
||||
* Overloaded constructor.
|
||||
* @param tdef the `ObjectDefinition` that constructs this object and maintains some of its immutable fields
|
||||
*/
|
||||
def apply(tdef : RepairRearmSiloDefinition) : RepairRearmSilo = {
|
||||
new RepairRearmSilo(tdef)
|
||||
}
|
||||
|
||||
import akka.actor.ActorContext
|
||||
|
||||
/**
|
||||
* Instantiate an configure a `Terminal` object
|
||||
* @param tdef the `ObjectDefinition` that constructs this object and maintains some of its immutable fields
|
||||
* @param id the unique id that will be assigned to this entity
|
||||
* @param context a context to allow the object to properly set up `ActorSystem` functionality
|
||||
* @return the `Terminal` object
|
||||
*/
|
||||
def Constructor(tdef : RepairRearmSiloDefinition)(id : Int, context : ActorContext) : RepairRearmSilo = {
|
||||
import akka.actor.Props
|
||||
val obj = RepairRearmSilo(tdef)
|
||||
obj.Actor = context.actorOf(Props(classOf[RepairRearmControl], obj), s"${tdef.Name}_$id")
|
||||
obj
|
||||
}
|
||||
}
|
||||
|
|
@ -11,7 +11,7 @@ import net.psforever.packet.game.ItemTransactionMessage
|
|||
* The `Definition` for any `Terminal` that is of a type "repair_silo."
|
||||
* Has both proximity-based operation and direct access purchasing power.
|
||||
*/
|
||||
class RepairRearmSiloDefinition(objectId : Int) extends EquipmentTerminalDefinition(objectId) {
|
||||
class RepairRearmSiloDefinition(objectId : Int) extends EquipmentTerminalDefinition(objectId) with ProximityDefinition {
|
||||
Name = "repair_silo"
|
||||
|
||||
private val buyFunc : (Player, ItemTransactionMessage)=>Terminal.Exchange = EquipmentTerminalDefinition.Buy(Map.empty, Map.empty, Map.empty)
|
||||
|
|
|
|||
|
|
@ -312,7 +312,7 @@ object GamePacketOpcode extends Enumeration {
|
|||
= Value
|
||||
|
||||
private def noDecoder(opcode : GamePacketOpcode.Type) = (a : BitVector) =>
|
||||
Attempt.failure(Err(s"Could not find a marshaller for game packet ${opcode}"))
|
||||
Attempt.failure(Err(s"Could not find a marshaller for game packet $opcode"))
|
||||
|
||||
/// Mapping of packet IDs to decoders. Notice that we are using the @switch annotation which ensures that the Scala
|
||||
/// compiler will be able to optimize this as a lookup table (switch statement). Microbenchmarks show a nearly 400x
|
||||
|
|
@ -549,7 +549,7 @@ object GamePacketOpcode extends Enumeration {
|
|||
// OPCODES 0xc0-cf
|
||||
case 0xc0 => noDecoder(CaptureFlagUpdateMessage)
|
||||
case 0xc1 => noDecoder(VanuModuleUpdateMessage)
|
||||
case 0xc2 => noDecoder(FacilityBenefitShieldChargeRequestMessage)
|
||||
case 0xc2 => game.FacilityBenefitShieldChargeRequestMessage.decode
|
||||
case 0xc3 => game.ProximityTerminalUseMessage.decode
|
||||
case 0xc4 => game.QuantityDeltaUpdateMessage.decode
|
||||
case 0xc5 => noDecoder(ChainLashMessage)
|
||||
|
|
@ -608,7 +608,7 @@ object GamePacketOpcode extends Enumeration {
|
|||
case 0xf1 => game.MailMessage.decode
|
||||
case 0xf2 => noDecoder(GameVarUpdate)
|
||||
case 0xf3 => noDecoder(ClientCheatedMessage)
|
||||
case default => noDecoder(opcode)
|
||||
case _ => noDecoder(opcode)
|
||||
}
|
||||
|
||||
implicit val codec: Codec[this.Value] = PacketHelpers.createEnumerationCodec(this, uint8L)
|
||||
|
|
|
|||
|
|
@ -0,0 +1,24 @@
|
|||
// Copyright (c) 2017 PSForever
|
||||
package net.psforever.packet.game
|
||||
|
||||
import net.psforever.packet.{GamePacketOpcode, Marshallable, PlanetSideGamePacket}
|
||||
import scodec.Codec
|
||||
import scodec.codecs._
|
||||
|
||||
/**
|
||||
* Dispatched by the client when driving a vehicle in the sphere of influence of an allied base
|
||||
* that is a dropship center or that possesses the lattice-connected benefit of a dropship center.
|
||||
* The vehicle that is being driven will not have perfect fully-charged shields at the time.
|
||||
* @param vehicle_guid the vehicle whose shield is being charged
|
||||
*/
|
||||
final case class FacilityBenefitShieldChargeRequestMessage(vehicle_guid : PlanetSideGUID)
|
||||
extends PlanetSideGamePacket {
|
||||
type Packet = FacilityBenefitShieldChargeRequestMessage
|
||||
def opcode = GamePacketOpcode.FacilityBenefitShieldChargeRequestMessage
|
||||
def encode = FacilityBenefitShieldChargeRequestMessage.encode(this)
|
||||
}
|
||||
|
||||
object FacilityBenefitShieldChargeRequestMessage extends Marshallable[FacilityBenefitShieldChargeRequestMessage] {
|
||||
implicit val codec : Codec[FacilityBenefitShieldChargeRequestMessage] =
|
||||
("vehicle_guid" | PlanetSideGUID.codec).as[FacilityBenefitShieldChargeRequestMessage]
|
||||
}
|
||||
|
|
@ -51,11 +51,31 @@ final case class FavoritesMessage(list : LoadoutType.Value,
|
|||
}
|
||||
|
||||
object FavoritesMessage extends Marshallable[FavoritesMessage] {
|
||||
/**
|
||||
* Overloaded constructor, for infantry loadouts specifically.
|
||||
* @param list the destination list
|
||||
* @param player_guid the player
|
||||
* @param line the zero-indexed line number of this entry in its list
|
||||
* @param label the identifier for this entry
|
||||
* @param armor the type of exo-suit, if an Infantry loadout
|
||||
* @return a `FavoritesMessage` object
|
||||
*/
|
||||
def apply(list : LoadoutType.Value, player_guid : PlanetSideGUID, line : Int, label : String, armor : Int) : FavoritesMessage = {
|
||||
FavoritesMessage(list, player_guid, line, label, Some(armor))
|
||||
}
|
||||
|
||||
/**
|
||||
* Overloaded constructor, for vehicle loadouts specifically.
|
||||
* @param list the destination list
|
||||
* @param player_guid the player
|
||||
* @param line the zero-indexed line number of this entry in its list
|
||||
* @param label the identifier for this entry
|
||||
* @return a `FavoritesMessage` object
|
||||
*/
|
||||
def apply(list : LoadoutType.Value, player_guid : PlanetSideGUID, line : Int, label : String) : FavoritesMessage = {
|
||||
FavoritesMessage(list, player_guid, line, label, None)
|
||||
}
|
||||
|
||||
implicit val codec : Codec[FavoritesMessage] = (
|
||||
implicit val codec : Codec[FavoritesMessage] = (
|
||||
("list" | LoadoutType.codec) >>:~ { value =>
|
||||
("player_guid" | PlanetSideGUID.codec) ::
|
||||
("line" | uint4L) ::
|
||||
|
|
|
|||
|
|
@ -0,0 +1,28 @@
|
|||
// Copyright (c) 2017 PSForever
|
||||
package game
|
||||
|
||||
import org.specs2.mutable._
|
||||
import net.psforever.packet._
|
||||
import net.psforever.packet.game._
|
||||
import scodec.bits._
|
||||
|
||||
class FacilityBenefitShieldChargeRequestMessageTest extends Specification {
|
||||
val string = hex"C2 4C00"
|
||||
|
||||
"decode" in {
|
||||
PacketCoding.DecodePacket(string).require match {
|
||||
case FacilityBenefitShieldChargeRequestMessage(guid) =>
|
||||
guid mustEqual PlanetSideGUID(76)
|
||||
case _ =>
|
||||
ko
|
||||
}
|
||||
}
|
||||
|
||||
"encode" in {
|
||||
val msg = FacilityBenefitShieldChargeRequestMessage(PlanetSideGUID(76))
|
||||
val pkt = PacketCoding.EncodePacket(msg).require.toByteVector
|
||||
|
||||
pkt mustEqual string
|
||||
}
|
||||
}
|
||||
|
||||
|
|
@ -26,7 +26,7 @@ class FavoritesMessageTest extends Specification {
|
|||
}
|
||||
|
||||
"encode (for infantry)" in {
|
||||
val msg = FavoritesMessage(LoadoutType.Infantry, PlanetSideGUID(3760), 0, "Agile (basic)", Option(1))
|
||||
val msg = FavoritesMessage(LoadoutType.Infantry, PlanetSideGUID(3760), 0, "Agile (basic)", 1)
|
||||
val pkt = PacketCoding.EncodePacket(msg).require.toByteVector
|
||||
|
||||
pkt mustEqual stringInfantry
|
||||
|
|
|
|||
|
|
@ -110,6 +110,42 @@ class LoadoutTest extends Specification {
|
|||
ldout1.subtype mustEqual 0
|
||||
ldout2.subtype mustEqual 1
|
||||
ldout3.subtype mustEqual 2
|
||||
ldout4.subtype mustEqual 3
|
||||
ldout4.subtype mustEqual InfantryLoadout.DetermineSubtype(player) //example
|
||||
}
|
||||
|
||||
"players have additional uniform subtype" in {
|
||||
val player = CreatePlayer()
|
||||
val slot = player.Slot(0)
|
||||
slot.Equipment = None //only an unequipped slot can have its Equipment Size changed (Rifle -> Max)
|
||||
|
||||
player.ExoSuit = ExoSuitType.Standard
|
||||
val ldout0 = Loadout.Create(player, "standard").asInstanceOf[InfantryLoadout]
|
||||
player.ExoSuit = ExoSuitType.Agile
|
||||
val ldout1 = Loadout.Create(player, "agile").asInstanceOf[InfantryLoadout]
|
||||
player.ExoSuit = ExoSuitType.Reinforced
|
||||
val ldout2 = Loadout.Create(player, "rein").asInstanceOf[InfantryLoadout]
|
||||
player.ExoSuit = ExoSuitType.Infiltration
|
||||
val ldout7 = Loadout.Create(player, "inf").asInstanceOf[InfantryLoadout]
|
||||
|
||||
Player.SuitSetup(player, ExoSuitType.MAX)
|
||||
val ldout3 = Loadout.Create(player, "weaponless").asInstanceOf[InfantryLoadout]
|
||||
slot.Equipment = None
|
||||
slot.Equipment = Tool(trhev_dualcycler)
|
||||
val ldout4 = Loadout.Create(player, "cycler").asInstanceOf[InfantryLoadout]
|
||||
slot.Equipment = None
|
||||
slot.Equipment = Tool(trhev_pounder)
|
||||
val ldout5 = Loadout.Create(player, "pounder").asInstanceOf[InfantryLoadout]
|
||||
slot.Equipment = None
|
||||
slot.Equipment = Tool(trhev_burster)
|
||||
val ldout6 = Loadout.Create(player, "burster").asInstanceOf[InfantryLoadout]
|
||||
|
||||
InfantryLoadout.DetermineSubtypeB(ldout0.exosuit, ldout0.subtype) mustEqual 0
|
||||
InfantryLoadout.DetermineSubtypeB(ldout1.exosuit, ldout1.subtype) mustEqual 1
|
||||
InfantryLoadout.DetermineSubtypeB(ldout2.exosuit, ldout2.subtype) mustEqual 2
|
||||
InfantryLoadout.DetermineSubtypeB(ldout3.exosuit, ldout3.subtype) mustEqual 3
|
||||
InfantryLoadout.DetermineSubtypeB(ldout4.exosuit, ldout4.subtype) mustEqual 4
|
||||
InfantryLoadout.DetermineSubtypeB(ldout5.exosuit, ldout5.subtype) mustEqual 5
|
||||
InfantryLoadout.DetermineSubtypeB(ldout6.exosuit, ldout6.subtype) mustEqual 6
|
||||
InfantryLoadout.DetermineSubtypeB(ldout7.exosuit, ldout7.subtype) mustEqual 7
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -208,25 +208,6 @@ class SpawnTubeObjectBuilderTest extends ActorTest {
|
|||
}
|
||||
}
|
||||
|
||||
class RepairRearmSiloObjectBuilderTest extends ActorTest {
|
||||
import net.psforever.objects.GlobalDefinitions.repair_silo
|
||||
import net.psforever.objects.serverobject.terminals.RepairRearmSilo
|
||||
"LockerObjectBuilder" should {
|
||||
"build" in {
|
||||
val hub = ServerObjectBuilderTest.NumberPoolHub
|
||||
val actor = system.actorOf(Props(classOf[ServerObjectBuilderTest.BuilderTestActor], ServerObjectBuilder(1,
|
||||
RepairRearmSilo.Constructor(repair_silo)), hub), "silo")
|
||||
actor ! "!"
|
||||
|
||||
val reply = receiveOne(Duration.create(1000, "ms"))
|
||||
assert(reply.isInstanceOf[RepairRearmSilo])
|
||||
assert(reply.asInstanceOf[RepairRearmSilo].HasGUID)
|
||||
assert(reply.asInstanceOf[RepairRearmSilo].GUID == PlanetSideGUID(1))
|
||||
assert(reply == hub(1).get)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
object ServerObjectBuilderTest {
|
||||
import net.psforever.objects.guid.source.LimitedNumberSource
|
||||
def NumberPoolHub : NumberPoolHub = {
|
||||
|
|
|
|||
|
|
@ -4,7 +4,7 @@ package objects.terminal
|
|||
import akka.actor.ActorRef
|
||||
import net.psforever.objects.serverobject.structures.{Building, StructureType}
|
||||
import net.psforever.objects._
|
||||
import net.psforever.objects.serverobject.terminals.{RepairRearmSilo, Terminal}
|
||||
import net.psforever.objects.serverobject.terminals.Terminal
|
||||
import net.psforever.objects.zones.Zone
|
||||
import net.psforever.packet.game.{ItemTransactionMessage, PlanetSideGUID}
|
||||
import net.psforever.types.{CharacterGender, PlanetSideEmpire, TransactionType}
|
||||
|
|
@ -13,7 +13,7 @@ import org.specs2.mutable.Specification
|
|||
class RepairRearmSiloTest extends Specification {
|
||||
"RepairRearmSilo" should {
|
||||
val player = Player(Avatar("test", PlanetSideEmpire.TR, CharacterGender.Male, 0, 0))
|
||||
val silo = RepairRearmSilo(GlobalDefinitions.repair_silo)
|
||||
val silo = Terminal(GlobalDefinitions.repair_silo)
|
||||
silo.Owner = new Building(0, Zone.Nowhere, StructureType.Building)
|
||||
silo.Owner.Faction = PlanetSideEmpire.TR
|
||||
|
||||
|
|
@ -22,7 +22,7 @@ class RepairRearmSiloTest extends Specification {
|
|||
}
|
||||
|
||||
"construct" in {
|
||||
val obj = RepairRearmSilo(GlobalDefinitions.repair_silo)
|
||||
val obj = Terminal(GlobalDefinitions.repair_silo)
|
||||
obj.Actor mustEqual ActorRef.noSender
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -7,7 +7,7 @@ import net.psforever.objects.serverobject.locks.IFFLock
|
|||
import net.psforever.objects.serverobject.mblocker.Locker
|
||||
import net.psforever.objects.serverobject.pad.VehicleSpawnPad
|
||||
import net.psforever.objects.serverobject.structures.{Building, FoundationBuilder, StructureType, WarpGate}
|
||||
import net.psforever.objects.serverobject.terminals.{ProximityTerminal, RepairRearmSilo, Terminal}
|
||||
import net.psforever.objects.serverobject.terminals.{ProximityTerminal, Terminal}
|
||||
import net.psforever.objects.serverobject.tube.SpawnTube
|
||||
import net.psforever.types.Vector3
|
||||
|
||||
|
|
@ -113,8 +113,10 @@ object Maps {
|
|||
LocalObject(2145, SpawnTube.Constructor(Vector3(3980.4062f, 4252.7656f, 257.5625f), Vector3(0, 0, 90)))
|
||||
LocalObject(2146, SpawnTube.Constructor(Vector3(3980.4062f, 4259.992f, 257.5625f), Vector3(0, 0, 90)))
|
||||
LocalObject(2147, SpawnTube.Constructor(Vector3(3980.4062f, 4267.3047f, 257.5625f), Vector3(0, 0, 90)))
|
||||
LocalObject(2050, RepairRearmSilo.Constructor(repair_silo))
|
||||
LocalObject(2062, RepairRearmSilo.Constructor(repair_silo))
|
||||
LocalObject(2049, ProximityTerminal.Constructor(repair_silo)) //repair terminal A
|
||||
LocalObject(2050, Terminal.Constructor(repair_silo)) //rearm terminal A
|
||||
LocalObject(2061, ProximityTerminal.Constructor(repair_silo)) //repair terminal B
|
||||
LocalObject(2062, Terminal.Constructor(repair_silo)) //rearm terminal B
|
||||
LocalObject(2239, Terminal.Constructor(spawn_terminal))
|
||||
LocalObject(2244, Terminal.Constructor(spawn_terminal))
|
||||
LocalObject(2245, Terminal.Constructor(spawn_terminal))
|
||||
|
|
@ -216,7 +218,9 @@ object Maps {
|
|||
ObjectToBuilding(1576, 2)
|
||||
ObjectToBuilding(1577, 2)
|
||||
ObjectToBuilding(1578, 2)
|
||||
ObjectToBuilding(2049, 2)
|
||||
ObjectToBuilding(2050, 2)
|
||||
ObjectToBuilding(2061, 2)
|
||||
ObjectToBuilding(2062, 2)
|
||||
ObjectToBuilding(2145, 2)
|
||||
ObjectToBuilding(2146, 2)
|
||||
|
|
@ -432,6 +436,8 @@ object Maps {
|
|||
def Building2() : Unit = {
|
||||
//HART building C
|
||||
LocalBuilding(2, FoundationBuilder(Building.Structure(StructureType.Building)))
|
||||
LocalObject(12, ProximityTerminal.Constructor(repair_silo)) //repair terminal A
|
||||
LocalObject(13, Terminal.Constructor(repair_silo)) //rearm terminal A //ItemTransaction: ItemTransactionMessage(PlanetSideGUID(2050),Buy,3,25mmbullet,0,PlanetSideGUID(0))
|
||||
LocalObject(186, Terminal.Constructor(cert_terminal))
|
||||
LocalObject(187, Terminal.Constructor(cert_terminal))
|
||||
LocalObject(188, Terminal.Constructor(cert_terminal))
|
||||
|
|
@ -479,6 +485,8 @@ object Maps {
|
|||
LocalObject(1087, Terminal.Constructor(implant_terminal_interface)) //TODO guid not correct
|
||||
LocalObject(1088, Terminal.Constructor(implant_terminal_interface)) //TODO guid not correct
|
||||
LocalObject(1089, Terminal.Constructor(implant_terminal_interface)) //TODO guid not correct
|
||||
ObjectToBuilding(12, 2)
|
||||
ObjectToBuilding(13, 2)
|
||||
ObjectToBuilding(186, 2)
|
||||
ObjectToBuilding(187, 2)
|
||||
ObjectToBuilding(188, 2)
|
||||
|
|
|
|||
|
|
@ -1104,7 +1104,7 @@ class WorldSessionActor extends Actor with MDCContextAware {
|
|||
vehicleService ! VehicleServiceMessage.UnscheduleDeconstruction(vehicle_guid)
|
||||
}
|
||||
sendResponse(PlanetsideAttributeMessage(vehicle_guid, 22, 0L)) //mount points on?
|
||||
//sendResponse(PlanetsideAttributeMessage(vehicle_guid, 0, vehicle.Definition.MaxHealth)))
|
||||
sendResponse(PlanetsideAttributeMessage(vehicle_guid, 0, 10))//vehicle.Definition.MaxHealth))
|
||||
sendResponse(PlanetsideAttributeMessage(vehicle_guid, 68, 0L)) //???
|
||||
sendResponse(PlanetsideAttributeMessage(vehicle_guid, 113, 0L)) //???
|
||||
ReloadVehicleAccessPermissions(vehicle)
|
||||
|
|
@ -2327,21 +2327,20 @@ class WorldSessionActor extends Actor with MDCContextAware {
|
|||
}
|
||||
}
|
||||
|
||||
case Some(obj : RepairRearmSilo) =>
|
||||
player.VehicleSeated match {
|
||||
case Some(vehicle_guid) =>
|
||||
val vehicle = continent.GUID(vehicle_guid).get.asInstanceOf[Vehicle]
|
||||
sendResponse(UseItemMessage(avatar_guid, unk1, object_guid, unk2, unk3, unk4, unk5, unk6, unk7, unk8, itemType))
|
||||
sendResponse(UseItemMessage(avatar_guid, unk1, vehicle_guid, unk2, unk3, unk4, unk5, unk6, unk7, unk8, vehicle.Definition.ObjectId))
|
||||
case None =>
|
||||
log.error("UseItem: expected seated vehicle, but found none")
|
||||
}
|
||||
|
||||
case Some(obj : Terminal) =>
|
||||
if(obj.Definition.isInstanceOf[MatrixTerminalDefinition]) {
|
||||
//TODO matrix spawn point; for now, just blindly bind to show work (and hope nothing breaks)
|
||||
sendResponse(BindPlayerMessage(1, "@ams", true, true, 0, 0, 0, obj.Position))
|
||||
}
|
||||
else if(obj.Definition == GlobalDefinitions.repair_silo) {
|
||||
FindLocalVehicle match {
|
||||
case Some(vehicle) =>
|
||||
sendResponse(UseItemMessage(avatar_guid, unk1, object_guid, unk2, unk3, unk4, unk5, unk6, unk7, unk8, itemType))
|
||||
sendResponse(UseItemMessage(avatar_guid, unk1, vehicle.GUID, unk2, unk3, unk4, unk5, unk6, unk7, unk8, vehicle.Definition.ObjectId))
|
||||
case None =>
|
||||
log.error("UseItem: expected seated vehicle, but found none")
|
||||
}
|
||||
}
|
||||
else {
|
||||
sendResponse(UseItemMessage(avatar_guid, unk1, object_guid, unk2, unk3, unk4, unk5, unk6, unk7, unk8, itemType))
|
||||
}
|
||||
|
|
@ -2368,7 +2367,7 @@ class WorldSessionActor extends Actor with MDCContextAware {
|
|||
}
|
||||
|
||||
case msg @ ProximityTerminalUseMessage(player_guid, object_guid, _) =>
|
||||
log.info(s"ProximityTerminal: $msg")
|
||||
log.info(s"ProximityTerminalUse: $msg")
|
||||
continent.GUID(object_guid) match {
|
||||
case Some(obj : Terminal with ProximityUnit) =>
|
||||
if(usingProximityTerminal.contains(object_guid)) {
|
||||
|
|
@ -2378,7 +2377,7 @@ class WorldSessionActor extends Actor with MDCContextAware {
|
|||
StartUsingProximityUnit(obj)
|
||||
}
|
||||
case Some(obj) => ;
|
||||
log.warn(s"ProximityTerminalUse: object is not a proximity terminal - $obj")
|
||||
log.warn(s"ProximityTerminalUse: object does not have proximity effects - $obj")
|
||||
case None =>
|
||||
log.warn(s"ProximityTerminalUse: no object with guid $object_guid found")
|
||||
}
|
||||
|
|
@ -2438,14 +2437,16 @@ class WorldSessionActor extends Actor with MDCContextAware {
|
|||
else {
|
||||
None
|
||||
}) match {
|
||||
case Some(owner : Player) =>
|
||||
case Some(owner : Player) => //InfantryLoadout
|
||||
avatar.SaveLoadout(owner, name, lineno)
|
||||
case Some(owner : Vehicle) =>
|
||||
import InfantryLoadout._
|
||||
sendResponse(FavoritesMessage(list, player_guid, line, name, DetermineSubtypeB(player.ExoSuit, DetermineSubtype(player))))
|
||||
case Some(owner : Vehicle) => //VehicleLoadout
|
||||
avatar.SaveLoadout(owner, name, lineno)
|
||||
sendResponse(FavoritesMessage(list, player_guid, line, name))
|
||||
case Some(_) | None =>
|
||||
log.error("FavoritesRequest: unexpected owner for favorites")
|
||||
}
|
||||
sendResponse(FavoritesMessage(list, player_guid, line, name))
|
||||
|
||||
case FavoritesAction.Delete =>
|
||||
avatar.DeleteLoadout(lineno)
|
||||
|
|
@ -2637,6 +2638,9 @@ class WorldSessionActor extends Actor with MDCContextAware {
|
|||
sendResponse(PlanetsideAttributeMessage(object_guid, attribute_type, attribute_value))
|
||||
}
|
||||
|
||||
case msg @ FacilityBenefitShieldChargeRequestMessage(guid) =>
|
||||
//log.info(s"ShieldChargeRequest: $msg")
|
||||
|
||||
case msg @ BattleplanMessage(char_id, player_name, zonr_id, diagrams) =>
|
||||
log.info("Battleplan: "+msg)
|
||||
|
||||
|
|
@ -4193,6 +4197,10 @@ class WorldSessionActor extends Actor with MDCContextAware {
|
|||
SetDelayedProximityUnitReset(terminal)
|
||||
ProximityHealCrystal(terminal)
|
||||
|
||||
case GlobalDefinitions.repair_silo =>
|
||||
SetDelayedProximityUnitReset(terminal)
|
||||
//TODO insert vehicle repair here; see ProximityMedicalTerminal for example
|
||||
|
||||
case _ => ;
|
||||
}
|
||||
}
|
||||
|
|
|
|||
Loading…
Reference in a new issue