2017-03-07 00:30:45 +00:00
|
|
|
// Copyright (c) 2017 PSForever
|
2017-03-04 15:06:10 +00:00
|
|
|
package game
|
|
|
|
|
|
|
|
|
|
import net.psforever.packet._
|
2017-05-10 00:30:58 +00:00
|
|
|
import net.psforever.packet.game.{ObjectCreateMessage, _}
|
2017-03-04 15:06:10 +00:00
|
|
|
import net.psforever.packet.game.objectcreate._
|
2017-05-07 05:34:55 +00:00
|
|
|
import net.psforever.types._
|
2017-03-19 01:04:20 +00:00
|
|
|
import org.specs2.mutable._
|
2017-03-04 15:06:10 +00:00
|
|
|
import scodec.bits._
|
|
|
|
|
|
|
|
|
|
class ObjectCreateMessageTest extends Specification {
|
2017-03-19 01:04:20 +00:00
|
|
|
val string_striker_projectile = hex"17 C5000000 A4B 009D 4C129 0CB0A 9814 00 F5 E3 040000666686400"
|
|
|
|
|
val string_implant_interface = hex"17 6C000000 01014C93304818000000"
|
|
|
|
|
val string_order_terminala = hex"17 A5000000 B2AF30EACF1889F7A3D1200007D2000000"
|
|
|
|
|
val string_ace_held = hex"17 76000000 0406900650C80480000000"
|
|
|
|
|
val string_boomertrigger = hex"17 76000000 58084A8100E80C00000000" //reconstructed from an inventory entry
|
|
|
|
|
val string_detonater_held = hex"17 76000000 1A886A8421080400000000"
|
|
|
|
|
val string_lasher_held = hex"17 BB000000 1688569D90B83 880000008082077036032000000"
|
|
|
|
|
val string_punisher_held = hex"17 F6000000 0A06612331083 88000000810381383E03200003793287C0E400000"
|
|
|
|
|
val string_rek_held = hex"17 86000000 27086C2350F800800000000000"
|
|
|
|
|
val string_captureflag = hex"17 E5000000 CE8EA10 04A47 B818A FE0E 00 00 0F 24000015000400160B09000" //LLU for Qumu on Amerish
|
|
|
|
|
val string_ace_dropped = hex"17 AF000000 90024113B329C5D5A2D1200005B440000000"
|
|
|
|
|
val string_detonater_dropped = hex"17 AF000000 EA8620ED1549B4B6A741500001B000000000"
|
|
|
|
|
val string_shotgunshell_dropped = hex"17 A5000000 F9A7D0D 5E269 BED5A F114 0000596000000"
|
|
|
|
|
val string_lasher_dropped = hex"17 F4000000 D69020C 99299 85D0A 5F10 00 00 20 400000004041038819018000000"
|
|
|
|
|
val string_punisher_dropped = hex"17 2F010000 E12A20B 915A9 28C9A 1412 00 00 33 200000004081C1901B01800001BCB5C2E07000000"
|
|
|
|
|
val string_rek_dropped = hex"17 BF000000 EC20311 85219 7AC1A 2D12 00 00 4E 4000000001800"
|
|
|
|
|
val string_boomer = hex"17 A5000000 CA0000F1630938D5A8F1400003F0031100"
|
|
|
|
|
val string_spitfire_short = hex"17 BB000000 9D37010 E4F08 6AFCA 0312 00 7F 42 2C1F0F0000F00"
|
|
|
|
|
val string_spitfire = hex"17 4F010000 9D3A910 D1D78 AE3FC 9111 00 00 69 4488107F80F2021DBF80B80C80000008086EDB83A03200000"
|
|
|
|
|
val string_trap = hex"17 BB000000 A8B630A 39FA6 FD666 801C 00 00 00 44C6097F80F00"
|
|
|
|
|
val string_aegis = hex"17 10010000 F80FC09 9DF96 0C676 801C 00 00 00 443E09FF0000000000000000000000000"
|
|
|
|
|
val string_orion = hex"17 5E010000 D82640B 92F76 01D65 F611 00 00 5E 4400006304BFC1E4041826E1503900000010104CE704C06400000"
|
|
|
|
|
val string_locker_container = hex"17 AF010000 E414C0C00000000000000000000600000818829DC2E030000000202378620D80C00000378FA0FADC000006F1FC199D800000"
|
|
|
|
|
val string_character = hex"17 73070000 BC8 3E0F 6C2D7 65535 CA16 00 00 09 9741E4F804000000 234530063007200610077006E00790052006F006E006E0069006500 220B7 E67B540404001000000000022B50100 268042006C00610063006B002000420065007200650074002000410072006D006F007500720065006400200043006F00720070007300 1700E0030050040003BC00000234040001A004000 3FFF67A8F A0A5424E0E800000000080952A9C3A03000001081103E040000000A023782F1080C0000016244108200000000808382403A030000014284C3A0C0000000202512F00B80C00000578F80F840000000280838B3C320300000080"
|
|
|
|
|
val string_character_backpack = hex"17 9C030000 BC8 340D F20A9 3956C AF0D 00 00 73 480000 87041006E00670065006C006C006F00 4A148 0000000000000000000000005C54200 24404F0072006900670069006E0061006C00200044006900730074007200690063007400 1740180181E8000000C202000042000000D202000000010A3C00"
|
|
|
|
|
|
2017-05-10 00:30:58 +00:00
|
|
|
"decode (striker projectile)" in {
|
2017-03-19 01:04:20 +00:00
|
|
|
PacketCoding.DecodePacket(string_striker_projectile).require match {
|
2017-03-04 15:06:10 +00:00
|
|
|
case ObjectCreateMessage(len, cls, guid, parent, data) =>
|
2017-03-19 01:04:20 +00:00
|
|
|
len mustEqual 197
|
|
|
|
|
cls mustEqual ObjectClass.striker_missile_targeting_projectile
|
|
|
|
|
guid mustEqual PlanetSideGUID(40192)
|
|
|
|
|
parent.isDefined mustEqual false
|
|
|
|
|
data.isDefined mustEqual true
|
|
|
|
|
data.get.isInstanceOf[TrackedProjectileData] mustEqual true
|
|
|
|
|
val projectile = data.get.asInstanceOf[TrackedProjectileData]
|
|
|
|
|
projectile.pos.coord.x mustEqual 4644.5938f
|
|
|
|
|
projectile.pos.coord.y mustEqual 5472.0938f
|
|
|
|
|
projectile.pos.coord.z mustEqual 82.375f
|
2017-07-10 19:19:47 +00:00
|
|
|
projectile.pos.orient.x mustEqual 0f
|
|
|
|
|
projectile.pos.orient.y mustEqual 30.9375f
|
|
|
|
|
projectile.pos.orient.z mustEqual 171.5625f
|
2017-03-19 01:04:20 +00:00
|
|
|
projectile.unk1 mustEqual 0
|
|
|
|
|
projectile.unk2 mustEqual TrackedProjectileData.striker_missile_targetting_projectile_data
|
2017-03-04 15:06:10 +00:00
|
|
|
case _ =>
|
|
|
|
|
ko
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
2017-03-19 01:04:20 +00:00
|
|
|
"decode (implant interface)" in {
|
|
|
|
|
PacketCoding.DecodePacket(string_implant_interface).require match {
|
2017-03-04 15:06:10 +00:00
|
|
|
case ObjectCreateMessage(len, cls, guid, parent, data) =>
|
2017-03-19 01:04:20 +00:00
|
|
|
len mustEqual 108
|
|
|
|
|
cls mustEqual 0x199
|
|
|
|
|
guid mustEqual PlanetSideGUID(1075)
|
2017-03-04 15:06:10 +00:00
|
|
|
parent.isDefined mustEqual true
|
2017-03-19 01:04:20 +00:00
|
|
|
parent.get.guid mustEqual PlanetSideGUID(514)
|
|
|
|
|
parent.get.slot mustEqual 1
|
2017-03-04 15:06:10 +00:00
|
|
|
data.isDefined mustEqual true
|
2017-05-10 00:30:58 +00:00
|
|
|
data.get.isInstanceOf[CommonTerminalData] mustEqual true
|
|
|
|
|
data.get.asInstanceOf[CommonTerminalData].faction mustEqual PlanetSideEmpire.VS
|
2017-03-04 15:06:10 +00:00
|
|
|
case _ =>
|
|
|
|
|
ko
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
2017-03-19 01:04:20 +00:00
|
|
|
"decode (order terminal a)" in {
|
|
|
|
|
PacketCoding.DecodePacket(string_order_terminala).require match {
|
2017-03-04 15:06:10 +00:00
|
|
|
case ObjectCreateMessage(len, cls, guid, parent, data) =>
|
2017-03-19 01:04:20 +00:00
|
|
|
len mustEqual 165
|
|
|
|
|
cls mustEqual ObjectClass.order_terminala
|
|
|
|
|
guid mustEqual PlanetSideGUID(3827)
|
|
|
|
|
parent.isDefined mustEqual false
|
|
|
|
|
data.isDefined mustEqual true
|
2017-05-10 00:30:58 +00:00
|
|
|
data.get.isInstanceOf[DroppedItemData[_]] mustEqual true
|
|
|
|
|
val drop = data.get.asInstanceOf[DroppedItemData[_]]
|
|
|
|
|
drop.pos.coord.x mustEqual 4579.3438f
|
|
|
|
|
drop.pos.coord.y mustEqual 5615.0703f
|
|
|
|
|
drop.pos.coord.z mustEqual 72.953125f
|
2017-07-10 19:19:47 +00:00
|
|
|
drop.pos.orient.x mustEqual 0f
|
|
|
|
|
drop.pos.orient.y mustEqual 0f
|
|
|
|
|
drop.pos.orient.z mustEqual 98.4375f
|
2017-05-10 00:30:58 +00:00
|
|
|
drop.obj.isInstanceOf[CommonTerminalData] mustEqual true
|
|
|
|
|
val term = drop.obj.asInstanceOf[CommonTerminalData]
|
|
|
|
|
term.faction mustEqual PlanetSideEmpire.NC
|
|
|
|
|
term.unk mustEqual 0
|
2017-03-19 01:04:20 +00:00
|
|
|
case _ =>
|
|
|
|
|
ko
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
"decode (ace, held)" in {
|
|
|
|
|
PacketCoding.DecodePacket(string_ace_held).require match {
|
|
|
|
|
case ObjectCreateMessage(len, cls, guid, parent, data) =>
|
|
|
|
|
len mustEqual 118
|
|
|
|
|
cls mustEqual ObjectClass.ace
|
|
|
|
|
guid mustEqual PlanetSideGUID(3173)
|
2017-03-04 15:06:10 +00:00
|
|
|
parent.isDefined mustEqual true
|
2017-03-19 01:04:20 +00:00
|
|
|
parent.get.guid mustEqual PlanetSideGUID(3336)
|
|
|
|
|
parent.get.slot mustEqual 0
|
2017-03-04 15:06:10 +00:00
|
|
|
data.isDefined mustEqual true
|
2017-03-19 01:04:20 +00:00
|
|
|
data.get.isInstanceOf[ACEData] mustEqual true
|
|
|
|
|
val ace = data.get.asInstanceOf[ACEData]
|
|
|
|
|
ace.unk1 mustEqual 4
|
|
|
|
|
ace.unk2 mustEqual 8
|
|
|
|
|
ace.unk3 mustEqual 0
|
2017-03-04 15:06:10 +00:00
|
|
|
case _ =>
|
|
|
|
|
ko
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
2017-03-19 01:04:20 +00:00
|
|
|
"decode (boomer trigger, held)" in {
|
|
|
|
|
PacketCoding.DecodePacket(string_boomertrigger).require match {
|
2017-03-04 15:06:10 +00:00
|
|
|
case ObjectCreateMessage(len, cls, guid, parent, data) =>
|
2017-03-19 01:04:20 +00:00
|
|
|
len mustEqual 118
|
|
|
|
|
cls mustEqual ObjectClass.boomer_trigger
|
|
|
|
|
guid mustEqual PlanetSideGUID(3600)
|
2017-03-04 15:06:10 +00:00
|
|
|
parent.isDefined mustEqual true
|
2017-03-19 01:04:20 +00:00
|
|
|
parent.get.guid mustEqual PlanetSideGUID(4272)
|
|
|
|
|
parent.get.slot mustEqual 0
|
2017-03-04 15:06:10 +00:00
|
|
|
data.isDefined mustEqual true
|
2017-03-19 01:04:20 +00:00
|
|
|
data.get.isInstanceOf[BoomerTriggerData] mustEqual true
|
|
|
|
|
data.get.asInstanceOf[BoomerTriggerData].unk mustEqual 0
|
2017-03-04 15:06:10 +00:00
|
|
|
case _ =>
|
|
|
|
|
ko
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
2017-03-19 01:04:20 +00:00
|
|
|
"decode (detonator, held)" in {
|
|
|
|
|
PacketCoding.DecodePacket(string_detonater_held).require match {
|
2017-03-04 15:06:10 +00:00
|
|
|
case ObjectCreateMessage(len, cls, guid, parent, data) =>
|
2017-03-19 01:04:20 +00:00
|
|
|
len mustEqual 118
|
|
|
|
|
cls mustEqual ObjectClass.command_detonater
|
|
|
|
|
guid mustEqual PlanetSideGUID(4162)
|
2017-03-04 15:06:10 +00:00
|
|
|
parent.isDefined mustEqual true
|
2017-03-19 01:04:20 +00:00
|
|
|
parent.get.guid mustEqual PlanetSideGUID(4149)
|
|
|
|
|
parent.get.slot mustEqual 0
|
2017-03-04 15:06:10 +00:00
|
|
|
data.isDefined mustEqual true
|
2017-03-19 01:04:20 +00:00
|
|
|
data.get.isInstanceOf[CommandDetonaterData] mustEqual true
|
|
|
|
|
val cud = data.get.asInstanceOf[CommandDetonaterData]
|
|
|
|
|
cud.unk1 mustEqual 4
|
|
|
|
|
cud.unk2 mustEqual 0
|
2017-03-04 15:06:10 +00:00
|
|
|
case _ =>
|
|
|
|
|
ko
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
2017-03-19 01:04:20 +00:00
|
|
|
"decode (lasher, held)" in {
|
|
|
|
|
PacketCoding.DecodePacket(string_lasher_held).require match {
|
2017-03-04 15:06:10 +00:00
|
|
|
case ObjectCreateMessage(len, cls, guid, parent, data) =>
|
2017-03-19 01:04:20 +00:00
|
|
|
len mustEqual 187
|
|
|
|
|
cls mustEqual ObjectClass.lasher
|
|
|
|
|
guid mustEqual PlanetSideGUID(3033)
|
|
|
|
|
parent.isDefined mustEqual true
|
|
|
|
|
parent.get.guid mustEqual PlanetSideGUID(4141)
|
|
|
|
|
parent.get.slot mustEqual 3
|
2017-03-04 15:06:10 +00:00
|
|
|
data.isDefined mustEqual true
|
2017-03-19 01:04:20 +00:00
|
|
|
data.get.isInstanceOf[WeaponData] mustEqual true
|
|
|
|
|
val wep = data.get.asInstanceOf[WeaponData]
|
2017-05-10 00:30:58 +00:00
|
|
|
wep.unk1 mustEqual 4
|
2017-03-19 01:04:20 +00:00
|
|
|
wep.unk2 mustEqual 8
|
|
|
|
|
wep.fire_mode mustEqual 0
|
2017-05-10 00:30:58 +00:00
|
|
|
wep.ammo.head.objectClass mustEqual ObjectClass.energy_cell
|
|
|
|
|
wep.ammo.head.guid mustEqual PlanetSideGUID(3548)
|
|
|
|
|
wep.ammo.head.parentSlot mustEqual 0
|
|
|
|
|
wep.ammo.head.obj.isInstanceOf[AmmoBoxData] mustEqual true
|
|
|
|
|
val ammo = wep.ammo.head.obj.asInstanceOf[AmmoBoxData]
|
2017-03-19 01:04:20 +00:00
|
|
|
ammo.unk mustEqual 8
|
|
|
|
|
case _ =>
|
|
|
|
|
ko
|
|
|
|
|
}
|
|
|
|
|
}
|
2017-03-04 15:06:10 +00:00
|
|
|
|
2017-03-19 01:04:20 +00:00
|
|
|
"decode (punisher, held)" in {
|
|
|
|
|
PacketCoding.DecodePacket(string_punisher_held).require match {
|
|
|
|
|
case ObjectCreateMessage(len, cls, guid, parent, data) =>
|
|
|
|
|
len mustEqual 246
|
|
|
|
|
cls mustEqual ObjectClass.punisher
|
|
|
|
|
guid mustEqual PlanetSideGUID(4147)
|
|
|
|
|
parent.isDefined mustEqual true
|
|
|
|
|
parent.get.guid mustEqual PlanetSideGUID(3092)
|
|
|
|
|
parent.get.slot mustEqual 3
|
|
|
|
|
data.isDefined mustEqual true
|
2017-05-10 00:30:58 +00:00
|
|
|
data.get.isInstanceOf[WeaponData] mustEqual true
|
|
|
|
|
val wep = data.get.asInstanceOf[WeaponData]
|
|
|
|
|
wep.unk1 mustEqual 4
|
2017-03-19 01:04:20 +00:00
|
|
|
wep.unk2 mustEqual 8
|
|
|
|
|
wep.fire_mode mustEqual 0
|
|
|
|
|
val ammo = wep.ammo
|
|
|
|
|
ammo.size mustEqual 2
|
2017-03-04 15:06:10 +00:00
|
|
|
//0
|
2017-03-19 01:04:20 +00:00
|
|
|
ammo.head.objectClass mustEqual ObjectClass.bullet_9mm
|
|
|
|
|
ammo.head.guid mustEqual PlanetSideGUID(3918)
|
|
|
|
|
ammo.head.parentSlot mustEqual 0
|
|
|
|
|
ammo.head.obj.isInstanceOf[AmmoBoxData] mustEqual true
|
|
|
|
|
ammo.head.obj.asInstanceOf[AmmoBoxData].unk mustEqual 8
|
2017-03-04 15:06:10 +00:00
|
|
|
//1
|
2017-03-19 01:04:20 +00:00
|
|
|
ammo(1).objectClass mustEqual ObjectClass.rocket
|
|
|
|
|
ammo(1).guid mustEqual PlanetSideGUID(3941)
|
|
|
|
|
ammo(1).parentSlot mustEqual 1
|
|
|
|
|
ammo(1).obj.isInstanceOf[AmmoBoxData] mustEqual true
|
|
|
|
|
ammo(1).obj.asInstanceOf[AmmoBoxData].unk mustEqual 8
|
|
|
|
|
case _ =>
|
|
|
|
|
ko
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
"decode (REK, held)" in {
|
|
|
|
|
PacketCoding.DecodePacket(string_rek_held).require match {
|
|
|
|
|
case ObjectCreateMessage(len, cls, guid, parent, data) =>
|
|
|
|
|
len mustEqual 134
|
|
|
|
|
cls mustEqual ObjectClass.remote_electronics_kit
|
|
|
|
|
guid mustEqual PlanetSideGUID(3893)
|
|
|
|
|
parent.isDefined mustEqual true
|
|
|
|
|
parent.get.guid mustEqual PlanetSideGUID(4174)
|
|
|
|
|
parent.get.slot mustEqual 0
|
|
|
|
|
data.isDefined mustEqual true
|
|
|
|
|
data.get.isInstanceOf[REKData] mustEqual true
|
|
|
|
|
val rek = data.get.asInstanceOf[REKData]
|
|
|
|
|
rek.unk1 mustEqual 0
|
|
|
|
|
rek.unk2 mustEqual 8
|
|
|
|
|
rek.unk3 mustEqual 0
|
|
|
|
|
case _ =>
|
|
|
|
|
ko
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
"decode (capture flag)" in {
|
|
|
|
|
PacketCoding.DecodePacket(string_captureflag).require match {
|
|
|
|
|
case ObjectCreateMessage(len, cls, guid, parent, data) =>
|
|
|
|
|
len mustEqual 229
|
|
|
|
|
cls mustEqual ObjectClass.capture_flag
|
|
|
|
|
guid mustEqual PlanetSideGUID(4330)
|
|
|
|
|
parent.isDefined mustEqual false
|
|
|
|
|
data.isDefined mustEqual true
|
|
|
|
|
data.get.isInstanceOf[CaptureFlagData] mustEqual true
|
|
|
|
|
val flag = data.get.asInstanceOf[CaptureFlagData]
|
|
|
|
|
flag.pos.coord.x mustEqual 3912.0312f
|
|
|
|
|
flag.pos.coord.y mustEqual 5169.4375f
|
|
|
|
|
flag.pos.coord.z mustEqual 59.96875f
|
2017-07-10 19:19:47 +00:00
|
|
|
flag.pos.orient.x mustEqual 0f
|
|
|
|
|
flag.pos.orient.y mustEqual 0f
|
|
|
|
|
flag.pos.orient.z mustEqual 47.8125f
|
2017-03-19 01:04:20 +00:00
|
|
|
flag.faction mustEqual PlanetSideEmpire.NC
|
|
|
|
|
flag.unk1 mustEqual 21
|
|
|
|
|
flag.unk2 mustEqual 4
|
|
|
|
|
flag.unk3 mustEqual 2838
|
|
|
|
|
flag.unk4 mustEqual 9
|
|
|
|
|
case _ =>
|
|
|
|
|
ko
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
"decode (ace, dropped)" in {
|
|
|
|
|
PacketCoding.DecodePacket(string_ace_dropped).require match {
|
|
|
|
|
case ObjectCreateMessage(len, cls, guid, parent, data) =>
|
|
|
|
|
len mustEqual 175
|
|
|
|
|
cls mustEqual ObjectClass.ace
|
|
|
|
|
guid mustEqual PlanetSideGUID(4388)
|
|
|
|
|
parent.isDefined mustEqual false
|
|
|
|
|
data.isDefined mustEqual true
|
|
|
|
|
data.get.isInstanceOf[DroppedItemData[_]] mustEqual true
|
|
|
|
|
val drop = data.get.asInstanceOf[DroppedItemData[_]]
|
|
|
|
|
drop.pos.coord.x mustEqual 4708.461f
|
|
|
|
|
drop.pos.coord.y mustEqual 5547.539f
|
|
|
|
|
drop.pos.coord.z mustEqual 72.703125f
|
2017-07-10 19:19:47 +00:00
|
|
|
drop.pos.orient.x mustEqual 0f
|
|
|
|
|
drop.pos.orient.y mustEqual 0f
|
|
|
|
|
drop.pos.orient.z mustEqual 194.0625f
|
2017-03-19 01:04:20 +00:00
|
|
|
drop.obj.isInstanceOf[ACEData] mustEqual true
|
|
|
|
|
val ace = drop.obj.asInstanceOf[ACEData]
|
|
|
|
|
ace.unk1 mustEqual 8
|
|
|
|
|
ace.unk2 mustEqual 8
|
|
|
|
|
case _ =>
|
|
|
|
|
ko
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
"decode (detonator, dropped)" in {
|
|
|
|
|
PacketCoding.DecodePacket(string_detonater_dropped).require match {
|
|
|
|
|
case ObjectCreateMessage(len, cls, guid, parent, data) =>
|
|
|
|
|
len mustEqual 175
|
|
|
|
|
cls mustEqual ObjectClass.command_detonater
|
|
|
|
|
guid mustEqual PlanetSideGUID(3682)
|
|
|
|
|
parent.isDefined mustEqual false
|
|
|
|
|
data.isDefined mustEqual true
|
|
|
|
|
data.get.isInstanceOf[DroppedItemData[_]] mustEqual true
|
|
|
|
|
val drop = data.get.asInstanceOf[DroppedItemData[_]]
|
|
|
|
|
drop.pos.coord.x mustEqual 4777.633f
|
|
|
|
|
drop.pos.coord.y mustEqual 5485.4062f
|
|
|
|
|
drop.pos.coord.z mustEqual 85.8125f
|
2017-07-10 19:19:47 +00:00
|
|
|
drop.pos.orient.x mustEqual 0f
|
|
|
|
|
drop.pos.orient.y mustEqual 0f
|
|
|
|
|
drop.pos.orient.z mustEqual 14.0625f
|
2017-03-19 01:04:20 +00:00
|
|
|
drop.obj.isInstanceOf[CommandDetonaterData] mustEqual true
|
|
|
|
|
case _ =>
|
|
|
|
|
ko
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
"decode (shotgun shells, dropped)" in {
|
|
|
|
|
PacketCoding.DecodePacket(string_shotgunshell_dropped).require match {
|
|
|
|
|
case ObjectCreateMessage(len, cls, guid, parent, data) =>
|
|
|
|
|
len mustEqual 165
|
|
|
|
|
cls mustEqual ObjectClass.shotgun_shell
|
|
|
|
|
guid mustEqual PlanetSideGUID(3453)
|
|
|
|
|
parent.isDefined mustEqual false
|
|
|
|
|
data.isDefined mustEqual true
|
|
|
|
|
data.get.isInstanceOf[DroppedItemData[_]] mustEqual true
|
|
|
|
|
val drop = data.get.asInstanceOf[DroppedItemData[_]]
|
|
|
|
|
drop.pos.coord.x mustEqual 4684.7344f
|
|
|
|
|
drop.pos.coord.y mustEqual 5547.4844f
|
|
|
|
|
drop.pos.coord.z mustEqual 83.765625f
|
2017-07-10 19:19:47 +00:00
|
|
|
drop.pos.orient.x mustEqual 0f
|
|
|
|
|
drop.pos.orient.y mustEqual 0f
|
|
|
|
|
drop.pos.orient.z mustEqual 199.6875f
|
2017-03-19 01:04:20 +00:00
|
|
|
drop.obj.isInstanceOf[AmmoBoxData] mustEqual true
|
|
|
|
|
val box = drop.obj.asInstanceOf[AmmoBoxData]
|
|
|
|
|
box.unk mustEqual 0
|
|
|
|
|
case _ =>
|
|
|
|
|
ko
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
"decode (lasher, dropped)" in {
|
|
|
|
|
PacketCoding.DecodePacket(string_lasher_dropped).require match {
|
|
|
|
|
case ObjectCreateMessage(len, cls, guid, parent, data) =>
|
|
|
|
|
len mustEqual 244
|
|
|
|
|
cls mustEqual ObjectClass.lasher
|
|
|
|
|
guid mustEqual PlanetSideGUID(3074)
|
|
|
|
|
parent.isDefined mustEqual false
|
|
|
|
|
data.isDefined mustEqual true
|
|
|
|
|
data.get.isInstanceOf[DroppedItemData[_]] mustEqual true
|
|
|
|
|
val drop = data.get.asInstanceOf[DroppedItemData[_]]
|
|
|
|
|
drop.pos.coord.x mustEqual 4691.1953f
|
|
|
|
|
drop.pos.coord.y mustEqual 5537.039f
|
|
|
|
|
drop.pos.coord.z mustEqual 65.484375f
|
2017-07-10 19:19:47 +00:00
|
|
|
drop.pos.orient.x mustEqual 0f
|
|
|
|
|
drop.pos.orient.y mustEqual 0f
|
|
|
|
|
drop.pos.orient.z mustEqual 0f
|
2017-03-19 01:04:20 +00:00
|
|
|
drop.obj.isInstanceOf[WeaponData] mustEqual true
|
|
|
|
|
val wep = drop.obj.asInstanceOf[WeaponData]
|
2017-05-10 00:30:58 +00:00
|
|
|
wep.unk1 mustEqual 4
|
2017-03-19 01:04:20 +00:00
|
|
|
wep.unk2 mustEqual 0
|
|
|
|
|
wep.fire_mode mustEqual 0
|
2017-05-10 00:30:58 +00:00
|
|
|
wep.ammo.head.objectClass mustEqual ObjectClass.energy_cell
|
|
|
|
|
wep.ammo.head.guid mustEqual PlanetSideGUID(3268)
|
|
|
|
|
wep.ammo.head.parentSlot mustEqual 0
|
|
|
|
|
wep.ammo.head.obj.isInstanceOf[AmmoBoxData] mustEqual true
|
|
|
|
|
val ammo = wep.ammo.head.obj.asInstanceOf[AmmoBoxData]
|
2017-03-19 01:04:20 +00:00
|
|
|
ammo.unk mustEqual 0
|
|
|
|
|
case _ =>
|
|
|
|
|
ko
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
"decode (punisher, dropped)" in {
|
|
|
|
|
PacketCoding.DecodePacket(string_punisher_dropped).require match {
|
|
|
|
|
case ObjectCreateMessage(len, cls, guid, parent, data) =>
|
|
|
|
|
len mustEqual 303
|
|
|
|
|
cls mustEqual ObjectClass.punisher
|
|
|
|
|
guid mustEqual PlanetSideGUID(2978)
|
|
|
|
|
parent.isDefined mustEqual false
|
|
|
|
|
data.isDefined mustEqual true
|
|
|
|
|
data.get.isInstanceOf[DroppedItemData[_]] mustEqual true
|
|
|
|
|
val drop = data.get.asInstanceOf[DroppedItemData[_]]
|
|
|
|
|
drop.pos.coord.x mustEqual 4789.133f
|
|
|
|
|
drop.pos.coord.y mustEqual 5522.3125f
|
|
|
|
|
drop.pos.coord.z mustEqual 72.3125f
|
2017-07-10 19:19:47 +00:00
|
|
|
drop.pos.orient.x mustEqual 0f
|
|
|
|
|
drop.pos.orient.y mustEqual 0f
|
|
|
|
|
drop.pos.orient.z mustEqual 306.5625f
|
2017-05-10 00:30:58 +00:00
|
|
|
drop.obj.isInstanceOf[WeaponData] mustEqual true
|
|
|
|
|
val wep = drop.obj.asInstanceOf[WeaponData]
|
|
|
|
|
wep.unk1 mustEqual 2
|
2017-03-19 01:04:20 +00:00
|
|
|
wep.unk2 mustEqual 0
|
|
|
|
|
wep.fire_mode mustEqual 0
|
|
|
|
|
val ammo = wep.ammo
|
|
|
|
|
ammo.size mustEqual 2
|
|
|
|
|
//0
|
|
|
|
|
ammo.head.objectClass mustEqual ObjectClass.bullet_9mm
|
|
|
|
|
ammo.head.guid mustEqual PlanetSideGUID(3528)
|
|
|
|
|
ammo.head.parentSlot mustEqual 0
|
|
|
|
|
ammo.head.obj.isInstanceOf[AmmoBoxData] mustEqual true
|
|
|
|
|
ammo.head.obj.asInstanceOf[AmmoBoxData].unk mustEqual 0
|
|
|
|
|
//1
|
|
|
|
|
ammo(1).objectClass mustEqual ObjectClass.rocket
|
|
|
|
|
ammo(1).guid mustEqual PlanetSideGUID(3031)
|
|
|
|
|
ammo(1).parentSlot mustEqual 1
|
|
|
|
|
ammo(1).obj.isInstanceOf[AmmoBoxData] mustEqual true
|
|
|
|
|
ammo(1).obj.asInstanceOf[AmmoBoxData].unk mustEqual 0
|
|
|
|
|
case _ =>
|
|
|
|
|
ko
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
"decode (REK, dropped)" in {
|
|
|
|
|
PacketCoding.DecodePacket(string_rek_dropped).require match {
|
|
|
|
|
case ObjectCreateMessage(len, cls, guid, parent, data) =>
|
|
|
|
|
len mustEqual 191
|
|
|
|
|
cls mustEqual ObjectClass.remote_electronics_kit
|
|
|
|
|
guid mustEqual PlanetSideGUID(4355)
|
|
|
|
|
parent.isDefined mustEqual false
|
|
|
|
|
data.isDefined mustEqual true
|
|
|
|
|
data.get.isInstanceOf[DroppedItemData[_]] mustEqual true
|
|
|
|
|
val dropped = data.get.asInstanceOf[DroppedItemData[_]]
|
|
|
|
|
dropped.pos.coord.x mustEqual 4675.039f
|
|
|
|
|
dropped.pos.coord.y mustEqual 5506.953f
|
|
|
|
|
dropped.pos.coord.z mustEqual 72.703125f
|
2017-07-10 19:19:47 +00:00
|
|
|
dropped.pos.orient.x mustEqual 0f
|
|
|
|
|
dropped.pos.orient.y mustEqual 0f
|
|
|
|
|
dropped.pos.orient.z mustEqual 230.625f
|
2017-03-19 01:04:20 +00:00
|
|
|
dropped.obj.isInstanceOf[REKData] mustEqual true
|
|
|
|
|
val rek = dropped.obj.asInstanceOf[REKData]
|
|
|
|
|
rek.unk1 mustEqual 8
|
|
|
|
|
rek.unk2 mustEqual 0
|
|
|
|
|
rek.unk3 mustEqual 3
|
|
|
|
|
case _ =>
|
|
|
|
|
ko
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
"decode (boomer)" in {
|
|
|
|
|
PacketCoding.DecodePacket(string_boomer).require match {
|
|
|
|
|
case ObjectCreateMessage(len, cls, guid, parent, data) =>
|
|
|
|
|
len mustEqual 165
|
|
|
|
|
cls mustEqual ObjectClass.boomer
|
|
|
|
|
guid mustEqual PlanetSideGUID(3840)
|
|
|
|
|
parent.isDefined mustEqual false
|
|
|
|
|
data.isDefined mustEqual true
|
|
|
|
|
data.get.isInstanceOf[SmallDeployableData] mustEqual true
|
|
|
|
|
val boomer = data.get.asInstanceOf[SmallDeployableData]
|
|
|
|
|
boomer.deploy.pos.coord.x mustEqual 4704.172f
|
|
|
|
|
boomer.deploy.pos.coord.y mustEqual 5546.4375f
|
|
|
|
|
boomer.deploy.pos.coord.z mustEqual 82.234375f
|
2017-07-10 19:19:47 +00:00
|
|
|
boomer.deploy.pos.orient.x mustEqual 0f
|
|
|
|
|
boomer.deploy.pos.orient.y mustEqual 0f
|
|
|
|
|
boomer.deploy.pos.orient.z mustEqual 272.8125f
|
2017-03-19 01:04:20 +00:00
|
|
|
boomer.deploy.unk mustEqual 0
|
|
|
|
|
boomer.deploy.player_guid mustEqual PlanetSideGUID(4145)
|
|
|
|
|
case _ =>
|
|
|
|
|
ko
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
"decode (spitfire, short)" in {
|
|
|
|
|
PacketCoding.DecodePacket(string_spitfire_short).require match {
|
|
|
|
|
case ObjectCreateMessage(len, cls, guid, parent, data) =>
|
|
|
|
|
len mustEqual 187
|
|
|
|
|
cls mustEqual ObjectClass.spitfire_turret
|
|
|
|
|
guid mustEqual PlanetSideGUID(4208)
|
|
|
|
|
parent.isDefined mustEqual false
|
|
|
|
|
data.isDefined mustEqual true
|
|
|
|
|
data.get.isInstanceOf[SmallTurretData] mustEqual true
|
|
|
|
|
val turret = data.get.asInstanceOf[SmallTurretData]
|
|
|
|
|
turret.deploy.pos.coord.x mustEqual 4577.7812f
|
|
|
|
|
turret.deploy.pos.coord.y mustEqual 5624.828f
|
|
|
|
|
turret.deploy.pos.coord.z mustEqual 72.046875f
|
2017-07-10 19:19:47 +00:00
|
|
|
turret.deploy.pos.orient.x mustEqual 0f
|
|
|
|
|
turret.deploy.pos.orient.y mustEqual 2.8125f
|
|
|
|
|
turret.deploy.pos.orient.z mustEqual 264.375f
|
2017-05-10 00:30:58 +00:00
|
|
|
turret.deploy.faction mustEqual PlanetSideEmpire.NC
|
2017-10-19 00:26:41 +00:00
|
|
|
turret.deploy.destroyed mustEqual true
|
|
|
|
|
turret.deploy.unk mustEqual 2
|
2017-03-19 01:04:20 +00:00
|
|
|
turret.deploy.player_guid mustEqual PlanetSideGUID(3871)
|
|
|
|
|
turret.health mustEqual 0
|
|
|
|
|
turret.internals.isDefined mustEqual false
|
|
|
|
|
case _ =>
|
|
|
|
|
ko
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
"decode (spitfire)" in {
|
|
|
|
|
PacketCoding.DecodePacket(string_spitfire).require match {
|
|
|
|
|
case ObjectCreateMessage(len, cls, guid, parent, data) =>
|
|
|
|
|
len mustEqual 335
|
|
|
|
|
cls mustEqual ObjectClass.spitfire_turret
|
|
|
|
|
guid mustEqual PlanetSideGUID(4265)
|
|
|
|
|
parent.isDefined mustEqual false
|
|
|
|
|
data.isDefined mustEqual true
|
|
|
|
|
data.get.isInstanceOf[SmallTurretData] mustEqual true
|
|
|
|
|
val turret = data.get.asInstanceOf[SmallTurretData]
|
|
|
|
|
turret.deploy.pos.coord.x mustEqual 4527.633f
|
|
|
|
|
turret.deploy.pos.coord.y mustEqual 6271.3594f
|
|
|
|
|
turret.deploy.pos.coord.z mustEqual 70.265625f
|
2017-07-10 19:19:47 +00:00
|
|
|
turret.deploy.pos.orient.x mustEqual 0f
|
|
|
|
|
turret.deploy.pos.orient.y mustEqual 0f
|
|
|
|
|
turret.deploy.pos.orient.z mustEqual 154.6875f
|
2017-05-10 00:30:58 +00:00
|
|
|
turret.deploy.faction mustEqual PlanetSideEmpire.VS
|
2017-10-19 00:26:41 +00:00
|
|
|
turret.deploy.unk mustEqual 2
|
2017-03-19 01:04:20 +00:00
|
|
|
turret.deploy.player_guid mustEqual PlanetSideGUID(4232)
|
|
|
|
|
turret.health mustEqual 255
|
|
|
|
|
turret.internals.isDefined mustEqual true
|
|
|
|
|
val internals = turret.internals.get
|
|
|
|
|
internals.objectClass mustEqual ObjectClass.spitfire_weapon
|
|
|
|
|
internals.guid mustEqual PlanetSideGUID(3064)
|
|
|
|
|
internals.parentSlot mustEqual 0
|
|
|
|
|
internals.obj.isInstanceOf[WeaponData] mustEqual true
|
|
|
|
|
val wep = internals.obj.asInstanceOf[WeaponData]
|
2017-05-10 00:30:58 +00:00
|
|
|
wep.unk1 mustEqual 0x6
|
2017-03-19 01:04:20 +00:00
|
|
|
wep.unk2 mustEqual 0x8
|
|
|
|
|
wep.fire_mode mustEqual 0
|
2017-05-10 00:30:58 +00:00
|
|
|
val ammo = wep.ammo.head
|
2017-03-19 01:04:20 +00:00
|
|
|
ammo.objectClass mustEqual ObjectClass.spitfire_ammo
|
|
|
|
|
ammo.guid mustEqual PlanetSideGUID(3694)
|
|
|
|
|
ammo.parentSlot mustEqual 0
|
|
|
|
|
ammo.obj.isInstanceOf[AmmoBoxData] mustEqual true
|
|
|
|
|
ammo.obj.asInstanceOf[AmmoBoxData].unk mustEqual 8
|
|
|
|
|
case _ =>
|
|
|
|
|
ko
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
"decode (trap)" in {
|
|
|
|
|
PacketCoding.DecodePacket(string_trap).require match {
|
|
|
|
|
case ObjectCreateMessage(len, cls, guid, parent, data) =>
|
|
|
|
|
len mustEqual 187
|
|
|
|
|
cls mustEqual ObjectClass.tank_traps
|
|
|
|
|
guid mustEqual PlanetSideGUID(2659)
|
|
|
|
|
parent.isDefined mustEqual false
|
|
|
|
|
data.isDefined mustEqual true
|
|
|
|
|
data.get.isInstanceOf[TRAPData] mustEqual true
|
|
|
|
|
val trap = data.get.asInstanceOf[TRAPData]
|
|
|
|
|
trap.deploy.pos.coord.x mustEqual 3572.4453f
|
|
|
|
|
trap.deploy.pos.coord.y mustEqual 3277.9766f
|
|
|
|
|
trap.deploy.pos.coord.z mustEqual 114.0f
|
2017-07-10 19:19:47 +00:00
|
|
|
trap.deploy.pos.orient.x mustEqual 0f
|
|
|
|
|
trap.deploy.pos.orient.y mustEqual 0f
|
|
|
|
|
trap.deploy.pos.orient.z mustEqual 90.0f
|
2017-05-10 00:30:58 +00:00
|
|
|
trap.deploy.faction mustEqual PlanetSideEmpire.VS
|
2017-10-19 00:26:41 +00:00
|
|
|
trap.deploy.unk mustEqual 2
|
2017-03-19 01:04:20 +00:00
|
|
|
trap.health mustEqual 255
|
|
|
|
|
trap.deploy.player_guid mustEqual PlanetSideGUID(2502)
|
|
|
|
|
case _ =>
|
|
|
|
|
ko
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
"decode (aegis)" in {
|
|
|
|
|
PacketCoding.DecodePacket(string_aegis).require match {
|
|
|
|
|
case ObjectCreateMessage(len, cls, guid, parent, data) =>
|
|
|
|
|
len mustEqual 272
|
|
|
|
|
cls mustEqual ObjectClass.deployable_shield_generator
|
|
|
|
|
guid mustEqual PlanetSideGUID(2556)
|
|
|
|
|
parent.isDefined mustEqual false
|
|
|
|
|
data.isDefined mustEqual true
|
|
|
|
|
data.get.isInstanceOf[AegisShieldGeneratorData] mustEqual true
|
|
|
|
|
val aegis = data.get.asInstanceOf[AegisShieldGeneratorData]
|
|
|
|
|
aegis.deploy.pos.coord.x mustEqual 3571.2266f
|
|
|
|
|
aegis.deploy.pos.coord.y mustEqual 3278.0938f
|
|
|
|
|
aegis.deploy.pos.coord.z mustEqual 114.0f
|
2017-07-10 19:19:47 +00:00
|
|
|
aegis.deploy.pos.orient.x mustEqual 0f
|
|
|
|
|
aegis.deploy.pos.orient.y mustEqual 0f
|
|
|
|
|
aegis.deploy.pos.orient.z mustEqual 90.0f
|
2017-05-10 00:30:58 +00:00
|
|
|
aegis.deploy.faction mustEqual PlanetSideEmpire.VS
|
2017-10-19 00:26:41 +00:00
|
|
|
aegis.deploy.unk mustEqual 2
|
2017-03-19 01:04:20 +00:00
|
|
|
aegis.health mustEqual 255
|
|
|
|
|
aegis.deploy.player_guid mustEqual PlanetSideGUID(2366)
|
|
|
|
|
case _ =>
|
|
|
|
|
ko
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
"decode (orion)" in {
|
|
|
|
|
PacketCoding.DecodePacket(string_orion).require match {
|
|
|
|
|
case ObjectCreateMessage(len, cls, guid, parent, data) =>
|
|
|
|
|
len mustEqual 350
|
|
|
|
|
cls mustEqual ObjectClass.portable_manned_turret_vs
|
|
|
|
|
guid mustEqual PlanetSideGUID(2916)
|
|
|
|
|
parent.isDefined mustEqual false
|
|
|
|
|
data.isDefined mustEqual true
|
|
|
|
|
data.get.isInstanceOf[OneMannedFieldTurretData] mustEqual true
|
|
|
|
|
val omft = data.get.asInstanceOf[OneMannedFieldTurretData]
|
|
|
|
|
omft.deploy.pos.coord.x mustEqual 3567.1406f
|
|
|
|
|
omft.deploy.pos.coord.y mustEqual 2988.0078f
|
|
|
|
|
omft.deploy.pos.coord.z mustEqual 71.84375f
|
2017-07-10 19:19:47 +00:00
|
|
|
omft.deploy.pos.orient.x mustEqual 0f
|
|
|
|
|
omft.deploy.pos.orient.y mustEqual 0f
|
|
|
|
|
omft.deploy.pos.orient.z mustEqual 185.625f
|
2017-05-10 00:30:58 +00:00
|
|
|
omft.deploy.faction mustEqual PlanetSideEmpire.VS
|
2017-10-19 00:26:41 +00:00
|
|
|
omft.deploy.unk mustEqual 2
|
2017-05-10 00:30:58 +00:00
|
|
|
omft.deploy.player_guid mustEqual PlanetSideGUID(2502)
|
2017-03-19 01:04:20 +00:00
|
|
|
omft.health mustEqual 255
|
|
|
|
|
omft.internals.isDefined mustEqual true
|
|
|
|
|
val internals = omft.internals.get
|
|
|
|
|
internals.objectClass mustEqual ObjectClass.energy_gun_vs
|
|
|
|
|
internals.guid mustEqual PlanetSideGUID(2615)
|
|
|
|
|
internals.parentSlot mustEqual 1
|
|
|
|
|
internals.obj.isInstanceOf[WeaponData] mustEqual true
|
|
|
|
|
val wep = internals.obj.asInstanceOf[WeaponData]
|
2017-05-10 00:30:58 +00:00
|
|
|
wep.unk1 mustEqual 0x6
|
2017-03-19 01:04:20 +00:00
|
|
|
wep.unk2 mustEqual 0x8
|
|
|
|
|
wep.fire_mode mustEqual 0
|
2017-05-10 00:30:58 +00:00
|
|
|
val ammo = wep.ammo.head
|
2017-03-19 01:04:20 +00:00
|
|
|
ammo.objectClass mustEqual ObjectClass.energy_gun_ammo
|
|
|
|
|
ammo.guid mustEqual PlanetSideGUID(2510)
|
|
|
|
|
ammo.parentSlot mustEqual 0
|
|
|
|
|
ammo.obj.isInstanceOf[AmmoBoxData] mustEqual true
|
|
|
|
|
ammo.obj.asInstanceOf[AmmoBoxData].unk mustEqual 8
|
|
|
|
|
case _ =>
|
|
|
|
|
ko
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
"decode (locker container)" in {
|
|
|
|
|
PacketCoding.DecodePacket(string_locker_container).require match {
|
|
|
|
|
case ObjectCreateMessage(len, cls, guid, parent, data) =>
|
|
|
|
|
len mustEqual 431
|
|
|
|
|
cls mustEqual ObjectClass.locker_container
|
|
|
|
|
guid mustEqual PlanetSideGUID(3148)
|
|
|
|
|
parent.isDefined mustEqual false
|
|
|
|
|
data.isDefined mustEqual true
|
|
|
|
|
data.get.isInstanceOf[LockerContainerData] mustEqual true
|
|
|
|
|
val locker = data.get.asInstanceOf[LockerContainerData]
|
|
|
|
|
val contents = locker.inventory.contents
|
|
|
|
|
contents.size mustEqual 3
|
|
|
|
|
//0
|
2017-05-10 00:30:58 +00:00
|
|
|
contents.head.objectClass mustEqual ObjectClass.nano_dispenser
|
|
|
|
|
contents.head.guid mustEqual PlanetSideGUID(2935)
|
|
|
|
|
contents.head.parentSlot mustEqual 0
|
|
|
|
|
contents.head.obj.isInstanceOf[WeaponData] mustEqual true
|
|
|
|
|
val dispenser = contents.head.obj.asInstanceOf[WeaponData]
|
|
|
|
|
dispenser.unk1 mustEqual 0x6
|
2017-03-19 01:04:20 +00:00
|
|
|
dispenser.unk2 mustEqual 0x0
|
2017-05-10 00:30:58 +00:00
|
|
|
dispenser.ammo.head.objectClass mustEqual ObjectClass.armor_canister
|
|
|
|
|
dispenser.ammo.head.guid mustEqual PlanetSideGUID(3426)
|
|
|
|
|
dispenser.ammo.head.parentSlot mustEqual 0
|
|
|
|
|
dispenser.ammo.head.obj.isInstanceOf[AmmoBoxData] mustEqual true
|
|
|
|
|
dispenser.ammo.head.obj.asInstanceOf[AmmoBoxData].unk mustEqual 0
|
2017-03-19 01:04:20 +00:00
|
|
|
//1
|
2017-05-10 00:30:58 +00:00
|
|
|
contents(1).objectClass mustEqual ObjectClass.armor_canister
|
|
|
|
|
contents(1).guid mustEqual PlanetSideGUID(4090)
|
|
|
|
|
contents(1).parentSlot mustEqual 45
|
|
|
|
|
contents(1).obj.isInstanceOf[AmmoBoxData] mustEqual true
|
|
|
|
|
contents(1).obj.asInstanceOf[AmmoBoxData].unk mustEqual 0
|
2017-03-04 15:06:10 +00:00
|
|
|
//2
|
2017-05-10 00:30:58 +00:00
|
|
|
contents(2).objectClass mustEqual ObjectClass.armor_canister
|
|
|
|
|
contents(2).guid mustEqual PlanetSideGUID(3326)
|
|
|
|
|
contents(2).parentSlot mustEqual 78
|
|
|
|
|
contents(2).obj.isInstanceOf[AmmoBoxData] mustEqual true
|
|
|
|
|
contents(2).obj.asInstanceOf[AmmoBoxData].unk mustEqual 0
|
2017-03-19 01:04:20 +00:00
|
|
|
case _ =>
|
|
|
|
|
ko
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
"decode (character, alive)" in {
|
|
|
|
|
PacketCoding.DecodePacket(string_character).require match {
|
|
|
|
|
case ObjectCreateMessage(len, cls, guid, parent, data) =>
|
|
|
|
|
len mustEqual 1907
|
|
|
|
|
cls mustEqual ObjectClass.avatar
|
|
|
|
|
guid mustEqual PlanetSideGUID(3902)
|
|
|
|
|
parent.isDefined mustEqual false
|
|
|
|
|
data.isDefined mustEqual true
|
|
|
|
|
data.get.isInstanceOf[CharacterData] mustEqual true
|
|
|
|
|
val pc = data.get.asInstanceOf[CharacterData]
|
|
|
|
|
pc.appearance.pos.coord.x mustEqual 3674.8438f
|
|
|
|
|
pc.appearance.pos.coord.y mustEqual 2726.789f
|
|
|
|
|
pc.appearance.pos.coord.z mustEqual 91.15625f
|
2017-07-10 19:19:47 +00:00
|
|
|
pc.appearance.pos.orient.x mustEqual 0f
|
|
|
|
|
pc.appearance.pos.orient.y mustEqual 0f
|
|
|
|
|
pc.appearance.pos.orient.z mustEqual 64.6875f
|
2017-05-10 00:30:58 +00:00
|
|
|
pc.appearance.pos.vel.isDefined mustEqual true
|
|
|
|
|
pc.appearance.pos.vel.get.x mustEqual 1.4375f
|
|
|
|
|
pc.appearance.pos.vel.get.y mustEqual -0.4375f
|
|
|
|
|
pc.appearance.pos.vel.get.z mustEqual 0f
|
2017-03-19 01:04:20 +00:00
|
|
|
pc.appearance.basic_appearance.name mustEqual "ScrawnyRonnie"
|
|
|
|
|
pc.appearance.basic_appearance.faction mustEqual PlanetSideEmpire.TR
|
|
|
|
|
pc.appearance.basic_appearance.sex mustEqual CharacterGender.Male
|
|
|
|
|
pc.appearance.basic_appearance.head mustEqual 5
|
|
|
|
|
pc.appearance.basic_appearance.voice mustEqual 5
|
|
|
|
|
pc.appearance.voice2 mustEqual 3
|
|
|
|
|
pc.appearance.black_ops mustEqual false
|
|
|
|
|
pc.appearance.jammered mustEqual false
|
|
|
|
|
pc.appearance.exosuit mustEqual ExoSuitType.Reinforced
|
|
|
|
|
pc.appearance.outfit_name mustEqual "Black Beret Armoured Corps"
|
|
|
|
|
pc.appearance.outfit_logo mustEqual 23
|
2017-07-05 01:44:24 +00:00
|
|
|
pc.appearance.facingPitch mustEqual 340.3125f
|
2017-03-19 01:04:20 +00:00
|
|
|
pc.appearance.facingYawUpper mustEqual 0
|
|
|
|
|
pc.appearance.lfs mustEqual false
|
|
|
|
|
pc.appearance.grenade_state mustEqual GrenadeState.None
|
|
|
|
|
pc.appearance.is_cloaking mustEqual false
|
|
|
|
|
pc.appearance.charging_pose mustEqual false
|
|
|
|
|
pc.appearance.on_zipline mustEqual false
|
2017-09-09 00:12:36 +00:00
|
|
|
pc.appearance.ribbons.upper mustEqual MeritCommendation.MarkovVeteran
|
|
|
|
|
pc.appearance.ribbons.middle mustEqual MeritCommendation.HeavyInfantry4
|
|
|
|
|
pc.appearance.ribbons.lower mustEqual MeritCommendation.TankBuster7
|
|
|
|
|
pc.appearance.ribbons.tos mustEqual MeritCommendation.SixYearTR
|
2017-03-19 01:04:20 +00:00
|
|
|
pc.health mustEqual 255
|
|
|
|
|
pc.armor mustEqual 253
|
|
|
|
|
pc.uniform_upgrade mustEqual UniformStyle.ThirdUpgrade
|
|
|
|
|
pc.command_rank mustEqual 5
|
|
|
|
|
pc.implant_effects.isDefined mustEqual true
|
|
|
|
|
pc.implant_effects.get mustEqual ImplantEffects.NoEffects
|
|
|
|
|
pc.cosmetics.isDefined mustEqual true
|
|
|
|
|
pc.cosmetics.get.no_helmet mustEqual true
|
|
|
|
|
pc.cosmetics.get.beret mustEqual true
|
|
|
|
|
pc.cosmetics.get.sunglasses mustEqual true
|
|
|
|
|
pc.cosmetics.get.earpiece mustEqual true
|
|
|
|
|
pc.cosmetics.get.brimmed_cap mustEqual false
|
|
|
|
|
//short test of inventory items
|
|
|
|
|
pc.inventory.isDefined mustEqual true
|
|
|
|
|
val contents = pc.inventory.get.contents
|
|
|
|
|
contents.size mustEqual 5
|
|
|
|
|
//0
|
2017-05-10 00:30:58 +00:00
|
|
|
contents.head.objectClass mustEqual ObjectClass.plasma_grenade
|
|
|
|
|
contents.head.guid mustEqual PlanetSideGUID(3662)
|
|
|
|
|
contents.head.parentSlot mustEqual 0
|
|
|
|
|
contents.head.obj.asInstanceOf[WeaponData].fire_mode mustEqual 0
|
|
|
|
|
contents.head.obj.asInstanceOf[WeaponData].ammo.head.objectClass mustEqual ObjectClass.plasma_grenade_ammo
|
|
|
|
|
contents.head.obj.asInstanceOf[WeaponData].ammo.head.guid mustEqual PlanetSideGUID(3751)
|
2017-03-19 01:04:20 +00:00
|
|
|
//1
|
2017-05-10 00:30:58 +00:00
|
|
|
contents(1).objectClass mustEqual ObjectClass.bank
|
|
|
|
|
contents(1).guid mustEqual PlanetSideGUID(3908)
|
|
|
|
|
contents(1).parentSlot mustEqual 1
|
|
|
|
|
contents(1).obj.asInstanceOf[WeaponData].fire_mode mustEqual 1
|
|
|
|
|
contents(1).obj.asInstanceOf[WeaponData].ammo.head.objectClass mustEqual ObjectClass.armor_canister
|
|
|
|
|
contents(1).obj.asInstanceOf[WeaponData].ammo.head.guid mustEqual PlanetSideGUID(4143)
|
2017-03-19 01:04:20 +00:00
|
|
|
//2
|
2017-05-10 00:30:58 +00:00
|
|
|
contents(2).objectClass mustEqual ObjectClass.mini_chaingun
|
|
|
|
|
contents(2).guid mustEqual PlanetSideGUID(4164)
|
|
|
|
|
contents(2).parentSlot mustEqual 2
|
|
|
|
|
contents(2).obj.asInstanceOf[WeaponData].fire_mode mustEqual 0
|
|
|
|
|
contents(2).obj.asInstanceOf[WeaponData].ammo.head.objectClass mustEqual ObjectClass.bullet_9mm
|
|
|
|
|
contents(2).obj.asInstanceOf[WeaponData].ammo.head.guid mustEqual PlanetSideGUID(3728)
|
2017-03-04 15:06:10 +00:00
|
|
|
//3
|
2017-05-10 00:30:58 +00:00
|
|
|
contents(3).objectClass mustEqual ObjectClass.phoenix //actually, a decimator
|
|
|
|
|
contents(3).guid mustEqual PlanetSideGUID(3603)
|
|
|
|
|
contents(3).parentSlot mustEqual 3
|
|
|
|
|
contents(3).obj.asInstanceOf[WeaponData].fire_mode mustEqual 0
|
|
|
|
|
contents(3).obj.asInstanceOf[WeaponData].ammo.head.objectClass mustEqual ObjectClass.phoenix_missile
|
|
|
|
|
contents(3).obj.asInstanceOf[WeaponData].ammo.head.guid mustEqual PlanetSideGUID(3056)
|
2017-03-04 15:06:10 +00:00
|
|
|
//4
|
2017-05-10 00:30:58 +00:00
|
|
|
contents(4).objectClass mustEqual ObjectClass.chainblade
|
|
|
|
|
contents(4).guid mustEqual PlanetSideGUID(4088)
|
|
|
|
|
contents(4).parentSlot mustEqual 4
|
|
|
|
|
contents(4).obj.asInstanceOf[WeaponData].fire_mode mustEqual 1
|
|
|
|
|
contents(4).obj.asInstanceOf[WeaponData].ammo.head.objectClass mustEqual ObjectClass.melee_ammo
|
|
|
|
|
contents(4).obj.asInstanceOf[WeaponData].ammo.head.guid mustEqual PlanetSideGUID(3279)
|
2017-03-19 01:04:20 +00:00
|
|
|
pc.drawn_slot mustEqual DrawnSlot.Rifle1
|
2017-03-04 15:06:10 +00:00
|
|
|
case _ =>
|
|
|
|
|
ko
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
2017-03-19 01:04:20 +00:00
|
|
|
"decode (character, backpack)" in {
|
|
|
|
|
PacketCoding.DecodePacket(string_character_backpack).require match {
|
|
|
|
|
case ObjectCreateMessage(len, cls, guid, parent, data) =>
|
|
|
|
|
len mustEqual 924L
|
|
|
|
|
cls mustEqual ObjectClass.avatar
|
|
|
|
|
guid mustEqual PlanetSideGUID(3380)
|
|
|
|
|
parent.isDefined mustEqual false
|
|
|
|
|
data.isDefined mustEqual true
|
|
|
|
|
data.get.isInstanceOf[CharacterData] mustEqual true
|
|
|
|
|
val pc = data.get.asInstanceOf[CharacterData]
|
|
|
|
|
pc.appearance.pos.coord.x mustEqual 4629.8906f
|
|
|
|
|
pc.appearance.pos.coord.y mustEqual 6316.4453f
|
|
|
|
|
pc.appearance.pos.coord.z mustEqual 54.734375f
|
2017-07-10 19:19:47 +00:00
|
|
|
pc.appearance.pos.orient.x mustEqual 0f
|
|
|
|
|
pc.appearance.pos.orient.y mustEqual 0f
|
|
|
|
|
pc.appearance.pos.orient.z mustEqual 126.5625f
|
2017-05-10 00:30:58 +00:00
|
|
|
pc.appearance.pos.vel.isDefined mustEqual false
|
2017-03-19 01:04:20 +00:00
|
|
|
pc.appearance.basic_appearance.name mustEqual "Angello"
|
|
|
|
|
pc.appearance.basic_appearance.faction mustEqual PlanetSideEmpire.VS
|
|
|
|
|
pc.appearance.basic_appearance.sex mustEqual CharacterGender.Male
|
|
|
|
|
pc.appearance.basic_appearance.head mustEqual 10
|
|
|
|
|
pc.appearance.basic_appearance.voice mustEqual 2
|
|
|
|
|
pc.appearance.voice2 mustEqual 0
|
|
|
|
|
pc.appearance.black_ops mustEqual false
|
|
|
|
|
pc.appearance.jammered mustEqual false
|
|
|
|
|
pc.appearance.exosuit mustEqual ExoSuitType.MAX
|
|
|
|
|
pc.appearance.outfit_name mustEqual "Original District"
|
|
|
|
|
pc.appearance.outfit_logo mustEqual 23
|
|
|
|
|
pc.appearance.facingPitch mustEqual 0
|
2017-07-05 01:44:24 +00:00
|
|
|
pc.appearance.facingYawUpper mustEqual 180.0f
|
2017-03-19 01:04:20 +00:00
|
|
|
pc.appearance.lfs mustEqual false
|
|
|
|
|
pc.appearance.grenade_state mustEqual GrenadeState.None
|
|
|
|
|
pc.appearance.is_cloaking mustEqual false
|
|
|
|
|
pc.appearance.charging_pose mustEqual false
|
|
|
|
|
pc.appearance.on_zipline mustEqual false
|
2017-09-09 00:12:36 +00:00
|
|
|
pc.appearance.ribbons.upper mustEqual MeritCommendation.Jacking2
|
|
|
|
|
pc.appearance.ribbons.middle mustEqual MeritCommendation.ScavengerVS1
|
2017-05-07 05:34:55 +00:00
|
|
|
pc.appearance.ribbons.lower mustEqual MeritCommendation.AMSSupport4
|
2017-09-09 00:12:36 +00:00
|
|
|
pc.appearance.ribbons.tos mustEqual MeritCommendation.SixYearVS
|
2017-03-19 01:04:20 +00:00
|
|
|
pc.health mustEqual 0
|
|
|
|
|
pc.armor mustEqual 0
|
|
|
|
|
pc.uniform_upgrade mustEqual UniformStyle.ThirdUpgrade
|
|
|
|
|
pc.command_rank mustEqual 2
|
|
|
|
|
pc.implant_effects.isDefined mustEqual false
|
|
|
|
|
pc.cosmetics.isDefined mustEqual true
|
|
|
|
|
pc.cosmetics.get.no_helmet mustEqual true
|
|
|
|
|
pc.cosmetics.get.beret mustEqual true
|
|
|
|
|
pc.cosmetics.get.sunglasses mustEqual true
|
|
|
|
|
pc.cosmetics.get.earpiece mustEqual true
|
|
|
|
|
pc.cosmetics.get.brimmed_cap mustEqual false
|
|
|
|
|
pc.inventory.isDefined mustEqual false
|
|
|
|
|
pc.drawn_slot mustEqual DrawnSlot.Pistol1
|
|
|
|
|
case _ =>
|
|
|
|
|
ko
|
|
|
|
|
}
|
2017-03-04 15:06:10 +00:00
|
|
|
}
|
|
|
|
|
|
2017-03-19 01:04:20 +00:00
|
|
|
"encode (striker projectile)" in {
|
|
|
|
|
val obj = TrackedProjectileData.striker(
|
2017-07-05 01:44:24 +00:00
|
|
|
PlacementData(4644.5938f, 5472.0938f, 82.375f, 0f, 30.9375f, 171.5625f),
|
2017-03-19 01:04:20 +00:00
|
|
|
0
|
|
|
|
|
)
|
|
|
|
|
val msg = ObjectCreateMessage(ObjectClass.striker_missile_targeting_projectile, PlanetSideGUID(40192), obj)
|
2017-03-04 15:06:10 +00:00
|
|
|
val pkt = PacketCoding.EncodePacket(msg).require.toByteVector
|
|
|
|
|
|
2017-07-05 01:44:24 +00:00
|
|
|
pkt.toBitVector.take(132) mustEqual string_striker_projectile.toBitVector.take(132)
|
|
|
|
|
pkt.toBitVector.drop(133).take(7) mustEqual string_striker_projectile.toBitVector.drop(133).take(7)
|
|
|
|
|
pkt.toBitVector.drop(141) mustEqual string_striker_projectile.toBitVector.drop(141)
|
2017-03-04 15:06:10 +00:00
|
|
|
}
|
|
|
|
|
|
2017-03-19 01:04:20 +00:00
|
|
|
"encode (implant interface)" in {
|
2017-05-10 00:30:58 +00:00
|
|
|
val obj = CommonTerminalData(PlanetSideEmpire.VS)
|
2017-03-19 01:04:20 +00:00
|
|
|
val msg = ObjectCreateMessage(0x199, PlanetSideGUID(1075), ObjectCreateMessageParent(PlanetSideGUID(514), 1), obj)
|
2017-03-04 15:06:10 +00:00
|
|
|
val pkt = PacketCoding.EncodePacket(msg).require.toByteVector
|
|
|
|
|
|
2017-03-19 01:04:20 +00:00
|
|
|
pkt mustEqual string_implant_interface
|
2017-03-04 15:06:10 +00:00
|
|
|
}
|
|
|
|
|
|
2017-03-19 01:04:20 +00:00
|
|
|
"encode (order terminal a)" in {
|
2017-05-10 00:30:58 +00:00
|
|
|
val obj = DroppedItemData(
|
2017-07-05 01:44:24 +00:00
|
|
|
PlacementData(4579.3438f, 5615.0703f, 72.953125f, 0f, 0f, 98.4375f),
|
2017-05-10 00:30:58 +00:00
|
|
|
CommonTerminalData(PlanetSideEmpire.NC)
|
|
|
|
|
)
|
2017-03-19 01:04:20 +00:00
|
|
|
val msg = ObjectCreateMessage(ObjectClass.order_terminala, PlanetSideGUID(3827), obj)
|
|
|
|
|
val pkt = PacketCoding.EncodePacket(msg).require.toByteVector
|
2017-03-04 15:06:10 +00:00
|
|
|
|
2017-03-19 01:04:20 +00:00
|
|
|
pkt mustEqual string_order_terminala
|
2017-03-04 15:06:10 +00:00
|
|
|
}
|
|
|
|
|
|
2017-03-19 01:04:20 +00:00
|
|
|
"encode (ace, held)" in {
|
|
|
|
|
val obj = ACEData(4, 8)
|
|
|
|
|
val msg = ObjectCreateMessage(ObjectClass.ace, PlanetSideGUID(3173), ObjectCreateMessageParent(PlanetSideGUID(3336), 0), obj)
|
2017-03-04 15:06:10 +00:00
|
|
|
val pkt = PacketCoding.EncodePacket(msg).require.toByteVector
|
|
|
|
|
|
2017-03-19 01:04:20 +00:00
|
|
|
pkt mustEqual string_ace_held
|
2017-03-04 15:06:10 +00:00
|
|
|
}
|
|
|
|
|
|
2017-03-19 01:04:20 +00:00
|
|
|
"encode (boomer trigger, held)" in {
|
|
|
|
|
val obj = BoomerTriggerData(0)
|
|
|
|
|
val msg = ObjectCreateMessage(ObjectClass.boomer_trigger, PlanetSideGUID(3600), ObjectCreateMessageParent(PlanetSideGUID(4272), 0), obj)
|
|
|
|
|
val pkt = PacketCoding.EncodePacket(msg).require.toByteVector
|
|
|
|
|
|
|
|
|
|
pkt mustEqual string_boomertrigger
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
"encode (detonater, held)" in {
|
|
|
|
|
val obj = CommandDetonaterData(4)
|
|
|
|
|
val msg = ObjectCreateMessage(ObjectClass.command_detonater, PlanetSideGUID(4162), ObjectCreateMessageParent(PlanetSideGUID(4149), 0), obj)
|
|
|
|
|
val pkt = PacketCoding.EncodePacket(msg).require.toByteVector
|
|
|
|
|
|
|
|
|
|
pkt mustEqual string_detonater_held
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
"encode (lasher, held)" in {
|
2017-05-10 00:30:58 +00:00
|
|
|
val obj = WeaponData(4, 8, ObjectClass.energy_cell, PlanetSideGUID(3548), 0, AmmoBoxData(8))
|
2017-03-19 01:04:20 +00:00
|
|
|
val msg = ObjectCreateMessage(ObjectClass.lasher, PlanetSideGUID(3033), ObjectCreateMessageParent(PlanetSideGUID(4141), 3), obj)
|
|
|
|
|
val pkt = PacketCoding.EncodePacket(msg).require.toByteVector
|
|
|
|
|
|
|
|
|
|
pkt mustEqual string_lasher_held
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
"encode (punisher, held)" in {
|
2017-05-10 00:30:58 +00:00
|
|
|
val obj =
|
|
|
|
|
WeaponData(4, 8, 0,
|
|
|
|
|
AmmoBoxData(ObjectClass.bullet_9mm, PlanetSideGUID(3918), 0, AmmoBoxData(8)) ::
|
|
|
|
|
AmmoBoxData(ObjectClass.rocket, PlanetSideGUID(3941), 1, AmmoBoxData(8)) ::
|
|
|
|
|
Nil
|
|
|
|
|
)(2)
|
2017-03-19 01:04:20 +00:00
|
|
|
val msg = ObjectCreateMessage(ObjectClass.punisher, PlanetSideGUID(4147), ObjectCreateMessageParent(PlanetSideGUID(3092), 3), obj)
|
|
|
|
|
val pkt = PacketCoding.EncodePacket(msg).require.toByteVector
|
|
|
|
|
|
|
|
|
|
pkt mustEqual string_punisher_held
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
"encode (REK, held)" in {
|
|
|
|
|
val obj = REKData(0, 8)
|
|
|
|
|
val msg = ObjectCreateMessage(ObjectClass.remote_electronics_kit, PlanetSideGUID(3893), ObjectCreateMessageParent(PlanetSideGUID(4174), 0), obj)
|
|
|
|
|
val pkt = PacketCoding.EncodePacket(msg).require.toByteVector
|
|
|
|
|
|
|
|
|
|
pkt mustEqual string_rek_held
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
"encode (capture flag)" in {
|
2017-07-05 01:44:24 +00:00
|
|
|
val obj = CaptureFlagData(PlacementData(3912.0312f, 5169.4375f, 59.96875f, 0f, 0f, 47.8125f), PlanetSideEmpire.NC, 21, 4, 2838, 9)
|
2017-03-19 01:04:20 +00:00
|
|
|
val msg = ObjectCreateMessage(ObjectClass.capture_flag, PlanetSideGUID(4330), obj)
|
|
|
|
|
val pkt = PacketCoding.EncodePacket(msg).require.toByteVector
|
|
|
|
|
|
|
|
|
|
pkt mustEqual string_captureflag
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
"encode (ace, dropped)" in {
|
|
|
|
|
val obj = DroppedItemData(
|
2017-07-10 19:19:47 +00:00
|
|
|
PlacementData(4708.461f, 5547.539f, 72.703125f, 0f, 0f, 194.0625f),
|
2017-03-19 01:04:20 +00:00
|
|
|
ACEData(8, 8)
|
|
|
|
|
)
|
|
|
|
|
val msg = ObjectCreateMessage(ObjectClass.ace, PlanetSideGUID(4388), obj)
|
|
|
|
|
val pkt = PacketCoding.EncodePacket(msg).require.toByteVector
|
|
|
|
|
|
|
|
|
|
pkt mustEqual string_ace_dropped
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
"encode (detonator, dropped)" in {
|
|
|
|
|
val obj = DroppedItemData(
|
2017-07-10 19:19:47 +00:00
|
|
|
PlacementData(4777.633f, 5485.4062f, 85.8125f, 0f, 0f, 14.0625f),
|
2017-03-19 01:04:20 +00:00
|
|
|
CommandDetonaterData()
|
|
|
|
|
)
|
|
|
|
|
val msg = ObjectCreateMessage(ObjectClass.command_detonater, PlanetSideGUID(3682), obj)
|
|
|
|
|
val pkt = PacketCoding.EncodePacket(msg).require.toByteVector
|
|
|
|
|
|
|
|
|
|
pkt mustEqual string_detonater_dropped
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
"encode (shotgun shells, dropped)" in {
|
|
|
|
|
val obj = DroppedItemData(
|
2017-07-10 19:19:47 +00:00
|
|
|
PlacementData(4684.7344f, 5547.4844f, 83.765625f, 0f, 0f, 199.6875f),
|
2017-03-19 01:04:20 +00:00
|
|
|
AmmoBoxData()
|
|
|
|
|
)
|
|
|
|
|
val msg = ObjectCreateMessage(ObjectClass.shotgun_shell, PlanetSideGUID(3453), obj)
|
|
|
|
|
val pkt = PacketCoding.EncodePacket(msg).require.toByteVector
|
|
|
|
|
|
|
|
|
|
pkt mustEqual string_shotgunshell_dropped
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
"encode (lasher, dropped)" in {
|
|
|
|
|
val obj = DroppedItemData(
|
2017-07-10 19:19:47 +00:00
|
|
|
PlacementData(4691.1953f, 5537.039f, 65.484375f, 0.0f, 0.0f, 0.0f),
|
2017-05-10 00:30:58 +00:00
|
|
|
WeaponData(4, 0, ObjectClass.energy_cell, PlanetSideGUID(3268), 0, AmmoBoxData())
|
2017-03-19 01:04:20 +00:00
|
|
|
)
|
|
|
|
|
val msg = ObjectCreateMessage(ObjectClass.lasher, PlanetSideGUID(3074), obj)
|
|
|
|
|
val pkt = PacketCoding.EncodePacket(msg).require.toByteVector
|
|
|
|
|
|
|
|
|
|
pkt mustEqual string_lasher_dropped
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
"encode (punisher, dropped)" in {
|
|
|
|
|
val obj = DroppedItemData(
|
2017-07-10 19:19:47 +00:00
|
|
|
PlacementData(4789.133f, 5522.3125f, 72.3125f, 0f, 0f, 306.5625f),
|
2017-05-10 00:30:58 +00:00
|
|
|
WeaponData(2, 0, 0,
|
2017-03-19 01:04:20 +00:00
|
|
|
AmmoBoxData(ObjectClass.bullet_9mm, PlanetSideGUID(3528), 0, AmmoBoxData()) ::
|
|
|
|
|
AmmoBoxData(ObjectClass.rocket, PlanetSideGUID(3031), 1, AmmoBoxData()) ::
|
|
|
|
|
Nil
|
2017-05-10 00:30:58 +00:00
|
|
|
)(2)
|
2017-03-19 01:04:20 +00:00
|
|
|
)
|
|
|
|
|
val msg = ObjectCreateMessage(ObjectClass.punisher, PlanetSideGUID(2978), obj)
|
|
|
|
|
val pkt = PacketCoding.EncodePacket(msg).require.toByteVector
|
|
|
|
|
|
|
|
|
|
pkt mustEqual string_punisher_dropped
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
"encode (REK, dropped)" in {
|
|
|
|
|
val obj = DroppedItemData(
|
2017-07-10 19:19:47 +00:00
|
|
|
PlacementData(4675.039f, 5506.953f, 72.703125f, 0f, 0f, 230.625f),
|
2017-03-19 01:04:20 +00:00
|
|
|
REKData(8, 0, 3)
|
|
|
|
|
)
|
|
|
|
|
val msg = ObjectCreateMessage(ObjectClass.remote_electronics_kit, PlanetSideGUID(4355), obj)
|
|
|
|
|
val pkt = PacketCoding.EncodePacket(msg).require.toByteVector
|
|
|
|
|
|
|
|
|
|
pkt mustEqual string_rek_dropped
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
"encode (boomer)" in {
|
|
|
|
|
val obj = SmallDeployableData(
|
2017-05-10 00:30:58 +00:00
|
|
|
CommonFieldData(
|
2017-07-10 19:19:47 +00:00
|
|
|
PlacementData(4704.172f, 5546.4375f, 82.234375f, 0f, 0f, 272.8125f),
|
2017-05-10 00:30:58 +00:00
|
|
|
PlanetSideEmpire.TR, 0, PlanetSideGUID(4145)
|
2017-03-19 01:04:20 +00:00
|
|
|
)
|
|
|
|
|
)
|
|
|
|
|
val msg = ObjectCreateMessage(ObjectClass.boomer, PlanetSideGUID(3840), obj)
|
|
|
|
|
val pkt = PacketCoding.EncodePacket(msg).require.toByteVector
|
|
|
|
|
|
|
|
|
|
pkt mustEqual string_boomer
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
"encode (spitfire, short)" in {
|
|
|
|
|
val obj = SmallTurretData(
|
2017-05-10 00:30:58 +00:00
|
|
|
CommonFieldData(
|
2017-07-10 19:19:47 +00:00
|
|
|
PlacementData(4577.7812f, 5624.828f, 72.046875f, 0f, 2.8125f, 264.375f),
|
2017-10-19 00:26:41 +00:00
|
|
|
PlanetSideEmpire.NC, true, 2, PlanetSideGUID(3871)
|
2017-03-19 01:04:20 +00:00
|
|
|
),
|
|
|
|
|
255 //sets to 0
|
|
|
|
|
)
|
|
|
|
|
val msg = ObjectCreateMessage(ObjectClass.spitfire_turret, PlanetSideGUID(4208), obj)
|
|
|
|
|
val pkt = PacketCoding.EncodePacket(msg).require.toByteVector
|
|
|
|
|
|
|
|
|
|
val pkt_bitv = pkt.toBitVector
|
|
|
|
|
val ori_bitv = string_spitfire_short.toBitVector
|
|
|
|
|
pkt_bitv.take(173) mustEqual ori_bitv.take(173)
|
|
|
|
|
pkt_bitv.drop(185) mustEqual ori_bitv.drop(185)
|
|
|
|
|
//TODO work on SmallTurretData to make this pass as a single stream
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
"encode (spitfire)" in {
|
|
|
|
|
val obj = SmallTurretData(
|
2017-05-10 00:30:58 +00:00
|
|
|
CommonFieldData(
|
2017-07-10 19:19:47 +00:00
|
|
|
PlacementData(4527.633f, 6271.3594f, 70.265625f, 0f, 0f, 154.6875f),
|
2017-10-19 00:26:41 +00:00
|
|
|
PlanetSideEmpire.VS, 2, PlanetSideGUID(4232)
|
2017-03-19 01:04:20 +00:00
|
|
|
),
|
|
|
|
|
255,
|
2017-05-10 00:30:58 +00:00
|
|
|
SmallTurretData.spitfire(PlanetSideGUID(3064), 0x6, 0x8, PlanetSideGUID(3694), 8)
|
2017-03-19 01:04:20 +00:00
|
|
|
)
|
|
|
|
|
val msg = ObjectCreateMessage(ObjectClass.spitfire_turret, PlanetSideGUID(4265), obj)
|
|
|
|
|
val pkt = PacketCoding.EncodePacket(msg).require.toByteVector
|
|
|
|
|
|
|
|
|
|
val pkt_bitv = pkt.toBitVector
|
|
|
|
|
val ori_bitv = string_spitfire.toBitVector
|
|
|
|
|
pkt_bitv.take(173) mustEqual ori_bitv.take(173)
|
|
|
|
|
pkt_bitv.drop(185) mustEqual ori_bitv.drop(185)
|
|
|
|
|
//TODO work on SmallTurretData to make this pass as a single stream
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
"encode (trap)" in {
|
|
|
|
|
val obj = TRAPData(
|
2017-05-10 00:30:58 +00:00
|
|
|
CommonFieldData(
|
2017-07-10 19:19:47 +00:00
|
|
|
PlacementData(3572.4453f, 3277.9766f, 114.0f, 0f, 0f, 90.0f),
|
2017-10-19 00:26:41 +00:00
|
|
|
PlanetSideEmpire.VS, 2, PlanetSideGUID(2502)
|
2017-03-19 01:04:20 +00:00
|
|
|
),
|
|
|
|
|
255
|
|
|
|
|
)
|
|
|
|
|
val msg = ObjectCreateMessage(ObjectClass.tank_traps, PlanetSideGUID(2659), obj)
|
|
|
|
|
val pkt = PacketCoding.EncodePacket(msg).require.toByteVector
|
|
|
|
|
|
|
|
|
|
val pkt_bitv = pkt.toBitVector
|
|
|
|
|
val ori_bitv = string_trap.toBitVector
|
|
|
|
|
pkt_bitv.take(173) mustEqual ori_bitv.take(173)
|
|
|
|
|
pkt_bitv.drop(185) mustEqual ori_bitv.drop(185)
|
|
|
|
|
//TODO work on TRAPData to make this pass as a single stream
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
"encode (aegis)" in {
|
|
|
|
|
val obj = AegisShieldGeneratorData(
|
2017-05-10 00:30:58 +00:00
|
|
|
CommonFieldData(
|
2017-07-10 19:19:47 +00:00
|
|
|
PlacementData(3571.2266f, 3278.0938f, 114.0f, 0f, 0f, 90.0f),
|
2017-10-19 00:26:41 +00:00
|
|
|
PlanetSideEmpire.VS, 2, PlanetSideGUID(2366)
|
2017-03-19 01:04:20 +00:00
|
|
|
),
|
|
|
|
|
255
|
|
|
|
|
)
|
|
|
|
|
val msg = ObjectCreateMessage(ObjectClass.deployable_shield_generator, PlanetSideGUID(2556), obj)
|
|
|
|
|
val pkt = PacketCoding.EncodePacket(msg).require.toByteVector
|
|
|
|
|
|
|
|
|
|
pkt mustEqual string_aegis
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
"encode (orion)" in {
|
|
|
|
|
val obj = OneMannedFieldTurretData(
|
2017-05-10 00:30:58 +00:00
|
|
|
CommonFieldData(
|
2017-07-10 19:19:47 +00:00
|
|
|
PlacementData(3567.1406f, 2988.0078f, 71.84375f, 0f, 0f, 185.625f),
|
2017-10-19 00:26:41 +00:00
|
|
|
PlanetSideEmpire.VS, 2, PlanetSideGUID(2502)
|
2017-03-19 01:04:20 +00:00
|
|
|
),
|
|
|
|
|
255,
|
2017-05-10 00:30:58 +00:00
|
|
|
OneMannedFieldTurretData.orion(PlanetSideGUID(2615), 0x6, 0x8, PlanetSideGUID(2510), 8)
|
2017-03-19 01:04:20 +00:00
|
|
|
)
|
|
|
|
|
val msg = ObjectCreateMessage(ObjectClass.portable_manned_turret_vs, PlanetSideGUID(2916), obj)
|
|
|
|
|
val pkt = PacketCoding.EncodePacket(msg).require.toByteVector
|
|
|
|
|
|
|
|
|
|
val pkt_bitv = pkt.toBitVector
|
|
|
|
|
val ori_bitv = string_orion.toBitVector
|
|
|
|
|
pkt_bitv.take(189) mustEqual ori_bitv.take(189)
|
|
|
|
|
pkt_bitv.drop(200) mustEqual ori_bitv.drop(200)
|
|
|
|
|
//TODO work on OneMannedFieldTurretData to make this pass as a single stream
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
"encode (locker container)" in {
|
|
|
|
|
val obj = LockerContainerData(
|
2017-03-04 15:06:10 +00:00
|
|
|
InventoryData(
|
new stuff for player server classes; this update is not yet complete
adjusted sample Reload code and added insertion and removal functions for inventory
more work on player classes; moving PacketResolution to another branch
decoupling GUIDs from objects; introduced Ammo enum; minor adjustments to inventory system; different object/class hierarchy
transferring basic files from another branch
converted from get/set to accessor/mutator; resolved conflict from name changes
refactored basic components such as GUID and location/orientation
utilities kludge; more fields are given accessor and mutators; create package for vehicle-specific classes
GUID assurance, now with less object creation
test files; changes to how AmmoBox initializes
sorry, a little bit of everything, so much I forgot to write it all down
switched to a unified fire mode object internal to a Tool
importing a heavily modified version of my GUID manager objects from the laternate branch; not finished or tested yet
created a Trait to make Key private, sources and selectors to allow NumberPools to exist independent of a NumberSource; placed Ascending into a misc folder
swapped the Return methods for selectors so that the more primitive logic is the one that needs to be overriden; renamed a selector to be more common; had to update some copyright messages
fixed major logic issue with NumberPool; added comments to NumberSource files
NumberSource tests
simplified and made more consistent the method naming convention of NumberSources
comments for NumberSelectors
starting on NumberSelector tests
modifications that should better support number pools; added a pool hub that acts on a predefined source
adjustment to how Tools and FireModeDefintion keep track of ammunition and ammunition slots; I don't think this is sufficient
small additions to Tools; filled out simple tests for other three Selectors
added object lookup notation for the pool hub
added more NumberSelector tests; removed the word 'Number' from subclass names
re-named classes, re-packaged classes, re-named packages; created new Selector, split pools to create a fallback for the NumberPoolHub
changes to NumberPool classes; tests on NumberPool classes
changes to NumberPool classes; tests on NumberPool classes2
some robust testing for NumberPoolHub, plus necessary modifications to other files
register and unregister functions now use Success and Failure conditions, save for one true thrown Exception
reduced the flow of certain algorithm chains, mainly by adding match statements and removing Exceptions
error message text
the same thing as the last commit, but with NumberPools rather than NumberPoolHub
various types of freeform registration
added sorting functions to Selectors to allow for hotswapping for number pools, especially to and from SpecificSelector; tests for NumberPoolHub
get numbers from an Array of indices, not the list of Numbers, in SimplePool
added a class to represent the four types of recovery kits
comments on Kit files
created package for supporting equipment classes; renamed /definition/ package
adding class for items that construct deployables, the router telepad included
added SimpleItem, classes for game Equipment that do not have internal state; re-organized ObjectDefinition files and the game objects they create to more naturally move around EquipmentSize and InventoryTile (size)
added SimpleItem tests (what they are...); removed example code that has hogging an import from AmmoBox
auto-sort for loading and fitting former inventory content back into the inventory
method of finding first available position to fit an certain size block in the inventory
changed CheckCollision return type to provide Try[List[Int]; fixed all existing references and tests
wrote comments for GridInventory methods; changed insertion param to be of form 'key -> element'
adding features to Player; created definitions for Player class; re-grouped ConstructionItem enumerations
initial work on implants; shuffled classes to better accommodate the new implant system, I think
wrote some tests for Implants; fixing Implant logic
wrote tests for Player class and made adjustments where necessary
basic initialization during Player creation based on exo-suit type
three wrapper Actors for the normal classes
comments on code
modified tests to improve accountability; added Resolver class to deal with multiple tasks that contribute to a larger task
changed Tools to an internal AmmoBox; don't have to def -= symbol if I def _= symbol
LivePlayerList -> MasterPlayerList, and added a Fit def for Player that checks holsters as well as inventory
example of packet conversion can be found with AmmoBoxDefinition
added conversion for ToolDefinition
added all Equipment packet conversion functionality; started working on Avatar-related conversions
continued effort towards a working Player packet conversion test
subclasses of Equipment apparently do not need to overide the type of the PacketConverter for generics
the logical conclusion: it doesn't matter what generics Packet returns so long as it returns an ObjectCreateConverter[] type
separated converters from definitions into files
changed some configuration information to final; added a bunch of converters, not fully tested though
changed function names in converters
replaced WSA packet-driven OCDM with Player object OCDM; upgrade to Float angular data
added partial support for LockerContainer; changed Equipment defaults to a common value
changes to AvatarConverter to include 5th slot; changes to VehicleConverter to make work; implementation of Fury in Vehicle->packet example in WSA
added a seat definition and renovated how the weapon controlled from a seat can be found
comments to files mainly; non-essential functionality to some classes, mostly access determination
moved converter tests to their own test file
write more of this test
added ServiceManager, as it is useful
pool range changes
added AvatarService, as it is useful
straightened out the GUID actors; added the static method for adding AmmoBoxes (to be converted later)
chnages to task resolution operation
complicated Task and TaskResolver logic is now possible; for example, you can schedule giving an AmmoBox a GUID, before giving a Tool a GUID, before placing the Tool in a player's hand; see Suppressor example in WSA
separated the Task trait and the TaskResolver actor into their own classes, moving the former RegistrationTaskResolver class into the /misc/ folder; deleted old backup copy of HubActor; modifications for PoC and supported tests
added better support and protection against putting things in the wrong hand when using inventories and the Player.Slot(n) function
GlobalDefinitions file; added laze pointer as an SItem, and gave it the command detonater management code; additionally fixed spelling of 'detonat[o]r' in Codec; early Terminal class work
updated tests to GlobalDefinitions entries; Terminal works but I don't like it
played with GUID pooling workflow, though to little avail; modifications to Terminal purchasing workflow, but still very volatile
modified NumberPoolActor and NumberPoolAccessor to make them more straightforward and not use akka ask as a go-between
fixed recovery options so that they do not cause more messages
trailing newline
InventoryItem (packet data) renamed InventoryItemData to remove ambiguity; Terminal functionality improved, allowing for swapping of exo-suits and the restoration of equipment positions
remove yet-unsupported Terminal messaging
made Terminal message more specific; can now put equipment into empty slot on exo-suit change; should report changes better
re-organized function calls to preserved items removed from holster slots on exo-suit change
moved predicate to the end of the list of params for recoverInventory so that repetition can be eliminated and a default value can be assigned
issues with making Tool; committing changes before revert of NumberPoolActor and NumberPoolAccessorActor to see if those broke it
a necessary evil, the reverting of these two Actors; subtask resolution does not work unless I do so, for now
restored the registration portion of tasking back to where it previously was (and better?)
NumberPoolActor and the ...AccessorActor are back to a comfortable place (and better?)
re-draw object in hand when switching exo-suits; build AmmoBoxes for Tool during Terminal-controlled creation, not Tool-controlled creation
order of task cleanup reversed to avoid index mismatch; added itsm to TerminalDefinition
common 5x5 AmmoBox size; added vehicle weapon ammo boxes to terminal
added error catching messages; stopped odd double-registering issue early
resolved issue where multiple subtasks started their main task multiple times; added checks that an object does not register a new GUID when it already has one
wrote unregistration code for Selling items back through the Terminal, repairing logic along the way; also, wrote a top-level GUID find for the Player for use of MoveItem
added framework for starting on Loadouts; managed issue with parent tasks starting before being summoned by child subtasks, often resulting in the complete skip of the execution phase of the parent; refactored registration tasks in WSA
modified Tool structure, exposing the AmmoSlot list a bit more
stuff stuff Tool ammo slot changes to default and comments
basic loadout framework for Infantry; need to integrate
initial work on FavoritesRequest packet
tests for FavoritesRequest packet
increased size of number pool for testing; wrote an algorithm that translates to and from the simplified version of objects stored in loadouts
refactored the tasking for adding Equipment and removing Equipment
updated the inventory so the Map of items does not have to rely on the GUID of an item being set before the item is inserted
untested routine for registering a player character; pushing all changes before making significant changes to the client init code structure
added to comments of BeginZoningMessage; transitioned player through and initial step of a more proper login GUID association
the current avatar is properly registered and there is something of a workflow with the messages and packets
corrected another bit of logic where inventories used to be indexed by object GUID in AvatarConverter; reversed unregister-remove task sequence such that GUID-less object is not allowed to exist in a stable object hierarchy
working Loadout loading
added identification functions to GlobalDefinitions; echo ObjectDelete back to client
accidentally got rid of something in WSA, but now restored; adding extra details to Terminal operations
separated Terminal into separate files and moved files into their own package under \objects\ for now; can delete loadouts now in WSA
better handling of ReloadMessage and MoveItemMessage
framework for better support involving dropping and picking up items
code comments and small modifications, such as the location and structure of the Terminal Equipment definitions
wrote comments in GlobalDefinitions; modified code so that a primitive form of player synchronization now occurs for future testing
added code to display already-dropped Equipment on the ground; limitations are explained; moved TaskResolver to more a global location, though I don't know if that helps
modified avatar unregister logic to ensure vacating player is deleted from other clients 'properly'
more comments; improved checks for MoveItemMessage; squared distances as necessary
subtle changes to login scripting so that test character is always offered
re-organizing the functions in WSA so that only the local objects separate the two message processing blocks
2017-05-30 22:46:01 +00:00
|
|
|
InventoryItemData(ObjectClass.nano_dispenser, PlanetSideGUID(2935), 0, WeaponData(0x6, 0x0, ObjectClass.armor_canister, PlanetSideGUID(3426), 0, AmmoBoxData())) ::
|
|
|
|
|
InventoryItemData(ObjectClass.armor_canister, PlanetSideGUID(4090), 45, AmmoBoxData()) ::
|
|
|
|
|
InventoryItemData(ObjectClass.armor_canister, PlanetSideGUID(3326), 78, AmmoBoxData()) ::
|
2017-03-19 01:04:20 +00:00
|
|
|
Nil
|
2017-03-04 15:06:10 +00:00
|
|
|
)
|
|
|
|
|
)
|
2017-03-19 01:04:20 +00:00
|
|
|
val msg = ObjectCreateMessage(ObjectClass.locker_container, PlanetSideGUID(3148), obj)
|
|
|
|
|
val pkt = PacketCoding.EncodePacket(msg).require.toByteVector
|
|
|
|
|
|
|
|
|
|
pkt mustEqual string_locker_container
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
"encode (character, alive)" in {
|
|
|
|
|
val obj = CharacterData(
|
|
|
|
|
CharacterAppearanceData(
|
|
|
|
|
PlacementData(
|
|
|
|
|
Vector3(3674.8438f, 2726.789f, 91.15625f),
|
2017-07-10 19:19:47 +00:00
|
|
|
Vector3(0f, 0f, 64.6875f),
|
2017-03-19 01:04:20 +00:00
|
|
|
Some(Vector3(1.4375f, -0.4375f, 0f))
|
|
|
|
|
),
|
|
|
|
|
BasicCharacterData(
|
|
|
|
|
"ScrawnyRonnie",
|
|
|
|
|
PlanetSideEmpire.TR,
|
|
|
|
|
CharacterGender.Male,
|
|
|
|
|
5,
|
|
|
|
|
5
|
|
|
|
|
),
|
|
|
|
|
3,
|
|
|
|
|
false,
|
|
|
|
|
false,
|
|
|
|
|
ExoSuitType.Reinforced,
|
|
|
|
|
"Black Beret Armoured Corps",
|
|
|
|
|
23,
|
|
|
|
|
false,
|
2017-07-05 01:44:24 +00:00
|
|
|
340.3125f, 0f,
|
2017-03-19 01:04:20 +00:00
|
|
|
false,
|
|
|
|
|
GrenadeState.None,
|
|
|
|
|
false, false, false,
|
2017-05-07 05:34:55 +00:00
|
|
|
RibbonBars(
|
2017-09-09 00:12:36 +00:00
|
|
|
MeritCommendation.MarkovVeteran,
|
|
|
|
|
MeritCommendation.HeavyInfantry4,
|
|
|
|
|
MeritCommendation.TankBuster7,
|
|
|
|
|
MeritCommendation.SixYearTR
|
2017-05-07 05:34:55 +00:00
|
|
|
)
|
2017-03-19 01:04:20 +00:00
|
|
|
),
|
|
|
|
|
255, 253,
|
|
|
|
|
UniformStyle.ThirdUpgrade,
|
|
|
|
|
5,
|
|
|
|
|
Some(ImplantEffects.NoEffects),
|
|
|
|
|
Some(Cosmetics(true, true, true, true, false)),
|
|
|
|
|
InventoryData(
|
new stuff for player server classes; this update is not yet complete
adjusted sample Reload code and added insertion and removal functions for inventory
more work on player classes; moving PacketResolution to another branch
decoupling GUIDs from objects; introduced Ammo enum; minor adjustments to inventory system; different object/class hierarchy
transferring basic files from another branch
converted from get/set to accessor/mutator; resolved conflict from name changes
refactored basic components such as GUID and location/orientation
utilities kludge; more fields are given accessor and mutators; create package for vehicle-specific classes
GUID assurance, now with less object creation
test files; changes to how AmmoBox initializes
sorry, a little bit of everything, so much I forgot to write it all down
switched to a unified fire mode object internal to a Tool
importing a heavily modified version of my GUID manager objects from the laternate branch; not finished or tested yet
created a Trait to make Key private, sources and selectors to allow NumberPools to exist independent of a NumberSource; placed Ascending into a misc folder
swapped the Return methods for selectors so that the more primitive logic is the one that needs to be overriden; renamed a selector to be more common; had to update some copyright messages
fixed major logic issue with NumberPool; added comments to NumberSource files
NumberSource tests
simplified and made more consistent the method naming convention of NumberSources
comments for NumberSelectors
starting on NumberSelector tests
modifications that should better support number pools; added a pool hub that acts on a predefined source
adjustment to how Tools and FireModeDefintion keep track of ammunition and ammunition slots; I don't think this is sufficient
small additions to Tools; filled out simple tests for other three Selectors
added object lookup notation for the pool hub
added more NumberSelector tests; removed the word 'Number' from subclass names
re-named classes, re-packaged classes, re-named packages; created new Selector, split pools to create a fallback for the NumberPoolHub
changes to NumberPool classes; tests on NumberPool classes
changes to NumberPool classes; tests on NumberPool classes2
some robust testing for NumberPoolHub, plus necessary modifications to other files
register and unregister functions now use Success and Failure conditions, save for one true thrown Exception
reduced the flow of certain algorithm chains, mainly by adding match statements and removing Exceptions
error message text
the same thing as the last commit, but with NumberPools rather than NumberPoolHub
various types of freeform registration
added sorting functions to Selectors to allow for hotswapping for number pools, especially to and from SpecificSelector; tests for NumberPoolHub
get numbers from an Array of indices, not the list of Numbers, in SimplePool
added a class to represent the four types of recovery kits
comments on Kit files
created package for supporting equipment classes; renamed /definition/ package
adding class for items that construct deployables, the router telepad included
added SimpleItem, classes for game Equipment that do not have internal state; re-organized ObjectDefinition files and the game objects they create to more naturally move around EquipmentSize and InventoryTile (size)
added SimpleItem tests (what they are...); removed example code that has hogging an import from AmmoBox
auto-sort for loading and fitting former inventory content back into the inventory
method of finding first available position to fit an certain size block in the inventory
changed CheckCollision return type to provide Try[List[Int]; fixed all existing references and tests
wrote comments for GridInventory methods; changed insertion param to be of form 'key -> element'
adding features to Player; created definitions for Player class; re-grouped ConstructionItem enumerations
initial work on implants; shuffled classes to better accommodate the new implant system, I think
wrote some tests for Implants; fixing Implant logic
wrote tests for Player class and made adjustments where necessary
basic initialization during Player creation based on exo-suit type
three wrapper Actors for the normal classes
comments on code
modified tests to improve accountability; added Resolver class to deal with multiple tasks that contribute to a larger task
changed Tools to an internal AmmoBox; don't have to def -= symbol if I def _= symbol
LivePlayerList -> MasterPlayerList, and added a Fit def for Player that checks holsters as well as inventory
example of packet conversion can be found with AmmoBoxDefinition
added conversion for ToolDefinition
added all Equipment packet conversion functionality; started working on Avatar-related conversions
continued effort towards a working Player packet conversion test
subclasses of Equipment apparently do not need to overide the type of the PacketConverter for generics
the logical conclusion: it doesn't matter what generics Packet returns so long as it returns an ObjectCreateConverter[] type
separated converters from definitions into files
changed some configuration information to final; added a bunch of converters, not fully tested though
changed function names in converters
replaced WSA packet-driven OCDM with Player object OCDM; upgrade to Float angular data
added partial support for LockerContainer; changed Equipment defaults to a common value
changes to AvatarConverter to include 5th slot; changes to VehicleConverter to make work; implementation of Fury in Vehicle->packet example in WSA
added a seat definition and renovated how the weapon controlled from a seat can be found
comments to files mainly; non-essential functionality to some classes, mostly access determination
moved converter tests to their own test file
write more of this test
added ServiceManager, as it is useful
pool range changes
added AvatarService, as it is useful
straightened out the GUID actors; added the static method for adding AmmoBoxes (to be converted later)
chnages to task resolution operation
complicated Task and TaskResolver logic is now possible; for example, you can schedule giving an AmmoBox a GUID, before giving a Tool a GUID, before placing the Tool in a player's hand; see Suppressor example in WSA
separated the Task trait and the TaskResolver actor into their own classes, moving the former RegistrationTaskResolver class into the /misc/ folder; deleted old backup copy of HubActor; modifications for PoC and supported tests
added better support and protection against putting things in the wrong hand when using inventories and the Player.Slot(n) function
GlobalDefinitions file; added laze pointer as an SItem, and gave it the command detonater management code; additionally fixed spelling of 'detonat[o]r' in Codec; early Terminal class work
updated tests to GlobalDefinitions entries; Terminal works but I don't like it
played with GUID pooling workflow, though to little avail; modifications to Terminal purchasing workflow, but still very volatile
modified NumberPoolActor and NumberPoolAccessor to make them more straightforward and not use akka ask as a go-between
fixed recovery options so that they do not cause more messages
trailing newline
InventoryItem (packet data) renamed InventoryItemData to remove ambiguity; Terminal functionality improved, allowing for swapping of exo-suits and the restoration of equipment positions
remove yet-unsupported Terminal messaging
made Terminal message more specific; can now put equipment into empty slot on exo-suit change; should report changes better
re-organized function calls to preserved items removed from holster slots on exo-suit change
moved predicate to the end of the list of params for recoverInventory so that repetition can be eliminated and a default value can be assigned
issues with making Tool; committing changes before revert of NumberPoolActor and NumberPoolAccessorActor to see if those broke it
a necessary evil, the reverting of these two Actors; subtask resolution does not work unless I do so, for now
restored the registration portion of tasking back to where it previously was (and better?)
NumberPoolActor and the ...AccessorActor are back to a comfortable place (and better?)
re-draw object in hand when switching exo-suits; build AmmoBoxes for Tool during Terminal-controlled creation, not Tool-controlled creation
order of task cleanup reversed to avoid index mismatch; added itsm to TerminalDefinition
common 5x5 AmmoBox size; added vehicle weapon ammo boxes to terminal
added error catching messages; stopped odd double-registering issue early
resolved issue where multiple subtasks started their main task multiple times; added checks that an object does not register a new GUID when it already has one
wrote unregistration code for Selling items back through the Terminal, repairing logic along the way; also, wrote a top-level GUID find for the Player for use of MoveItem
added framework for starting on Loadouts; managed issue with parent tasks starting before being summoned by child subtasks, often resulting in the complete skip of the execution phase of the parent; refactored registration tasks in WSA
modified Tool structure, exposing the AmmoSlot list a bit more
stuff stuff Tool ammo slot changes to default and comments
basic loadout framework for Infantry; need to integrate
initial work on FavoritesRequest packet
tests for FavoritesRequest packet
increased size of number pool for testing; wrote an algorithm that translates to and from the simplified version of objects stored in loadouts
refactored the tasking for adding Equipment and removing Equipment
updated the inventory so the Map of items does not have to rely on the GUID of an item being set before the item is inserted
untested routine for registering a player character; pushing all changes before making significant changes to the client init code structure
added to comments of BeginZoningMessage; transitioned player through and initial step of a more proper login GUID association
the current avatar is properly registered and there is something of a workflow with the messages and packets
corrected another bit of logic where inventories used to be indexed by object GUID in AvatarConverter; reversed unregister-remove task sequence such that GUID-less object is not allowed to exist in a stable object hierarchy
working Loadout loading
added identification functions to GlobalDefinitions; echo ObjectDelete back to client
accidentally got rid of something in WSA, but now restored; adding extra details to Terminal operations
separated Terminal into separate files and moved files into their own package under \objects\ for now; can delete loadouts now in WSA
better handling of ReloadMessage and MoveItemMessage
framework for better support involving dropping and picking up items
code comments and small modifications, such as the location and structure of the Terminal Equipment definitions
wrote comments in GlobalDefinitions; modified code so that a primitive form of player synchronization now occurs for future testing
added code to display already-dropped Equipment on the ground; limitations are explained; moved TaskResolver to more a global location, though I don't know if that helps
modified avatar unregister logic to ensure vacating player is deleted from other clients 'properly'
more comments; improved checks for MoveItemMessage; squared distances as necessary
subtle changes to login scripting so that test character is always offered
re-organizing the functions in WSA so that only the local objects separate the two message processing blocks
2017-05-30 22:46:01 +00:00
|
|
|
InventoryItemData(ObjectClass.plasma_grenade, PlanetSideGUID(3662), 0, WeaponData(0, 0, ObjectClass.plasma_grenade_ammo, PlanetSideGUID(3751), 0, AmmoBoxData())) ::
|
|
|
|
|
InventoryItemData(ObjectClass.bank, PlanetSideGUID(3908), 1, WeaponData(0, 0, 1, ObjectClass.armor_canister, PlanetSideGUID(4143), 0, AmmoBoxData())) ::
|
|
|
|
|
InventoryItemData(ObjectClass.mini_chaingun, PlanetSideGUID(4164), 2, WeaponData(0, 0, ObjectClass.bullet_9mm, PlanetSideGUID(3728), 0, AmmoBoxData())) ::
|
|
|
|
|
InventoryItemData(ObjectClass.phoenix, PlanetSideGUID(3603), 3, WeaponData(0, 0, ObjectClass.phoenix_missile, PlanetSideGUID(3056), 0, AmmoBoxData())) ::
|
|
|
|
|
InventoryItemData(ObjectClass.chainblade, PlanetSideGUID(4088), 4, WeaponData(0, 0, 1, ObjectClass.melee_ammo, PlanetSideGUID(3279), 0, AmmoBoxData())) ::
|
2017-03-19 01:04:20 +00:00
|
|
|
Nil
|
|
|
|
|
),
|
|
|
|
|
DrawnSlot.Rifle1
|
|
|
|
|
)
|
|
|
|
|
val msg = ObjectCreateMessage(ObjectClass.avatar, PlanetSideGUID(3902), obj)
|
|
|
|
|
val pkt = PacketCoding.EncodePacket(msg).require.toByteVector
|
|
|
|
|
|
|
|
|
|
val pkt_bitv = pkt.toBitVector
|
|
|
|
|
val ori_bitv = string_character.toBitVector
|
|
|
|
|
pkt_bitv.take(452) mustEqual ori_bitv.take(452) //skip 126
|
|
|
|
|
pkt_bitv.drop(578).take(438) mustEqual ori_bitv.drop(578).take(438) //skip 2
|
|
|
|
|
pkt_bitv.drop(1018).take(17) mustEqual ori_bitv.drop(1018).take(17) //skip 11
|
|
|
|
|
pkt_bitv.drop(1046).take(147) mustEqual ori_bitv.drop(1046).take(147) //skip 3
|
|
|
|
|
pkt_bitv.drop(1196) mustEqual ori_bitv.drop(1196)
|
|
|
|
|
//TODO work on CharacterData to make this pass as a single stream
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
"encode (character, backpack)" in {
|
|
|
|
|
val obj = CharacterData(
|
|
|
|
|
CharacterAppearanceData(
|
2017-07-05 01:44:24 +00:00
|
|
|
PlacementData(4629.8906f, 6316.4453f, 54.734375f, 0f, 0f, 126.5625f),
|
2017-03-19 01:04:20 +00:00
|
|
|
BasicCharacterData(
|
|
|
|
|
"Angello",
|
|
|
|
|
PlanetSideEmpire.VS,
|
|
|
|
|
CharacterGender.Male,
|
|
|
|
|
10,
|
|
|
|
|
2
|
|
|
|
|
),
|
|
|
|
|
0,
|
|
|
|
|
false,
|
|
|
|
|
false,
|
|
|
|
|
ExoSuitType.MAX,
|
|
|
|
|
"Original District",
|
|
|
|
|
23,
|
|
|
|
|
true, //backpack
|
2017-07-05 01:44:24 +00:00
|
|
|
0f, 180.0f,
|
2017-03-19 01:04:20 +00:00
|
|
|
false,
|
|
|
|
|
GrenadeState.None,
|
|
|
|
|
false, false, false,
|
2017-05-07 05:34:55 +00:00
|
|
|
RibbonBars(
|
2017-09-09 00:12:36 +00:00
|
|
|
MeritCommendation.Jacking2,
|
|
|
|
|
MeritCommendation.ScavengerVS1,
|
2017-05-07 05:34:55 +00:00
|
|
|
MeritCommendation.AMSSupport4,
|
2017-09-09 00:12:36 +00:00
|
|
|
MeritCommendation.SixYearVS
|
2017-05-07 05:34:55 +00:00
|
|
|
)
|
2017-03-19 01:04:20 +00:00
|
|
|
),
|
|
|
|
|
0, 0,
|
|
|
|
|
UniformStyle.ThirdUpgrade,
|
|
|
|
|
2,
|
|
|
|
|
None,
|
|
|
|
|
Some(Cosmetics(true, true, true, true, false)),
|
|
|
|
|
None,
|
|
|
|
|
DrawnSlot.Pistol1
|
|
|
|
|
)
|
|
|
|
|
val msg = ObjectCreateMessage(ObjectClass.avatar, PlanetSideGUID(3380), obj)
|
2017-03-04 15:06:10 +00:00
|
|
|
val pkt = PacketCoding.EncodePacket(msg).require.toByteVector
|
|
|
|
|
|
2017-03-19 01:04:20 +00:00
|
|
|
val pkt_bitv = pkt.toBitVector
|
|
|
|
|
val ori_bitv = string_character_backpack.toBitVector
|
|
|
|
|
pkt_bitv.take(300) mustEqual ori_bitv.take(300) //skip 2
|
|
|
|
|
pkt_bitv.drop(302).take(14) mustEqual ori_bitv.drop(302).take(14) //skip 126
|
2017-07-05 01:44:24 +00:00
|
|
|
pkt_bitv.drop(442).take(305) mustEqual ori_bitv.drop(442).take(305) //skip 1
|
|
|
|
|
pkt_bitv.drop(748).take(9) mustEqual ori_bitv.drop(748).take(9) // skip 2
|
|
|
|
|
pkt_bitv.drop(759).take(157) mustEqual ori_bitv.drop(759).take(157) //skip 1
|
2017-03-19 01:04:20 +00:00
|
|
|
pkt_bitv.drop(917) mustEqual ori_bitv.drop(917)
|
|
|
|
|
//TODO work on CharacterData to make this pass as a single stream
|
2017-03-04 15:06:10 +00:00
|
|
|
}
|
|
|
|
|
}
|