Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Adding CustomKeycard for CustomItems #98

Open
wants to merge 10 commits into
base: dev
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from 3 commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
16 changes: 16 additions & 0 deletions EXILED/Exiled.API/Extensions/BitwiseExtensions.cs
Original file line number Diff line number Diff line change
Expand Up @@ -59,5 +59,21 @@ public static T ModifyFlags<T>(this T flags, bool value, params T[] changeFlags)

return (T)Enum.ToObject(typeof(T), currentValue);
}

/// <summary>
/// Checks if flag has specified value.
/// </summary>
/// <param name="flag">Flag to check.</param>
/// <param name="value">Value to check in flag.</param>
/// <typeparam name="T">The type of the enum.</typeparam>
/// <returns><see langword="true"/> if value is presented in flag. Otherwise, <see langword="false"/>.</returns>
public static bool HasFlagFast<T>(this T flag, T value)
where T : Enum
{
long flagValue = Convert.ToInt64(flag);
long valueValue = Convert.ToInt64(value);

return (flagValue & valueValue) == valueValue;
}
}
}
121 changes: 121 additions & 0 deletions EXILED/Exiled.CustomItems/API/Features/CustomKeycard.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,121 @@
// -----------------------------------------------------------------------
// <copyright file="CustomKeycard.cs" company="Exiled Team">
// Copyright (c) Exiled Team. All rights reserved.
// Licensed under the CC BY-SA 3.0 license.
// </copyright>
// -----------------------------------------------------------------------

namespace Exiled.CustomItems.API.Features
{
using System;

using Exiled.API.Enums;
using Exiled.API.Extensions;
using Exiled.API.Features;
using Exiled.API.Features.Doors;
using Exiled.Events.EventArgs.Item;
using Exiled.Events.EventArgs.Player;
using MapGeneration.Distributors;

/// <summary>
/// The Custom keycard base class.
/// </summary>
public abstract class CustomKeycard : CustomItem
{
/// <inheritdoc/>
/// <exception cref="ArgumentOutOfRangeException">Throws if specified <see cref="ItemType"/> is not Keycard.</exception>
public override ItemType Type
{
get => base.Type;
set
{
if (!value.IsKeycard())
throw new ArgumentOutOfRangeException("Type", value, "Invalid keycard type.");

base.Type = value;
}
}

/// <summary>
/// Gets or sets the permissions for custom keycard.
/// </summary>
public virtual KeycardPermissions Permissions { get; set; }

/// <summary>
/// Called when custom keycard interacts with a door.
/// </summary>
/// <param name="player">Owner of Custom keycard.</param>
/// <param name="door">Door with which interacting.</param>
/// <param name="isAllowed">Indicates whether door can be opened.</param>
protected virtual void OnInteractingDoor(Player player, Door door, ref bool isAllowed)
{
}

/// <summary>
/// Called when custom keycard interacts with a locker.
/// </summary>
/// <param name="player">Owner of Custom keycard.</param>
/// <param name="chamber">Chamber with which interacting.</param>
/// <param name="isAllowed">Indicates whether chamber can be opened.</param>
protected virtual void OnInteractingLocker(Player player, LockerChamber chamber, ref bool isAllowed)
{
}

private void OnInternalKeycardInteracting(KeycardInteractingEventArgs ev)
{
if (!Check(ev.Pickup))
return;

if (!ev.Door.IsKeycardDoor || ev.Door.KeycardPermissions == KeycardPermissions.None || ev.Door.IsLocked || ev.Player.IsBypassModeEnabled)
return;

if (ev.Door.KeycardPermissions.HasFlagFast(KeycardPermissions.ScpOverride))
{
ev.IsAllowed = Permissions.HasFlagFast(KeycardPermissions.Checkpoints);
return;
}

bool isAllowed = Permissions.HasFlagFast(ev.Door.KeycardPermissions);

OnInteractingDoor(ev.Player, ev.Door, ref isAllowed);

ev.IsAllowed = isAllowed;
}

private void OnInternalInteractingDoor(InteractingDoorEventArgs ev)
{
if (!Check(ev.Player.CurrentItem))
return;

if (ev.Door.KeycardPermissions == KeycardPermissions.None || ev.Door.IsLocked || ev.Player.IsBypassModeEnabled)
return;

if (ev.Door.KeycardPermissions.HasFlagFast(KeycardPermissions.ScpOverride))
{
ev.IsAllowed = Permissions.HasFlagFast(KeycardPermissions.Checkpoints);
return;
}

bool isAllowed = Permissions.HasFlagFast(ev.Door.KeycardPermissions);

OnInteractingDoor(ev.Player, ev.Door, ref isAllowed);

ev.IsAllowed = isAllowed;
}

private void OnInternalInteractingLocker(InteractingLockerEventArgs ev)
{
if (!Check(ev.Player.CurrentItem))
return;

if ((KeycardPermissions)ev.Chamber.RequiredPermissions == KeycardPermissions.None || ev.Player.IsBypassModeEnabled)
return;

bool isAllowed = Permissions.HasFlagFast((KeycardPermissions)ev.Chamber.RequiredPermissions);

OnInteractingLocker(ev.Player, ev.Chamber, ref isAllowed);

ev.IsAllowed = isAllowed;
}
}
}
Loading