mirror of
https://github.com/psforever/PSF-LoginServer.git
synced 2026-01-19 18:44:45 +00:00
sorry med app, home lock benefits
This commit is contained in:
parent
73c9c5a4a0
commit
20168cac27
|
|
@ -60,10 +60,6 @@ add_property maelstrom equiptime 1000
|
|||
add_property maelstrom holstertime 1000
|
||||
add_property magcutter equiptime 250
|
||||
add_property magcutter holstertime 250
|
||||
add_property medicalapplicator equiptime 500
|
||||
add_property medicalapplicator holstertime 500
|
||||
add_property medicalapplicator firemode0_refiretime 500
|
||||
add_property medicalapplicator firemode1_refiretime 500
|
||||
add_property mini_chaingun equiptime 750
|
||||
add_property mini_chaingun holstertime 750
|
||||
add_property nano_dispenser equiptime 750
|
||||
|
|
|
|||
|
|
@ -150,6 +150,11 @@ object MiddlewareActor {
|
|||
packet.isInstanceOf[ChatMsg]
|
||||
}
|
||||
|
||||
/** `PropertyOverrideMessage` ptsd from other large packets causing issues when bundled */
|
||||
private def propertyOverrideMessageGuard(packet: PlanetSidePacket): Boolean = {
|
||||
packet.isInstanceOf[PropertyOverrideMessage]
|
||||
}
|
||||
|
||||
/**
|
||||
* A function for blanking tasks related to inbound packet resolution.
|
||||
* Do nothing.
|
||||
|
|
@ -259,7 +264,8 @@ class MiddlewareActor(
|
|||
MiddlewareActor.keepAliveMessageGuard,
|
||||
MiddlewareActor.characterInfoMessageGuard,
|
||||
MiddlewareActor.squadDetailDefinitionMessageGuard,
|
||||
MiddlewareActor.chatMsgGuard
|
||||
MiddlewareActor.chatMsgGuard,
|
||||
MiddlewareActor.propertyOverrideMessageGuard
|
||||
)
|
||||
|
||||
private val smpHistoryLength: Int = 100
|
||||
|
|
|
|||
|
|
@ -2218,12 +2218,12 @@ class AvatarActor(
|
|||
.Holsters()
|
||||
.foreach(holster =>
|
||||
holster.Equipment match {
|
||||
case Some(tool: Tool) if tool.Definition == GlobalDefinitions.medicalapplicator =>
|
||||
/*case Some(tool: Tool) if tool.Definition == GlobalDefinitions.medicalapplicator =>
|
||||
//todo fix so player may hold medapp when loading the zone (client crash)
|
||||
val item = SimpleItem(GlobalDefinitions.flail_targeting_laser)
|
||||
holster.Equipment = None
|
||||
holster.Equipment = item
|
||||
item.GUID = PlanetSideGUID(gen.getAndIncrement)
|
||||
item.GUID = PlanetSideGUID(gen.getAndIncrement)*/
|
||||
case Some(tool: Tool) =>
|
||||
tool.AmmoSlots.foreach(slot => {
|
||||
slot.Box.GUID = PlanetSideGUID(gen.getAndIncrement)
|
||||
|
|
|
|||
|
|
@ -12,7 +12,7 @@ import net.psforever.actors.session.{AvatarActor, SessionActor}
|
|||
import net.psforever.actors.zone.ZoneActor
|
||||
import net.psforever.objects.LivePlayerList
|
||||
import net.psforever.objects.sourcing.PlayerSource
|
||||
import net.psforever.objects.zones.ZoneInfo
|
||||
import net.psforever.objects.zones.{Zone, ZoneInfo}
|
||||
import net.psforever.packet.game.SetChatFilterMessage
|
||||
import net.psforever.services.chat.{DefaultChannel, OutfitChannel, SquadChannel}
|
||||
import net.psforever.services.local.{LocalAction, LocalServiceMessage}
|
||||
|
|
@ -20,7 +20,7 @@ import net.psforever.services.teamwork.{SquadResponse, SquadService, SquadServic
|
|||
import net.psforever.types.ChatMessageType.CMT_QUIT
|
||||
import org.log4s.Logger
|
||||
|
||||
import java.util.concurrent.{Executors, TimeUnit}
|
||||
import java.util.concurrent.{Executors, ScheduledFuture, TimeUnit}
|
||||
import scala.annotation.unused
|
||||
import scala.collection.{Seq, mutable}
|
||||
import scala.concurrent.ExecutionContext.Implicits.global
|
||||
|
|
@ -368,7 +368,9 @@ class ChatOperations(
|
|||
case (Some(buildings), Some(faction), Some(_)) =>
|
||||
//TODO implement timer
|
||||
//schedule processing of buildings with a delay
|
||||
processBuildingsWithDelay(buildings, faction, 1000) //delay of 1000ms between each building operation
|
||||
processBuildingsWithDelay(buildings, faction, 1000) { zone =>
|
||||
zone.actor ! ZoneActor.AssignLockedBy(zone, notifyPlayers=true)
|
||||
}
|
||||
true
|
||||
case _ =>
|
||||
false
|
||||
|
|
@ -379,30 +381,30 @@ class ChatOperations(
|
|||
buildings: Seq[Building],
|
||||
faction: PlanetSideEmpire.Value,
|
||||
delayMillis: Long
|
||||
): Unit = {
|
||||
val buildingIterator = buildings.iterator
|
||||
scheduler.scheduleAtFixedRate(
|
||||
)(onComplete: Zone => Unit): Unit = {
|
||||
val buildingsToProcess = buildings.filter(b => b.CaptureTerminal.isDefined && b.Faction != faction)
|
||||
val iterator = buildingsToProcess.iterator
|
||||
val zone = buildings.head.Zone
|
||||
var handle: ScheduledFuture[_] = null
|
||||
handle = scheduler.scheduleAtFixedRate(
|
||||
() => {
|
||||
if (buildingIterator.hasNext) {
|
||||
val building = buildingIterator.next()
|
||||
if (iterator.hasNext) {
|
||||
val building = iterator.next()
|
||||
val terminal = building.CaptureTerminal.get
|
||||
val zone = building.Zone
|
||||
val zoneActor = zone.actor
|
||||
val buildingActor = building.Actor
|
||||
//clear any previous hack
|
||||
if (building.CaptureTerminalIsHacked) {
|
||||
zone.LocalEvents ! LocalServiceMessage(
|
||||
zone.id,
|
||||
LocalAction.ResecureCaptureTerminal(terminal, PlayerSource.Nobody)
|
||||
)
|
||||
}
|
||||
//push any updates this might cause
|
||||
zoneActor ! ZoneActor.ZoneMapUpdate()
|
||||
//convert faction affiliation
|
||||
buildingActor ! BuildingActor.SetFaction(faction)
|
||||
buildingActor ! BuildingActor.AmenityStateChange(terminal, Some(false))
|
||||
//push for map updates again
|
||||
building.Actor ! BuildingActor.SetFaction(faction)
|
||||
building.Actor ! BuildingActor.AmenityStateChange(terminal, Some(false))
|
||||
zoneActor ! ZoneActor.ZoneMapUpdate()
|
||||
} else {
|
||||
handle.cancel(false)
|
||||
onComplete(zone)
|
||||
}
|
||||
},
|
||||
0,
|
||||
|
|
|
|||
|
|
@ -54,7 +54,7 @@ import net.psforever.objects.serverobject.turret.FacilityTurret
|
|||
import net.psforever.objects.vehicles._
|
||||
import net.psforever.objects.zones.{Zone, ZoneHotSpotProjector, Zoning}
|
||||
import net.psforever.objects._
|
||||
import net.psforever.packet.game.{AvatarAwardMessage, AvatarSearchCriteriaMessage, AvatarStatisticsMessage, AwardCompletion, BindPlayerMessage, BindStatus, CargoMountPointStatusMessage, ChangeShortcutBankMessage, ChatChannel, CreateShortcutMessage, DroppodFreefallingMessage, LoadMapMessage, ObjectCreateDetailedMessage, ObjectDeleteMessage, PlanetsideStringAttributeMessage, PlayerStateShiftMessage, SetChatFilterMessage, SetCurrentAvatarMessage, ShiftState}
|
||||
import net.psforever.packet.game.{AvatarAwardMessage, AvatarSearchCriteriaMessage, AvatarStatisticsMessage, AwardCompletion, BindPlayerMessage, BindStatus, CargoMountPointStatusMessage, ChangeShortcutBankMessage, ChatChannel, CreateShortcutMessage, DroppodFreefallingMessage, LoadMapMessage, ObjectCreateDetailedMessage, ObjectDeleteMessage, PlayerStateShiftMessage, SetChatFilterMessage, SetCurrentAvatarMessage, ShiftState}
|
||||
import net.psforever.packet.game.{AvatarDeadStateMessage, BroadcastWarpgateUpdateMessage, ChatMsg, ContinentalLockUpdateMessage, DeadState, DensityLevelUpdateMessage, DeployRequestMessage, DeployableInfo, DeployableObjectsInfoMessage, DeploymentAction, DisconnectMessage, DroppodError, DroppodLaunchResponseMessage, FriendsResponse, GenericObjectActionMessage, GenericObjectStateMsg, HotSpotUpdateMessage, ObjectAttachMessage, ObjectCreateMessage, PlanetsideAttributeEnum, PlanetsideAttributeMessage, PropertyOverrideMessage, ReplicationStreamMessage, SetEmpireMessage, TimeOfDayMessage, TriggerEffectMessage, ZoneForcedCavernConnectionsMessage, ZoneInfoMessage, ZoneLockInfoMessage, ZonePopulationUpdateMessage, HotSpotInfo => PacketHotSpotInfo}
|
||||
import net.psforever.packet.game.{BeginZoningMessage, DroppodLaunchRequestMessage, ReleaseAvatarRequestMessage, SpawnRequestMessage, WarpgateRequest}
|
||||
import net.psforever.packet.game.DeathStatistic
|
||||
|
|
@ -559,18 +559,12 @@ class ZoningOperations(
|
|||
val popTR = zone.Players.count(_.faction == PlanetSideEmpire.TR)
|
||||
val popNC = zone.Players.count(_.faction == PlanetSideEmpire.NC)
|
||||
val popVS = zone.Players.count(_.faction == PlanetSideEmpire.VS)
|
||||
|
||||
zone.Buildings.foreach({ case (_, building) => initBuilding(continentNumber, building.MapId, building) })
|
||||
sendResponse(ZonePopulationUpdateMessage(continentNumber, 414, 138, popTR, 138, popNC, 138, popVS, 138, popBO))
|
||||
//TODO should actually not claim that the sanctuary or VR zones are locked by their respective empire
|
||||
if (continentNumber == 11)
|
||||
sendResponse(ContinentalLockUpdateMessage(continentNumber, PlanetSideEmpire.NC))
|
||||
else if (continentNumber == 12)
|
||||
sendResponse(ContinentalLockUpdateMessage(continentNumber, PlanetSideEmpire.TR))
|
||||
else if (continentNumber == 13)
|
||||
sendResponse(ContinentalLockUpdateMessage(continentNumber, PlanetSideEmpire.VS))
|
||||
else
|
||||
if (continentNumber == 11 || continentNumber == 12 || continentNumber == 13)
|
||||
sendResponse(ContinentalLockUpdateMessage(continentNumber, PlanetSideEmpire.NEUTRAL))
|
||||
else
|
||||
sendResponse(ContinentalLockUpdateMessage(continentNumber, zone.lockedBy))
|
||||
//CaptureFlagUpdateMessage()
|
||||
//VanuModuleUpdateMessage()
|
||||
//ModuleLimitsMessage()
|
||||
|
|
@ -642,6 +636,8 @@ class ZoningOperations(
|
|||
)
|
||||
}
|
||||
}
|
||||
player.Zone.ApplyHomeLockBenefitsOnLogin(player)
|
||||
SessionOutfitHandlers.HandleLoginOutfitCheck(player, sessionLogic)
|
||||
}
|
||||
|
||||
def handleZoneResponse(foundZone: Zone): Unit = {
|
||||
|
|
@ -2094,7 +2090,7 @@ class ZoningOperations(
|
|||
session = session.copy(player = p, avatar = a)
|
||||
sessionLogic.persist()
|
||||
setupAvatarFunc = AvatarRejoin
|
||||
dropMedicalApplicators(p)
|
||||
//dropMedicalApplicators(p)
|
||||
avatarActor ! AvatarActor.ReplaceAvatar(a)
|
||||
avatarLoginResponse(a)
|
||||
|
||||
|
|
@ -2104,7 +2100,7 @@ class ZoningOperations(
|
|||
deadState = DeadState.Dead
|
||||
session = session.copy(player = p, avatar = a)
|
||||
sessionLogic.persist()
|
||||
dropMedicalApplicators(p)
|
||||
//dropMedicalApplicators(p)
|
||||
HandleReleaseAvatar(p, inZone)
|
||||
avatarActor ! AvatarActor.ReplaceAvatar(a)
|
||||
avatarLoginResponse(a)
|
||||
|
|
@ -2548,9 +2544,6 @@ class ZoningOperations(
|
|||
sessionLogic.general.toggleTeleportSystem(obj, TelepadLike.AppraiseTeleportationSystem(obj, continent))
|
||||
}
|
||||
}
|
||||
if (player.outfit_id == 0) {
|
||||
SessionOutfitHandlers.HandleLoginOutfitCheck(player, sessionLogic)
|
||||
}
|
||||
/*make weather happen
|
||||
sendResponse(WeatherMessage(List(),List(
|
||||
StormInfo(Vector3(0.1f, 0.15f, 0.0f), 240, 217),
|
||||
|
|
@ -2674,7 +2667,6 @@ class ZoningOperations(
|
|||
log.debug(s"AvatarRejoin: ${player.Name} - $guid -> $data")
|
||||
}
|
||||
setupAvatarFunc = AvatarCreate
|
||||
SessionOutfitHandlers.HandleLoginOutfitCheck(player, sessionLogic)
|
||||
/*make weather happen
|
||||
sendResponse(WeatherMessage(List(),List(
|
||||
StormInfo(Vector3(0.1f, 0.15f, 0.0f), 240, 217),
|
||||
|
|
|
|||
|
|
@ -8,6 +8,8 @@ import net.psforever.actors.commands.NtuCommand
|
|||
import net.psforever.actors.zone.building._
|
||||
import net.psforever.objects.serverobject.structures.{Amenity, Building, StructureType, WarpGate}
|
||||
import net.psforever.objects.zones.Zone
|
||||
import net.psforever.packet.PlanetSideGamePacket
|
||||
import net.psforever.packet.game.ContinentalLockUpdateMessage
|
||||
import net.psforever.persistence
|
||||
import net.psforever.services.galaxy.{GalaxyAction, GalaxyServiceMessage}
|
||||
import net.psforever.services.local.{LocalAction, LocalServiceMessage}
|
||||
|
|
@ -76,6 +78,9 @@ object BuildingActor {
|
|||
|
||||
final case class DensityLevelUpdate(building: Building) extends Command
|
||||
|
||||
final case class ContinentalLock(zone: Zone) extends Command
|
||||
|
||||
final case class HomeLockBenefits(msg: PlanetSideGamePacket) extends Command
|
||||
/**
|
||||
* Set a facility affiliated to one faction to be affiliated to a different faction.
|
||||
* @param details building and event system references
|
||||
|
|
@ -252,6 +257,14 @@ class BuildingActor(
|
|||
case DensityLevelUpdate(building) =>
|
||||
details.galaxyService ! GalaxyServiceMessage(GalaxyAction.SendResponse(details.building.densityLevelUpdateMessage(building)))
|
||||
Behaviors.same
|
||||
|
||||
case ContinentalLock(zone) =>
|
||||
details.galaxyService ! GalaxyServiceMessage(GalaxyAction.SendResponse(ContinentalLockUpdateMessage(zone.Number, zone.lockedBy)))
|
||||
Behaviors.same
|
||||
|
||||
case HomeLockBenefits(msg) =>
|
||||
details.galaxyService ! GalaxyServiceMessage(GalaxyAction.SendResponse(msg))
|
||||
Behaviors.same
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -78,6 +78,8 @@ object ZoneActor {
|
|||
final case class RewardThisDeath(entity: PlanetSideGameObject with FactionAffinity with InGameHistory) extends Command
|
||||
|
||||
final case class RewardOurSupporters(target: SourceEntry, history: Iterable[InGameActivity], kill: Kill, bep: Long) extends Command
|
||||
|
||||
final case class AssignLockedBy(zone: Zone, notifyPlayers: Boolean) extends Command
|
||||
}
|
||||
|
||||
class ZoneActor(
|
||||
|
|
@ -115,6 +117,7 @@ class ZoneActor(
|
|||
// TODO this happens during testing, need a way to not always persist during tests
|
||||
}
|
||||
}
|
||||
AssignLockedBy(zone, notifyPlayers=false)
|
||||
case Failure(e) => log.error(e.getMessage)
|
||||
}
|
||||
|
||||
|
|
@ -187,10 +190,29 @@ class ZoneActor(
|
|||
.values
|
||||
.foreach(_.Actor ! BuildingActor.MapUpdate())
|
||||
Behaviors.same
|
||||
|
||||
case AssignLockedBy(zone, notifyPlayers) =>
|
||||
AssignLockedBy(zone, notifyPlayers)
|
||||
Behaviors.same
|
||||
}
|
||||
.receiveSignal {
|
||||
case (_, PostStop) =>
|
||||
Behaviors.same
|
||||
}
|
||||
}
|
||||
|
||||
def AssignLockedBy(zone: Zone, notifyPlayers: Boolean): Unit = {
|
||||
val buildings = zone.Buildings.values
|
||||
val facilities = buildings.filter(_.BuildingType == StructureType.Facility).toSeq
|
||||
val factions = facilities.map(_.Faction).toSet
|
||||
zone.lockedBy =
|
||||
if (factions.size == 1) factions.head
|
||||
else PlanetSideEmpire.NEUTRAL
|
||||
zone.benefitRecipient =
|
||||
if (facilities.nonEmpty && facilities.forall(_.Faction == facilities.head.Faction))
|
||||
facilities.head.Faction
|
||||
else
|
||||
zone.benefitRecipient
|
||||
if (facilities.nonEmpty && notifyPlayers) { zone.NotifyContinentalLockBenefits(zone, facilities.head) }
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -32,9 +32,9 @@ import scalax.collection.GraphEdge._
|
|||
import scala.util.Try
|
||||
import akka.actor.typed
|
||||
import net.psforever.actors.session.AvatarActor
|
||||
import net.psforever.actors.zone.ZoneActor
|
||||
import net.psforever.actors.zone.{BuildingActor, ZoneActor}
|
||||
import net.psforever.actors.zone.building.WarpGateLogic
|
||||
import net.psforever.objects.avatar.Avatar
|
||||
import net.psforever.objects.avatar.{Avatar, PlayerControl}
|
||||
import net.psforever.objects.definition.ObjectDefinition
|
||||
import net.psforever.objects.geometry.d3.VolumetricGeometry
|
||||
import net.psforever.objects.guid.pool.NumberPool
|
||||
|
|
@ -56,6 +56,7 @@ import net.psforever.objects.vital.interaction.{DamageInteraction, DamageResult}
|
|||
import net.psforever.objects.vital.prop.DamageWithPosition
|
||||
import net.psforever.objects.vital.Vitality
|
||||
import net.psforever.objects.zones.blockmap.{BlockMap, SectorPopulation}
|
||||
import net.psforever.packet.game.PropertyOverrideMessage
|
||||
import net.psforever.services.Service
|
||||
import net.psforever.zones.Zones
|
||||
|
||||
|
|
@ -194,6 +195,16 @@ class Zone(val id: String, val map: ZoneMap, zoneNumber: Int) {
|
|||
*/
|
||||
private var zoneInitialized: Promise[Boolean] = Promise[Boolean]()
|
||||
|
||||
/**
|
||||
* For ContinentalLockUpdateMessage
|
||||
*/
|
||||
var lockedBy: PlanetSideEmpire.Value = PlanetSideEmpire.NEUTRAL
|
||||
|
||||
/**
|
||||
* Used with lockedBy, but persists until another empire locks the cont
|
||||
*/
|
||||
var benefitRecipient: PlanetSideEmpire.Value = PlanetSideEmpire.NEUTRAL
|
||||
|
||||
/**
|
||||
* When the zone has completed initializing, this will be the future.
|
||||
* @see `init(ActorContext)`
|
||||
|
|
@ -639,6 +650,79 @@ class Zone(val id: String, val map: ZoneMap, zoneNumber: Int) {
|
|||
}
|
||||
output.toList
|
||||
}
|
||||
|
||||
def NotifyContinentalLockBenefits(zone: Zone, building: Building): Unit = {
|
||||
building.Actor ! BuildingActor.ContinentalLock(zone)
|
||||
ApplyHomeLockBenefits(building)
|
||||
}
|
||||
|
||||
def ApplyHomeLockBenefits(building: Building): Unit = {
|
||||
val homeSets: Map[PlanetSideEmpire.Value, Set[Int]] = Map(
|
||||
PlanetSideEmpire.TR -> Set(1, 2),
|
||||
PlanetSideEmpire.VS -> Set(5, 6),
|
||||
PlanetSideEmpire.NC -> Set(7, 10)
|
||||
)
|
||||
val homePerks: Map[PlanetSideEmpire.Value, String] = Map(
|
||||
PlanetSideEmpire.TR -> "battlewagon prowler threemanheavybuggy",
|
||||
PlanetSideEmpire.VS -> "magrider twomanhoverbuggy aurora",
|
||||
PlanetSideEmpire.NC -> "thunderer twomanheavybuggy vanguard"
|
||||
)
|
||||
|
||||
def isLockedBy(homeSet: Set[Int], empire: PlanetSideEmpire.Value): Boolean =
|
||||
Zones.zones.filter(z => homeSet.contains(z.Number)).forall(_.benefitRecipient == empire)
|
||||
|
||||
val perks: Map[PlanetSideEmpire.Value, String] =
|
||||
PlanetSideEmpire.values.map { empire =>
|
||||
val empirePerks = homeSets.collect {
|
||||
case (owner, zoneSet) if owner != empire && isLockedBy(zoneSet, empire) =>
|
||||
homePerks(owner)
|
||||
}
|
||||
empire -> empirePerks.mkString(" ")
|
||||
}.toMap
|
||||
|
||||
if (perks.values.forall(_.isEmpty)) {/*do nothing*/}
|
||||
else {
|
||||
val msg = PropertyOverrideMessage(List(PropertyOverrideMessage.GamePropertyScope(0, List(PropertyOverrideMessage.GamePropertyTarget(343,
|
||||
List(PropertyOverrideMessage.GameProperty("purchase_exempt_vs", perks(PlanetSideEmpire.VS)),
|
||||
PropertyOverrideMessage.GameProperty("purchase_exempt_tr", perks(PlanetSideEmpire.TR)),
|
||||
PropertyOverrideMessage.GameProperty("purchase_exempt_nc", perks(PlanetSideEmpire.NC))))))))
|
||||
building.Actor ! BuildingActor.HomeLockBenefits(msg)
|
||||
}
|
||||
}
|
||||
|
||||
def ApplyHomeLockBenefitsOnLogin(player: Player): Unit = {
|
||||
val homeSets: Map[PlanetSideEmpire.Value, Set[Int]] = Map(
|
||||
PlanetSideEmpire.TR -> Set(1, 2),
|
||||
PlanetSideEmpire.VS -> Set(5, 6),
|
||||
PlanetSideEmpire.NC -> Set(7, 10)
|
||||
)
|
||||
val homePerks: Map[PlanetSideEmpire.Value, String] = Map(
|
||||
PlanetSideEmpire.TR -> "battlewagon prowler threemanheavybuggy",
|
||||
PlanetSideEmpire.VS -> "magrider twomanhoverbuggy aurora",
|
||||
PlanetSideEmpire.NC -> "thunderer twomanheavybuggy vanguard"
|
||||
)
|
||||
|
||||
def isLockedBy(homeSet: Set[Int], empire: PlanetSideEmpire.Value): Boolean =
|
||||
Zones.zones.filter(z => homeSet.contains(z.Number)).forall(_.benefitRecipient == empire)
|
||||
|
||||
val perks: Map[PlanetSideEmpire.Value, String] =
|
||||
PlanetSideEmpire.values.map { empire =>
|
||||
val empirePerks = homeSets.collect {
|
||||
case (owner, zoneSet) if owner != empire && isLockedBy(zoneSet, empire) =>
|
||||
homePerks(owner)
|
||||
}
|
||||
empire -> empirePerks.mkString(" ")
|
||||
}.toMap
|
||||
|
||||
if (perks.values.forall(_.isEmpty)) {/*do nothing*/}
|
||||
else {
|
||||
val msg = PropertyOverrideMessage(List(PropertyOverrideMessage.GamePropertyScope(0, List(PropertyOverrideMessage.GamePropertyTarget(343,
|
||||
List(PropertyOverrideMessage.GameProperty("purchase_exempt_vs", perks(PlanetSideEmpire.VS)),
|
||||
PropertyOverrideMessage.GameProperty("purchase_exempt_tr", perks(PlanetSideEmpire.TR)),
|
||||
PropertyOverrideMessage.GameProperty("purchase_exempt_nc", perks(PlanetSideEmpire.NC))))))))
|
||||
PlayerControl.sendResponse(player.Zone, player.Name, msg)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
|
|
|
|||
|
|
@ -275,19 +275,27 @@ class HackCaptureActor extends Actor {
|
|||
.collect { case p if p.Faction == hackedByFaction =>
|
||||
events ! LocalServiceMessage(p.Name, msg)
|
||||
}
|
||||
val zoneBases = building.Zone.Buildings.filter(base =>
|
||||
base._2.BuildingType == StructureType.Facility)
|
||||
val ownedBases = building.Zone.Buildings.filter(base =>
|
||||
base._2.BuildingType == StructureType.Facility && base._2.Faction == hackedByFaction
|
||||
&& base._2.GUID != building.GUID)
|
||||
val zoneTowers = building.Zone.Buildings.filter(tower =>
|
||||
tower._2.BuildingType == StructureType.Tower && tower._2.Faction != hackedByFaction)
|
||||
// All major facilities in zone are now owned by the hacking faction. Capture all towers in the zone
|
||||
// Base that was just hacked is not counted (hence the size - 1) because it wasn't always in ownedBases (async?)
|
||||
if (zoneBases.size - 1 == ownedBases.size && zoneTowers.nonEmpty)
|
||||
{
|
||||
processBuildingsWithDelay(zoneTowers.values.toSeq, hackedByFaction, 1000)
|
||||
val buildings = building.Zone.Buildings.values
|
||||
val hackedBaseId = building.GUID
|
||||
val facilities = buildings.filter(_.BuildingType == StructureType.Facility).toSeq
|
||||
val ownedFacilities = facilities.filter(b =>
|
||||
b.Faction == hackedByFaction && b.GUID != hackedBaseId
|
||||
)
|
||||
val towersToCapture = buildings.filter(b =>
|
||||
b.BuildingType == StructureType.Tower && b.Faction != hackedByFaction
|
||||
).toSeq
|
||||
if (ownedFacilities.size == facilities.size - 1) {
|
||||
building.Zone.lockedBy = hackedByFaction
|
||||
building.Zone.benefitRecipient = hackedByFaction
|
||||
building.Zone.NotifyContinentalLockBenefits(building.Zone, building)
|
||||
if (towersToCapture.nonEmpty) {
|
||||
processBuildingsWithDelay(towersToCapture, hackedByFaction, 1000)
|
||||
}
|
||||
}
|
||||
else if (building.Zone.lockedBy != PlanetSideEmpire.NEUTRAL) {
|
||||
building.Zone.lockedBy = PlanetSideEmpire.NEUTRAL
|
||||
building.Zone.NotifyContinentalLockBenefits(building.Zone, building)
|
||||
}
|
||||
} else {
|
||||
log.info("Base hack completed, but base was out of NTU.")
|
||||
}
|
||||
|
|
|
|||
Loading…
Reference in a new issue