public string Execute(
            double chargePercent = 100,
            [CurrentCharacterIfNull] ICharacter character = null)
        {
            var chargeFraction = MathHelper.Clamp(chargePercent / 100, min: 0, max: 1);

            using var tempLandClaims = Api.Shared.GetTempList <ILogicObject>();
            LandClaimSystem.SharedGetAreasInBounds(
                new RectangleInt(character.TilePosition, (1, 1)),
                tempLandClaims,
                addGracePadding: false);

            var landClaim = tempLandClaims.AsList().FirstOrDefault();

            if (landClaim is null)
            {
                return("No power grid exist near " + character.Name);
            }

            var landClaimAreasGroup = LandClaimSystem.SharedGetLandClaimAreasGroup(landClaim);
            var powerGrid           = LandClaimAreasGroup.GetPrivateState(landClaimAreasGroup).PowerGrid;
            var powerGridState      = PowerGrid.GetPublicState(powerGrid);

            powerGridState.ElectricityAmount = powerGridState.ElectricityCapacity * chargeFraction;

            return($"Charge amount of the power grid modified to {chargeFraction * 100}%");
        }
Beispiel #2
0
        private static void ServerTransferAreasGroupToFactionOwnership(
            ILogicObject faction,
            ICharacter byCharacter,
            ILogicObject areasGroup)
        {
            var areas = LandClaimAreasGroup.GetPrivateState(areasGroup).ServerLandClaimsAreas;

            foreach (var area in areas)
            {
                ServerUnregisterArea(area);
            }

            var publicState = LandClaimAreasGroup.GetPublicState(areasGroup);

            publicState.ServerSetFaction(faction);

            var centerTilePosition
                = new Vector2Ushort(
                      (ushort)areas.Average(a => LandClaimArea.GetPublicState(a).LandClaimCenterTilePosition.X),
                      (ushort)areas.Average(a => LandClaimArea.GetPublicState(a).LandClaimCenterTilePosition.Y));

            Logger.Important(
                $"Transferred land claim areas group to the faction ownership: {areasGroup} at {centerTilePosition}");
            FactionSystem.ServerOnLandClaimExpanded(faction, centerTilePosition, byCharacter);

            foreach (var area in areas)
            {
                ServerRegisterArea(area);
            }
        }
Beispiel #3
0
        public static bool ServerIsVehicleInsideOwnerBase(IDynamicWorldObject vehicle)
        {
            var vehicleCurrentBase = LandClaimSystem.SharedGetLandClaimAreasGroup(vehicle.TilePosition);

            if (vehicleCurrentBase is null)
            {
                return(false);
            }

            var vehicleOwners = vehicle.GetPrivateState <VehiclePrivateState>().Owners;

            foreach (var area in LandClaimAreasGroup.GetPrivateState(vehicleCurrentBase)
                     .ServerLandClaimsAreas)
            {
                using var areaOwners = Api.Shared.WrapInTempList(
                          LandClaimArea.GetPrivateState(area)
                          .ServerGetLandOwners());

                foreach (var ownerName in vehicleOwners)
                {
                    if (areaOwners.Contains(ownerName))
                    {
                        return(true);
                    }
                }
            }

            return(false);
        }
Beispiel #4
0
        public static string ServerSetOwner(ushort x, ushort y, string newOwnerName)
        {
            using var tempList = Api.Shared.GetTempList <ILogicObject>();
            LandClaimSystem.SharedGetAreasInBounds(new RectangleInt(x, y, 1, 1), tempList, addGracePadding: false);

            var landClaimsModified = 0;

            foreach (var area in tempList.AsList())
            {
                var areasGroup = LandClaimSystem.SharedGetLandClaimAreasGroup(area);
                if (LandClaimAreasGroup.GetPublicState(areasGroup).ServerFaction is not null)
                {
                    // cannot change an owner of the faction land claim
                    continue;
                }

                var privateState = LandClaimArea.GetPrivateState(area);
                privateState.LandClaimFounder = newOwnerName;
                privateState.DirectLandOwners.Clear();
                privateState.DirectLandOwners.Add(newOwnerName);
                landClaimsModified++;
            }

            return($"Modified {landClaimsModified} land claims");
        }
Beispiel #5
0
        public static string SharedGetAreaOwnerFactionClanTag(ILogicObject area)
        {
            var areasGroup            = SharedGetLandClaimAreasGroup(area);
            var areasGroupPublicState = LandClaimAreasGroup.GetPublicState(areasGroup);

            return(areasGroupPublicState.FactionClanTag);
        }
Beispiel #6
0
        private static ILogicObject ServerGetOwningFaction(IWorldObject worldObject)
        {
            ILogicObject faction = null;

            if (worldObject is IStaticWorldObject staticWorldObject)
            {
                var areasGroup = LandClaimSystem.SharedGetLandClaimAreasGroup(staticWorldObject);
                if (areasGroup is null)
                {
                    throw new Exception(
                              "Cannot modify faction access mode for an object without a faction land claim area");
                }

                faction = LandClaimAreasGroup.GetPublicState(areasGroup).ServerFaction;
            }
            else if (worldObject.ProtoGameObject is IProtoVehicle)
            {
                var clanTag = worldObject.GetPublicState <VehiclePublicState>().ClanTag;
                if (string.IsNullOrEmpty(clanTag))
                {
                    throw new Exception("The vehicle doesn't belong to a faction: " + worldObject);
                }

                faction = FactionSystem.ServerGetFactionByClanTag(clanTag);
            }

            if (faction is null)
            {
                throw new Exception(
                          "Cannot modify faction access mode for an object without a faction land claim area");
            }

            return(faction);
        }
Beispiel #7
0
        private static void ServerResetDecayTimerForLandClaimAreasGroup(ILogicObject areasGroup)
        {
            var areasGroupPrivateState = LandClaimAreasGroup.GetPrivateState(areasGroup);
            var areasGroupPublicState  = LandClaimAreasGroup.GetPublicState(areasGroup);
            var areas = areasGroupPrivateState.ServerLandClaimsAreas;

            // TODO: it's better to move this code to another place as this property is used in several other places
            areasGroupPublicState.IsFounderDemoPlayer = ServerGetIsFounderDemoPlayer(areas);

            // reset the decay timer for all land claim buildings inside this areas group
            var decayDelayDuration = LandClaimSystem.ServerGetDecayDelayDurationForLandClaimAreas(
                areas,
                areasGroupPublicState.IsFounderDemoPlayer,
                out _);

            foreach (var area in areas)
            {
                var worldObject = LandClaimArea.GetPrivateState(area)
                                  .ServerLandClaimWorldObject;

                StructureDecaySystem.ServerResetDecayTimer(
                    worldObject.GetPrivateState <StructurePrivateState>(),
                    decayDelayDuration);
            }
        }
        public static bool ServerIsVehicleInsideOwnerBase(IDynamicWorldObject vehicle)
        {
            var vehicleCurrentBase = LandClaimSystem.SharedGetLandClaimAreasGroup(vehicle.TilePosition);

            if (vehicleCurrentBase == null)
            {
                return(false);
            }

            var vehicleOwners = vehicle.GetPrivateState <VehiclePrivateState>().Owners;

            foreach (var area in LandClaimAreasGroup.GetPrivateState(vehicleCurrentBase).ServerLandClaimsAreas)
            {
                var areaOwners = LandClaimArea.GetPrivateState(area).LandOwners;
                foreach (var ownerName in vehicleOwners)
                {
                    if (areaOwners.Contains(ownerName, StringComparer.Ordinal))
                    {
                        return(true);
                    }
                }
            }

            return(false);
        }
        private void RefreshSafeStorageAndPowerGrid()
        {
            var objectPublicState = this.landClaimWorldObject.GetPublicState <ObjectLandClaimPublicState>();
            var area                   = objectPublicState.LandClaimAreaObject;
            var areasGroup             = LandClaimArea.GetPublicState(area).LandClaimAreasGroup;
            var areasGroupPrivateState = LandClaimAreasGroup.GetPrivateState(areasGroup);

            // setup power grid
            var powerGrid = areasGroupPrivateState.PowerGrid;
            var oldViewModelPowerGridState = this.ViewModelPowerGridState;

            this.ViewModelPowerGridState = new ViewModelPowerGridState(PowerGrid.GetPublicState(powerGrid));
            oldViewModelPowerGridState?.Dispose();

            // setup safe storage
            this.DisposeViewModelItemsContainerExchange();

            this.ViewModelItemsContainerExchange = new ViewModelItemsContainerExchange(
                areasGroupPrivateState.ItemsContainer,
                callbackTakeAllItemsSuccess: () => { },
                enableShortcuts: this.IsSafeStorageAvailable)
            {
                IsContainerTitleVisible = false,
            };

            this.ViewModelItemsContainerExchange.Container.SlotsCountChanged
                += this.SafeStorageSlotsChangedHandler;

            this.ViewModelItemsContainerExchange.Container.ItemsReset
                += this.SafeStorageSlotsChangedHandler;
        }
        public static double SharedCalculateCooldownRemains(ILogicObject areasGroup)
        {
            var privateState = LandClaimAreasGroup.GetPrivateState(areasGroup);
            var time         = IsServer
                           ? Server.Game.FrameTime
                           : Client.CurrentGame.ServerFrameTimeApproximated;

            return(Math.Max(0, privateState.ShieldProtectionCooldownExpirationTime - time));
        }
Beispiel #11
0
        private void ServerRemote_TransferLandClaimToFactionOwnership(ILogicObject area)
        {
            var character  = ServerRemoteContext.Character;
            var areasGroup = SharedGetLandClaimAreasGroup(area);

            if (LandClaimAreasGroup.GetPublicState(areasGroup).ServerFaction is not null)
            {
                // already has a faction (and it's not possible to change the faction)
                Logger.Warning("The land claim areas group is already transferred to a faction.");
                return;
            }

            FactionSystem.ServerValidateHasAccessRights(character,
                                                        FactionMemberAccessRights.LandClaimManagement,
                                                        out var faction);

            var factionOwnedAreas = SharedEnumerateAllFactionAreas(FactionSystem.SharedGetClanTag(faction));
            var claimLimitRemains = FactionConstants.SharedGetFactionLandClaimsLimit(
                Faction.GetPublicState(faction).Level)
                                    - factionOwnedAreas.Count();

            claimLimitRemains -= LandClaimAreasGroup.GetPrivateState(areasGroup).ServerLandClaimsAreas.Count;
            if (claimLimitRemains < 0)
            {
                Logger.Warning(
                    "Cannot transfer land claims to the faction as it will exceed the land claims number limit");
                return;
            }

            Logger.Important("Will transfer land claims to the faction: after upgrade the remaining limit will be "
                             + claimLimitRemains);

            // verify user has access to the land claim
            var owner = ServerRemoteContext.Character;

            if (!Server.World.IsInPrivateScope(area, owner))
            {
                throw new Exception(
                          "Cannot interact with the land claim object as the area is not in private scope: "
                          + area);
            }

            if (!LandClaimArea.GetPrivateState(area).ServerGetLandOwners()
                .Contains(owner.Name))
            {
                throw new Exception("Player is not an owner of the land claim area");
            }

            ServerTransferAreasGroupToFactionOwnership(faction, character, areasGroup);

            var worldObject = InteractionCheckerSystem.SharedGetCurrentInteraction(character);

            InteractableWorldObjectHelper.ServerTryAbortInteraction(character, worldObject);
        }
Beispiel #12
0
        public static void ClientDeactivateShield(ILogicObject areasGroup)
        {
            var status = SharedGetShieldPublicStatus(areasGroup);

            if (status == ShieldProtectionStatus.Inactive)
            {
                Logger.Important("The shield is already inactive");
                return;
            }

            var stackPanel = new StackPanel();

            stackPanel.Children.Add(
                DialogWindow.CreateTextElement(
                    string.Format(CoreStrings.ShieldProtection_DeactivationNotes_Format,
                                  ClientTimeFormatHelper.FormatTimeDuration(
                                      SharedCooldownDuration,
                                      appendSeconds: false)),
                    TextAlignment.Left));

            var accessRight            = FactionMemberAccessRights.BaseShieldManagement;
            var areasGroupPublicState  = LandClaimAreasGroup.GetPublicState(areasGroup);
            var hasNoFactionPermission = !string.IsNullOrEmpty(areasGroupPublicState.FactionClanTag) &&
                                         !FactionSystem.ClientHasAccessRight(accessRight);

            if (hasNoFactionPermission)
            {
                var message = FactionSystem.ClientHasFaction
                                  ? string.Format(
                    CoreStrings.Faction_Permission_Required_Format,
                    accessRight.GetDescription())
                                  : CoreStrings.Faction_ErrorDontHaveFaction;

                var textElement = DialogWindow.CreateTextElement("[br]" + message,
                                                                 TextAlignment.Left);

                textElement.Foreground = Client.UI.GetApplicationResource <Brush>("BrushColorRed6");
                textElement.FontWeight = FontWeights.Bold;
                stackPanel.Children.Add(textElement);
            }

            var dialog = DialogWindow.ShowDialog(
                CoreStrings.ShieldProtection_Dialog_ConfirmDeactivation,
                stackPanel,
                okText: CoreStrings.ShieldProtection_Button_DeactivateShield,
                okAction: () => Instance.CallServer(_ => _.ServerRemote_DeactivateShield(areasGroup)),
                cancelAction: () => { },
                focusOnCancelButton: true);

            if (hasNoFactionPermission)
            {
                dialog.ButtonOk.IsEnabled = false;
            }
        }
Beispiel #13
0
        private static void ServerPlayerOnlineStateChangedHandler(ICharacter character, bool isOnline)
        {
            if (!isOnline)
            {
                return;
            }

            // notify about the ongoing raids on ally bases
            foreach (var pair in ServerNotifiedCharactersForAreasGroups)
            {
                if (!pair.Value.Contains(character))
                {
                    // this character was not notified for that mark
                    continue;
                }

                var mark        = pair.Key;
                var areasGroup  = mark.AreasGroup;
                var mapPosition = LandClaimSystem.SharedGetLandClaimGroupCenterPosition(areasGroup);
                var areas       = LandClaimAreasGroup.GetPrivateState(areasGroup)
                                  .ServerLandClaimsAreas;
                var faction = areas
                              .Select(LandClaimSystem.ServerGetLandOwnerFactionOrFounderFaction)
                              .FirstOrDefault(f => f is not null);
                if (faction is null)
                {
                    continue;
                }

                var isOwner = false;
                foreach (var area in areas)
                {
                    if (LandClaimSystem.ServerIsOwnedArea(area, character, requireFactionPermission: false))
                    {
                        isOwner = true;
                        break;
                    }
                }

                if (isOwner)
                {
                    // no need to notify
                    continue;
                }

                Instance.CallClient(character,
                                    _ => _.ClientRemote_AllyBaseUnderRaid(
                                        areasGroup.Id,
                                        mark.FactionMemberName,
                                        mark.ClanTag,
                                        mapPosition));
            }
        }
Beispiel #14
0
        public ViewModelShieldProtectionControl(ILogicObject areasGroup)
        {
            this.areasGroup   = areasGroup;
            this.privateState = LandClaimAreasGroup.GetPrivateState(areasGroup);
            this.publicState  = LandClaimAreasGroup.GetPublicState(areasGroup);

            this.privateState.ClientSubscribe(
                _ => _.ShieldProtectionCurrentChargeElectricity,
                _ =>
            {
                this.NotifyPropertyChanged(nameof(this.ElectricityAmount));
                this.NotifyPropertyChanged(nameof(this.CanActivateShield));
                this.NotifyPropertyChanged(nameof(this.HasFullCharge));
                this.UpdateCurrentDurations();
            },
                this);

            this.privateState.ClientSubscribe(
                _ => _.ShieldProtectionCooldownExpirationTime,
                _ => this.RefreshState(),
                this);

            this.publicState.ClientSubscribe(
                _ => _.ShieldActivationTime,
                _ => this.RefreshState(),
                this);

            this.publicState.ClientSubscribe(
                _ => _.Status,
                _ => this.RefreshState(),
                this);

            this.RefreshState();

            this.IsLandClaimInsideAnotherBase = LandClaimShieldProtectionHelper.SharedIsLandClaimInsideAnotherBase(
                areasGroup);

            FactionSystem.ClientCurrentFactionAccessRightsChanged += this.CurrentFactionAccessRightsChangedHandler;

            UpdateCurrentDurationsEverySecond();

            void UpdateCurrentDurationsEverySecond()
            {
                if (this.IsDisposed)
                {
                    return;
                }

                this.UpdateCurrentDurations();
                ClientTimersSystem.AddAction(1, UpdateCurrentDurationsEverySecond);
            }
        }
Beispiel #15
0
        private void ServerRemote_SetDirectAccessMode(IStaticWorldObject worldObject, WorldObjectDirectAccessMode mode)
        {
            var character = ServerRemoteContext.Character;

            if (!(worldObject.ProtoGameObject is IProtoObjectWithAccessMode protoObjectWithAccessMode))
            {
                throw new Exception("This world object doesn't have an access mode");
            }

            if (!protoObjectWithAccessMode.SharedCanInteract(character, worldObject, writeToLog: true))
            {
                return;
            }

            var areasGroup = LandClaimSystem.SharedGetLandClaimAreasGroup(worldObject);

            if (areasGroup is not null &&
                LandClaimAreasGroup.GetPublicState(areasGroup).ServerFaction is not null)
            {
                throw new Exception(
                          "Cannot modify direct access mode for an object within a faction land claim area");
            }

            if (!WorldObjectOwnersSystem.SharedIsOwner(character, worldObject) &&
                !CreativeModeSystem.SharedIsInCreativeMode(character))
            {
                throw new Exception("The player character is not an owner of " + worldObject);
            }

            if (mode == WorldObjectDirectAccessMode.Closed &&
                !protoObjectWithAccessMode.IsClosedAccessModeAvailable)
            {
                throw new Exception("Closed access mode is not supported for " + protoObjectWithAccessMode);
            }

            if (mode == WorldObjectDirectAccessMode.OpensToEveryone &&
                !protoObjectWithAccessMode.IsEveryoneAccessModeAvailable)
            {
                throw new Exception("Everyone access mode is not supported for " + protoObjectWithAccessMode);
            }

            var privateState = worldObject.GetPrivateState <IObjectWithAccessModePrivateState>();

            if (privateState.DirectAccessMode == mode)
            {
                return;
            }

            privateState.DirectAccessMode = mode;
            Logger.Info($"Direct access mode changed: {mode}; {worldObject}", character);
        }
Beispiel #16
0
            private static void ServerAreasGroupChangedHandler(
                ILogicObject area,
                [CanBeNull] ILogicObject areasGroupFrom,
                [CanBeNull] ILogicObject areasGroupTo)
            {
                var byMember = ServerPlayerCharacterCurrentActionStateContext.CurrentCharacter
                               ?? (ServerRemoteContext.IsRemoteCall
                                       ? ServerRemoteContext.Character
                                       : null);

                if (areasGroupTo is not null)
                {
                    var clanTag = LandClaimAreasGroup.GetPublicState(areasGroupTo).FactionClanTag;
                    if (string.IsNullOrEmpty(clanTag))
                    {
                        return;
                    }

                    var faction            = FactionSystem.ServerGetFactionByClanTag(clanTag);
                    var centerTilePosition = LandClaimArea.GetPublicState(area).LandClaimCenterTilePosition;
                    Logger.Important(
                        string.Format("Faction-owned land claim areas group expanded with a new claim area: {0} at {1}",
                                      areasGroupTo,
                                      centerTilePosition));

                    FactionSystem.ServerOnLandClaimExpanded(faction,
                                                            centerTilePosition,
                                                            byMember: byMember);
                }
                else if (areasGroupFrom is not null)
                {
                    var clanTag = LandClaimAreasGroup.GetPublicState(areasGroupFrom).FactionClanTag;
                    if (string.IsNullOrEmpty(clanTag))
                    {
                        return;
                    }

                    var faction            = FactionSystem.ServerGetFactionByClanTag(clanTag);
                    var centerTilePosition = LandClaimArea.GetPublicState(area).LandClaimCenterTilePosition;
                    Logger.Important(
                        string.Format("Faction-owned land claim areas group removed: {0} at {1}",
                                      areasGroupFrom,
                                      centerTilePosition));

                    FactionSystem.ServerOnLandClaimRemoved(faction,
                                                           centerTilePosition,
                                                           byMember: byMember);
                }
            }
Beispiel #17
0
        public static IEnumerable <ILogicObject> SharedEnumerateAllFactionAreas(string clanTag)
        {
            if (string.IsNullOrEmpty(clanTag))
            {
                throw new ArgumentNullException();
            }

            return(SharedEnumerateAllAreas()
                   .Where(a =>
            {
                var areasGroup = SharedGetLandClaimAreasGroup(a);
                var areasGroupPublicState = LandClaimAreasGroup.GetPublicState(areasGroup);
                return areasGroupPublicState.FactionClanTag == clanTag;
            }));
        }
Beispiel #18
0
            public void ReInitialize()
            {
                this.Reset();

                this.stateSubscriptionStorage = new StateSubscriptionStorage();

                var groupPublicState = LandClaimAreasGroup.GetPublicState(this.areasGroup);

                groupPublicState.ClientSubscribe(
                    o => o.LastRaidTime,
                    this.RefreshRaidedState,
                    this.stateSubscriptionStorage);

                this.RefreshRaidedState();
            }
Beispiel #19
0
            private static void ServerBaseBrokenHandler(ILogicObject areasGroup, List <ILogicObject> newAreaGroups)
            {
                var faction = LandClaimAreasGroup.GetPublicState(areasGroup).ServerFaction;

                if (faction is null)
                {
                    return;
                }

                foreach (var newAreasGroup in newAreaGroups)
                {
                    LandClaimAreasGroup.GetPublicState(newAreasGroup).ServerSetFaction(faction);
                }

                ServerRefreshFactionClaimAccess(faction);
            }
            public Controller(
                ILogicObject areasGroup,
                WorldMapController worldMapController)
            {
                this.areasGroup               = areasGroup;
                this.worldMapController       = worldMapController;
                this.stateSubscriptionStorage = new StateSubscriptionStorage();

                var groupPublicState = LandClaimAreasGroup.GetPublicState(areasGroup);

                groupPublicState.ClientSubscribe(
                    o => o.LastRaidTime,
                    this.RefreshRaidedState,
                    this.stateSubscriptionStorage);

                this.RefreshRaidedState();
            }
Beispiel #21
0
        private static void ServerRefreshLandClaimAreasGroup(ILogicObject areasGroup)
        {
            var areas = LandClaimAreasGroup.GetPrivateState(areasGroup).ServerLandClaimsAreas;

            foreach (var area in areas)
            {
                var areaBounds = LandClaimSystem.SharedGetLandClaimAreaBounds(area, addGracePadding: true);
                var owners     = LandClaimArea.GetPrivateState(area).LandOwners;

                foreach (var owner in owners)
                {
                    var character = Server.Characters.GetPlayerCharacter(owner);
                    if (character == null ||
                        !character.ServerIsOnline)
                    {
                        continue;
                    }

                    if (!areaBounds.Contains(character.TilePosition))
                    {
                        continue;
                    }

                    // the land claim area contains an online owner character
                    ServerResetDecayTimer();
                    return;
                }
            }

            // helper method to reset the decay timer for all land claim buildings inside this areas group
            void ServerResetDecayTimer()
            {
                var decayDelayDuration = LandClaimSystem.ServerGetDecayDelayDurationForLandClaimAreas(areas);

                foreach (var area in areas)
                {
                    var worldObject = LandClaimArea.GetPrivateState(area)
                                      .ServerLandClaimWorldObject;

                    StructureDecaySystem.ServerResetDecayTimer(
                        worldObject.GetPrivateState <StructurePrivateState>(),
                        decayDelayDuration);
                }
            }
        }
Beispiel #22
0
        private SetOwnersResult ServerRemote_SetOwners(IWorldObject worldObject, List <string> newOwners)
        {
            var maxOwners = worldObject.ProtoGameObject is IProtoObjectDoor
                                ? RateDoorOwnersMax.SharedValue
                                : byte.MaxValue;

            if (newOwners.Count > maxOwners)
            {
                return(SetOwnersResult.ErrorAccessListSizeLimitExceeded);
            }

            var character = ServerRemoteContext.Character;

            if (worldObject is IStaticWorldObject staticWorldObject)
            {
                if (!staticWorldObject.ProtoStaticWorldObject
                    .SharedCanInteract(character, worldObject, writeToLog: true))
                {
                    throw new Exception("Cannot interact with " + worldObject);
                }

                if (!SharedIsOwner(character, worldObject))
                {
                    throw new Exception("Not an owner");
                }

                var areasGroup = LandClaimSystem.SharedGetLandClaimAreasGroup(staticWorldObject);
                if (areasGroup is not null &&
                    LandClaimAreasGroup.GetPublicState(areasGroup).ServerFaction is not null)
                {
                    throw new Exception(
                              "Cannot modify owners list for an object within a faction land claim area");
                }
            }
            else // dynamic world object (a vehicle, etc)
            {
                if (!worldObject.ProtoWorldObject.SharedCanInteract(character, worldObject, writeToLog: false))
                {
                    throw new Exception("Cannot interact with " + worldObject);
                }
            }

            return(ServerSetOwners(worldObject, newOwners, byOwner: character));
        }
        public string Execute(
            ShieldProtectionStatus status,
            [CurrentCharacterIfNull] ICharacter character = null)
        {
            if (!LandClaimShieldProtectionConstants.SharedIsEnabled)
            {
                return("S.H.I.E.L.D. protection is not available");
            }

            if (status == ShieldProtectionStatus.Active)
            {
                status = ShieldProtectionStatus.Activating;
            }

            using var tempAreas = Api.Shared.GetTempList <ILogicObject>();
            LandClaimSystem.SharedGetAreasInBounds(
                new RectangleInt(character.TilePosition, (1, 1)),
                tempAreas,
                addGracePadding: false);

            var area = tempAreas.AsList().FirstOrDefault();

            if (area is null)
            {
                return("No base exist near " + character.Name);
            }

            var areasGroup = LandClaimSystem.SharedGetLandClaimAreasGroup(area);

            LandClaimShieldProtectionSystem.SharedGetShieldProtectionMaxStatsForBase(areasGroup,
                                                                                     out _,
                                                                                     out _);

            var privateState = LandClaimAreasGroup.GetPrivateState(areasGroup);

            privateState.ShieldProtectionCooldownExpirationTime = 0;

            var publicState = LandClaimAreasGroup.GetPublicState(areasGroup);

            publicState.Status = status;
            publicState.ShieldActivationTime = Server.Game.FrameTime;

            return($"Status of the S.H.I.E.L.D. changed to {status}.");
        }
Beispiel #24
0
        public static bool SharedIsOwner(ICharacter who, IWorldObject worldObject, out bool isFactionAccess)
        {
            isFactionAccess = false;

            switch (worldObject)
            {
            case IStaticWorldObject staticWorldObject:
            {
                var areasGroup = LandClaimSystem.SharedGetLandClaimAreasGroup(staticWorldObject);
                if (areasGroup is null ||
                    LandClaimAreasGroup.GetPublicState(areasGroup).FactionClanTag is not {
                    } clanTag ||
                    string.IsNullOrEmpty(clanTag))
                {
                    break;
                }

                // the static object is inside the faction-owned land claim,
                // verify permission
                isFactionAccess = true;
                return(SharedHasFactionAccessRights(who,
                                                    FactionMemberAccessRights.LandClaimManagement,
                                                    clanTag));
            }

            case IDynamicWorldObject when worldObject.ProtoGameObject is IProtoVehicle:
            {
                var clanTag = worldObject.GetPublicState <VehiclePublicState>().ClanTag;
                if (string.IsNullOrEmpty(clanTag))
                {
                    break;
                }

                // the vehicle is owned by faction
                // verify whether the character has the access right
                isFactionAccess = true;
                return(WorldObjectAccessModeSystem.SharedHasAccess(who, worldObject, writeToLog: true));
            }
            }

            return(SharedGetDirectOwners(worldObject).Contains(who.Name));
        }
        private static void Refresh()
        {
            var position   = ClientCurrentCharacterHelper.Character?.TilePosition ?? Vector2Ushort.Zero;
            var areasGroup = LandClaimSystem.SharedGetLandClaimAreasGroup(position, addGracePadding: false)
                             ?? LandClaimSystem.SharedGetLandClaimAreasGroup(position, addGracePadding: true);

            var lastRaidTime = areasGroup is not null
                                   ? LandClaimAreasGroup.GetPublicState(areasGroup).LastRaidTime ?? double.MinValue
                                   : double.MinValue;

            var time = Api.Client.CurrentGame.ServerFrameTimeRounded;
            var timeSinceRaidStart   = time - lastRaidTime;
            var timeRemainsToRaidEnd = LandClaimSystemConstants.SharedRaidBlockDurationSeconds - timeSinceRaidStart;

            timeRemainsToRaidEnd = Math.Max(timeRemainsToRaidEnd, 0);

            if (timeRemainsToRaidEnd <= 0)
            {
                // no raid here - hide notification
                currentNotification?.Hide(quick: true);
                currentNotification = null;
                return;
            }

            // raid here, display/update notification
            var text = GetNotificationText(timeRemainsToRaidEnd);

            if (currentNotification is not null &&
                !currentNotification.IsHiding)
            {
                currentNotification.Message = text;
                return;
            }

            currentNotification = NotificationSystem.ClientShowNotification(
                title: Notification_Title,
                message: text,
                autoHide: false,
                // TODO: add custom icon here, currently we're using a placeholder icon
                icon: Api.GetProtoEntity <ItemBombModern>().Icon,
                playSound: false);
        }
Beispiel #26
0
        public static bool SharedIsWorldObjectOwnedByFaction(IStaticWorldObject worldObject, out string clanTag)
        {
            var areasGroup = SharedGetLandClaimAreasGroup(worldObject);

            if (areasGroup is null)
            {
                clanTag = null;
                return(false);
            }

            var areasGroupPublicState = LandClaimAreasGroup.GetPublicState(areasGroup);

            clanTag = areasGroupPublicState.FactionClanTag;
            if (string.IsNullOrEmpty(clanTag))
            {
                clanTag = null;
                return(false);
            }

            return(true);
        }
Beispiel #27
0
        public static IReadOnlyList <string> SharedGetOwners(IWorldObject worldObject, out bool isFactionAccess)
        {
            isFactionAccess = false;

            switch (worldObject)
            {
            case IStaticWorldObject staticWorldObject:
            {
                var areasGroup = LandClaimSystem.SharedGetLandClaimAreasGroup(staticWorldObject);
                if (areasGroup is null ||
                    LandClaimAreasGroup.GetPublicState(areasGroup).FactionClanTag is not {
                    } clanTag ||
                    string.IsNullOrEmpty(clanTag))
                {
                    break;
                }

                // the static object is inside the faction-owned land claim,
                var faction = FactionSystem.ServerGetFactionByClanTag(clanTag);
                return(FactionSystem.ServerGetFactionMemberNames(faction).ToList());
            }

            case IDynamicWorldObject when worldObject.ProtoGameObject is IProtoVehicle:
            {
                var clanTag = worldObject.GetPublicState <VehiclePublicState>().ClanTag;
                if (string.IsNullOrEmpty(clanTag))
                {
                    break;
                }

                // the vehicle is owned by faction
                var faction = FactionSystem.ServerGetFactionByClanTag(clanTag);
                return(FactionSystem.ServerGetFactionMemberNames(faction).ToList());
            }
            }

            return(SharedGetDirectOwners(worldObject));
        }
Beispiel #28
0
        private static bool ServerIsCharacterInsideOwnedBase(ICharacter character, out bool isInsideNotOwnedBase)
        {
            var currentBase = LandClaimSystem.SharedGetLandClaimAreasGroup(character.TilePosition);

            if (currentBase is null)
            {
                isInsideNotOwnedBase = false;
                return(false);
            }

            foreach (var area in LandClaimAreasGroup.GetPrivateState(currentBase)
                     .ServerLandClaimsAreas)
            {
                if (LandClaimSystem.SharedIsOwnedArea(area, character, requireFactionPermission: false))
                {
                    isInsideNotOwnedBase = false;
                    return(true);
                }
            }

            isInsideNotOwnedBase = true;
            return(false);
        }
Beispiel #29
0
            private static void ServerRefreshFactionClaimAccess(ILogicObject faction)
            {
                using var tempList = Api.Shared.GetTempList <ILogicObject>();
                Api.GetProtoEntity <LandClaimAreasGroup>()
                .GetAllGameObjects(tempList.AsList());

                foreach (var areasGroup in tempList.AsList())
                {
                    if (!ReferenceEquals(LandClaimAreasGroup.GetPublicState(areasGroup).ServerFaction,
                                         faction))
                    {
                        continue;
                    }

                    var areas = LandClaimAreasGroup.GetPrivateState(areasGroup)
                                .ServerLandClaimsAreas;
                    foreach (var area in areas)
                    {
                        ServerUnregisterArea(area);
                        ServerRegisterArea(area);
                    }
                }
            }
        public string Execute(
            double chargePercent = 100,
            [CurrentCharacterIfNull] ICharacter character = null)
        {
            if (!LandClaimShieldProtectionConstants.SharedIsEnabled)
            {
                return("S.H.I.E.L.D. protection is not available");
            }

            var chargeFraction = MathHelper.Clamp(chargePercent / 100, min: 0, max: 1);

            using var tempAreas = Api.Shared.GetTempList <ILogicObject>();
            LandClaimSystem.SharedGetAreasInBounds(
                new RectangleInt(character.TilePosition, (1, 1)),
                tempAreas,
                addGracePadding: false);

            var area = tempAreas.AsList().FirstOrDefault();

            if (area is null)
            {
                return("No base exist near " + character.Name);
            }

            var areasGroup = LandClaimSystem.SharedGetLandClaimAreasGroup(area);

            LandClaimShieldProtectionSystem.SharedGetShieldProtectionMaxStatsForBase(areasGroup,
                                                                                     out _,
                                                                                     out var electricityCapacity);

            var privateState = LandClaimAreasGroup.GetPrivateState(areasGroup);

            privateState.ShieldProtectionCurrentChargeElectricity = electricityCapacity * chargeFraction;
            privateState.ShieldProtectionCooldownExpirationTime   = 0; // reset the cooldown

            return($"Charge amount of the S.H.I.E.L.D. modified to {chargeFraction * 100}% and cooldown reset.");
        }