From 74c22803082f2eb67c60f88ae8607d26de97bbeb Mon Sep 17 00:00:00 2001 From: Jesus QC <69375249+Jesus-QC@users.noreply.github.com> Date: Mon, 22 Jul 2024 02:18:00 +0200 Subject: [PATCH 01/28] fetching master (#132) Co-authored-by: Nameless <85962933+Misfiy@users.noreply.github.com> Co-authored-by: Misaka-ZeroTwo <45165615+Misaka-ZeroTwo@users.noreply.github.com> --- .github/workflows/release.yml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/.github/workflows/release.yml b/.github/workflows/release.yml index 035650f02..bcbe907cc 100644 --- a/.github/workflows/release.yml +++ b/.github/workflows/release.yml @@ -11,7 +11,7 @@ defaults: working-directory: ./EXILED env: - EXILED_REFERENCES_URL: https://Exiled-Official.github.io/SL-References/Master.zip + EXILED_REFERENCES_URL: https://Exiled-Official.github.io/SL-References/Dev.zip EXILED_REFERENCES_PATH: ${{ github.workspace }}/EXILED/References EXILED_DLL_ARCHIVER_URL: https://github.com/Exiled-Official/EXILED-DLL-Archiver/releases/latest/download/EXILED-DLL-Archiver.exe From 42346565e83869956f78c27a22f83f0e4f6e5790 Mon Sep 17 00:00:00 2001 From: Jesus QC <69375249+Jesus-QC@users.noreply.github.com> Date: Mon, 22 Jul 2024 13:37:41 +0200 Subject: [PATCH 02/28] DocFX Reimplementation (#131) --- .github/workflows/docs.yml | 100 +++++----- EXILED/docs/articles/contributing/index.md | 38 ++++ EXILED/docs/articles/index.md | 49 +++++ .../articles/installation/automatic/linux.md | 43 +++++ .../installation/automatic/windows.md | 43 +++++ EXILED/docs/articles/installation/index.md | 15 ++ EXILED/docs/articles/installation/manual.md | 24 +++ EXILED/docs/articles/plugins/events.md | 61 +++++++ EXILED/docs/articles/plugins/mec.md | 49 +++++ EXILED/docs/articles/plugins/structure.md | 172 ++++++++++++++++++ EXILED/docs/articles/toc.yml | 21 +++ EXILED/docs/assets/exiled.png | Bin 0 -> 852 bytes EXILED/docs/assets/favicon.ico | Bin 0 -> 251966 bytes EXILED/docs/docfx.json | 60 ++++++ EXILED/docs/filterConfig.yml | 10 + EXILED/docs/index.md | 16 ++ EXILED/docs/toc.yml | 6 + 17 files changed, 662 insertions(+), 45 deletions(-) create mode 100644 EXILED/docs/articles/contributing/index.md create mode 100644 EXILED/docs/articles/index.md create mode 100644 EXILED/docs/articles/installation/automatic/linux.md create mode 100644 EXILED/docs/articles/installation/automatic/windows.md create mode 100644 EXILED/docs/articles/installation/index.md create mode 100644 EXILED/docs/articles/installation/manual.md create mode 100644 EXILED/docs/articles/plugins/events.md create mode 100644 EXILED/docs/articles/plugins/mec.md create mode 100644 EXILED/docs/articles/plugins/structure.md create mode 100644 EXILED/docs/articles/toc.yml create mode 100644 EXILED/docs/assets/exiled.png create mode 100644 EXILED/docs/assets/favicon.ico create mode 100644 EXILED/docs/docfx.json create mode 100644 EXILED/docs/filterConfig.yml create mode 100644 EXILED/docs/index.md create mode 100644 EXILED/docs/toc.yml diff --git a/.github/workflows/docs.yml b/.github/workflows/docs.yml index e22c60eb2..351cdd3be 100644 --- a/.github/workflows/docs.yml +++ b/.github/workflows/docs.yml @@ -4,55 +4,65 @@ on: push: branches: - master - pull_request: - branches: - - master -defaults: - run: - working-directory: ./EXILED +# Sets permissions of the GITHUB_TOKEN to allow deployment to GitHub Pages +permissions: + actions: read + pages: write + id-token: write env: - EXILED_REFERENCES_URL: https://misaka-zerotwo.github.io/SL-References/Master.zip + EXILED_REFERENCES_URL: https://Exiled-Official.github.io/SL-References/Dev.zip EXILED_REFERENCES_PATH: ${{ github.workspace }}/EXILED/References + +# Allow only one concurrent deployment, skipping runs queued between the run in-progress and latest queued. +# However, do NOT cancel in-progress runs as we want to allow these production deployments to complete. +# Important due to https://t.ly/5DZAy +concurrency: + group: "pages" + cancel-in-progress: false jobs: - build_and_publish_docs: - runs-on: windows-latest - + publish-docs: + environment: + name: github-pages + url: ${{ steps.deployment.outputs.page_url }} + + runs-on: ubuntu-latest + steps: - - name: Checkout - uses: actions/checkout@v2.3.4 - - - name: Setup .NET Core SDK - uses: actions/setup-dotnet@v1.7.2 - - - name: Setup Nuget - uses: iRebbok/setup-nuget@master - - - name: Get references - shell: pwsh - run: | - Invoke-WebRequest -Uri ${{ EXILED_REFERENCES_URL }} -OutFile ${{ github.workspace }}/EXILED/References.zip - Expand-Archive -Path References.zip -DestinationPath ${{ env.EXILED_REFERENCES_PATH }} - - - name: Download DocFX - uses: crazy-max/ghaction-chocolatey@v1 - with: - args: install docfx --pre - - - name: Run DocFX - env: - EXILED_REFERENCES: ${{ env.EXILED_REFERENCES_PATH }} - run: docfx docfx.json; docfx docfx.json - - - name: Deploy to GitHub Pages - if: github.event_name == 'push' && success() #Only publishes on push to master to avoid docs mishaps - uses: crazy-max/ghaction-github-pages@v2 - with: - target_branch: gh-pages - build_dir: _site - keep_history: true - jekyll: false - env: - GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }} + - name: Checkout + uses: actions/checkout@v3 + + - name: Dotnet Setup + uses: actions/setup-dotnet@v3 + with: + dotnet-version: 8.x + + - run: dotnet tool update -g docfx + + - name: Setup .NET Core SDK + uses: actions/setup-dotnet@v1.7.2 + + - name: Setup Nuget + uses: iRebbok/setup-nuget@master + + - name: Get references + shell: pwsh + run: | + Invoke-WebRequest -Uri $env:EXILED_REFERENCES_URL -OutFile $env:GITHUB_WORKSPACE/EXILED/References.zip + Expand-Archive -Path $env:GITHUB_WORKSPACE/EXILED/References.zip -DestinationPath $env:EXILED_REFERENCES_PATH + + - run: docfx EXILED/docs/docfx.json + env: + EXILED_REFERENCES: ${{ env.EXILED_REFERENCES_PATH }} + + - name: Upload artifact + uses: actions/upload-pages-artifact@v3 + with: + # Upload entire repository + path: 'EXILED/docs/_site' + + - name: Deploy to GitHub Pages + id: deployment + uses: actions/deploy-pages@v4 diff --git a/EXILED/docs/articles/contributing/index.md b/EXILED/docs/articles/contributing/index.md new file mode 100644 index 000000000..021e1baa6 --- /dev/null +++ b/EXILED/docs/articles/contributing/index.md @@ -0,0 +1,38 @@ +--- +title: Contributing to EXILED +--- +# Contributing to EXILED + +This is a simple tutorial guiding you to contribute to our framework. + +### Forking EXILED +First, create a fork of our [GitHub repository](https://github.com/Exiled-Official/EXILED). + +Then, clone it to your computer like so: `git clone https://github.com/your-username/EXILED.git` + +Open a terminal in your forked EXILED folder and run ```git checkout dev```. This will switch you to the dev branch, which all pull requests should be submitted to. + +### Setting `EXILED_REFERENCES` + +If you haven't already, install the `SCP: Secret Laboratory Dedicated Server` through Steam or extract [this zip file](https://Exiled-Official.github.io/SL-References/Dev.zip) to an easily accessible folder. + +#### Windows users +Open the Environment Variables menu by searching for `Environment Variables` in the Start Menu. + +Create a new environment variable titled `EXILED_REFERENCES`. + +The value should point to `your_steamapps_directory/common/SCP Secret Laboratory Dedicated Server/SCPSL_Data/Managed`, or to the folder where you extracted the zip file mentioned earlier. + +#### Linux users +Add `export EXILED_REFERENCES="PATH"` to your `~/.bashrc` or similar file. + +PATH should point to `your_steamapps_directory/common/SCP Secret Laboratory Dedicated Server/SCPSL_Data/Managed`, or to the folder where you extracted the zip file mentioned earlier. + +--- + +You should now be able to open the EXILED directory in your favorite IDE. + + +Once you are done, test your changes thoroughly, and then submit a pull request to the main EXILED repository. Make sure you are targeting the `dev` branch, not `master`! + +Happy coding! \ No newline at end of file diff --git a/EXILED/docs/articles/index.md b/EXILED/docs/articles/index.md new file mode 100644 index 000000000..48ce7e0e1 --- /dev/null +++ b/EXILED/docs/articles/index.md @@ -0,0 +1,49 @@ +--- +title: Introduction +--- + +# Exiled Introduction + +## About EXILED + +**EXILED** is a low level plugin framework for SCP: Secret Laboratory. + +It offers an event system for developers to hook in order to manipulate or change game code, or implement their own functions. + +All **EXILED** events are coded with [Harmony](https://harmony.pardeike.net/) using IL transpilers, meaning they require no direct editing of server Assemblies to function, which allows for two unique benefits. + +- The entirety of the frameworks code can be freely published and shared. Allowing developers to better understand how it works, as well as contributing to the framework itself. +- Since all of the code related to the framework is done outside of the server assembly, things like small game updates will have little, if any, effect on the framework. + +--- + +# Frequently Asked Questions + +## What is EXILED? +EXILED - short for "EXtended In-runtime Library for External Development" is a plugin framework for SCP: Secret Laboratory compatible with MP2. It is not a direct replacement for SMOD, but it's purpose is to implement an event-based framework using Harmony patches, that plugin developers can utilize to develop plugins for SCP:SL servers. + +## How do I install EXILED? +See the [Installation](https://jesus-qc.github.io/EXILED/articles/installation/index.html) page for installation information. + +## How do I install plugins? +All plugins contain a DLL file (found in its latest release) that is used to load the plugin. Place the plugin in the appropriate plugin folder. +- Windows: `%AppData%\EXILED\Configs(ServerPortHere)-configs.yml` +- Linux: `~/.config/EXILED/Configs(ServerPortHere)-configs.yml` + +## Where is plugin configuration stored? +Plugin configuration is stored in a separate folder than the base-game config files. +- Windows: `%AppData%\EXILED\Plugins` +- Linux: `~/.config/EXILED/Plugins` + +## Is there a plugin for upgrading items in hand, inside SCP-914? +No, this is unnecessary because this is a base-game feature! Simply set the `914_mode` config_gameplay config to `DroppedAndHeld`. + +## What is Harmony? +Harmony is a library that examines the code of a program as it is being run, allowing developers to tap into those functions, and run their own code, either adding onto, or completely replacing, the code the program would normally run. + + +The reason EXILED uses harmony is to allow easier updating of the framework in conjunction with game updates. Under ideal circumstances, a new game update will not break EXILED itself, and the only thing needed to make EXILED work again, is a very simple copy/paste of a few lines of code into the new Assembly-CSharp file. + + +By keeping all of our code outside of the Assembly, other developers can have full, unhindered access to the entirety of EXILED's source code, making collaboration easier.
+Additionally, it means that our code will be mostly unaffected by game updates. Unless the game drastically changes code in a very specific function EXILED uses for an event patch, a game update may not even require EXILED itself to also be updated. diff --git a/EXILED/docs/articles/installation/automatic/linux.md b/EXILED/docs/articles/installation/automatic/linux.md new file mode 100644 index 000000000..2bd2e6934 --- /dev/null +++ b/EXILED/docs/articles/installation/automatic/linux.md @@ -0,0 +1,43 @@ +--- +title: Automatic Linux Installation +--- + +# Automatic Linux Installation + +Download `Exiled.Installer-Linux` from [here](https://github.com/Exiled-Official/EXILED/releases). + +Move it into your **server directory** and run it using `./Exiled.Installer-Linux` +- Make sure the server directory is the one where LocalAdmin executable is found. + +#### Usage +``` +Usage: + Exiled.Installer [options] [[--] ...]] + +Options: + -p, --path (REQUIRED) Path to the folder with the SL server [default: YourWorkingFolder] + --appdata (REQUIRED) Forces the folder to be the AppData folder (useful for containers when pterodactyl runs as root) [default: YourAppDataPath] + --pre-releases Includes pre-releases [default: False] + --target-version Target version for installation + --github--token Uses a token for auth in case the rate limit is exceeded (no permissions required) + --exit Automatically exits the application anyway + --get-versions Gets all possible versions for installation + --version Show version information + -?, -h, --help Show help and usage information + +Additional Arguments: + Arguments passed to the application that is being run. +``` + +----- + +#### Examples + +- ##### Installation in a specific folder, specific version and specific appdata folder +```powershell title="Basic installation in the folder you are in" +.\Exiled.Installer-Linux --pre-releases +``` + +```powershell title="Installation in a specific folder, specific version and specific appdata folder" +.\Exiled.Installer-Linux -p /home/user/scpsl/server --appdata /home/user/scpsl --target-version 2.0.8 +``` \ No newline at end of file diff --git a/EXILED/docs/articles/installation/automatic/windows.md b/EXILED/docs/articles/installation/automatic/windows.md new file mode 100644 index 000000000..d28ba2449 --- /dev/null +++ b/EXILED/docs/articles/installation/automatic/windows.md @@ -0,0 +1,43 @@ +--- +title: Automatic Windows Installation +--- + +# Automatic Windows Installation + +Download `Exiled.Installer-Win.exe` from [here](https://github.com/Exiled-Official/EXILED/releases). + +Move it into your **server directory** and double click the .exe. +- Make sure the server directory is the one where LocalAdmin.exe is found. + +#### Usage +``` +Usage: + Exiled.Installer [options] [[--] ...]] + +Options: + -p, --path (REQUIRED) Path to the folder with the SL server [default: YourWorkingFolder] + --appdata (REQUIRED) Forces the folder to be the AppData folder (useful for containers when pterodactyl runs as root) [default: YourAppDataPath] + --pre-releases Includes pre-releases [default: False] + --target-version Target version for installation + --github--token Uses a token for auth in case the rate limit is exceeded (no permissions required) + --exit Automatically exits the application anyway + --get-versions Gets all possible versions for installation + --version Show version information + -?, -h, --help Show help and usage information + +Additional Arguments: + Arguments passed to the application that is being run. +``` + +----- + +#### Examples +Using powershell. + +```powershell title="Basic installation in the folder you are in" +.\Exiled.Installer-Win --pre-releases +``` + +```powershell title="Installation in a specific folder, specific version and specific appdata folder" +.\Exiled.Installer-Win -p D:\Games\SCPSL\Server --appdata C --target-version 2.0.8 +``` \ No newline at end of file diff --git a/EXILED/docs/articles/installation/index.md b/EXILED/docs/articles/installation/index.md new file mode 100644 index 000000000..dba236d2c --- /dev/null +++ b/EXILED/docs/articles/installation/index.md @@ -0,0 +1,15 @@ +--- +title: Installing EXILED +--- + +# Installing EXILED + +## Automatic Installation + +Exiled has a tool that allows you to install **automatically** the framework for you. + +## Guides + +- [Window Automatic Installation](/EXILED/articles/installation/automatic/windows.html). +- [Linux Automatic Installation](/EXILED/articles/installation/automatic/linux.html). +- [Manual Installation](EXILED/articles/installation/manual.html). \ No newline at end of file diff --git a/EXILED/docs/articles/installation/manual.md b/EXILED/docs/articles/installation/manual.md new file mode 100644 index 000000000..650f02fbc --- /dev/null +++ b/EXILED/docs/articles/installation/manual.md @@ -0,0 +1,24 @@ +--- +title: Manual Installation +--- + +# Manual Installation + +You can download exiled manually following this steps: + +### Pick a release + +You can select a release inside [our official GitHub repo](https://github.com/Exiled-Official/EXILED/releases/). + +### Download the release + +Download the `Exiled.tar.gz` file and extract it with your favourite tool, we recommend [7Zip](https://www.7-zip.org/) or [WinRar](https://www.win-rar.com/download.html?&L=6). + +### Installation + +1. Move the file **``Assembly-CSharp.dll``** to: **`(Your Server Folder)/SCPSL_Data/Managed`** and replace the file. +2. Move the **``EXILED``** folder to **`%appdata%`** + +#### Note: +- Windows: This **`%appdata%`** folder is the one located inside **`AppData/Roaming`**, not just `AppData`. +- Linux: This **`%appdata%`** folder is the one called **`~/.config`**. \ No newline at end of file diff --git a/EXILED/docs/articles/plugins/events.md b/EXILED/docs/articles/plugins/events.md new file mode 100644 index 000000000..8bd83cc15 --- /dev/null +++ b/EXILED/docs/articles/plugins/events.md @@ -0,0 +1,61 @@ +--- +title: Events +--- + +This tutorial assumes that you are familiar with C# and with setting up a plugin in the EXILED framework. See the tutorial if you are unfamiliar with setting up a plugin using EXILED. + +# Events: What are they? +**Events** play a key role in the EXILED framework and all of the plugins utilizing it. Almost every plugin created using the EXILED framework uses events in one way or another. So, what are they? An event is a simple way of being informed when *something* happens. Events range from the round ending, to a player throwing an item or opening a door, to even SCP-096 being enraged! Events allow you to attach code that executes when something occurs before, during, or at the conclusion of a round. + +For example, say that you have the following method. + +```cs +public void OnDead() +{ + // Show hint to player. +} +``` + +With EXILED, it is possible to achieve the desired result: Showing a hint to a player who dies. + +## Event structure +The EXILED framework consists of two different types of events: Events that can be disallowed, and those that cannot. Events that can be disallowed can prevent certain events from happening; as an example, preventing a player from dying when they normally should. The ability to prevent certain events from happening is what gives EXILED its beauty. + +All events are part of a static class called a **handler**. All handlers can be found in the `Exiled.Events` namespace. Every handler is related to a specific feature in the game (eg. `Exiled.Events.Scp096` contains SCP-096 related events). + +Almost all events have a corresponding **event argument** class. The event argument provides the data of an event, as well as the ability to prevent it from occurring. All event arguments can be found in the `Exiled.Events.EventArgs` namespace, and all event arguments inherit from `System.EventArgs`. + +### Example: Enraging event +The following is the structure of the `Exiled.Events.EventArgs.EnragingEventArgs`. +```cs +public class EnragingEventArgs : System.EventArgs +{ + // Note: Constructor omitted. + public Scp096 Scp096 { get; } // The SCP-096 instance. + public Player Player { get; } // The player controlling SCP-096. + public bool IsAllowed { get; set; } // Whether or not SCP-096 can be enraged. +} +``` +Notice the `IsAllowed` property of the event. This property, which defaults to `true`, can be set to `false` to prevent SCP-096 from being enraged. For most events that can be disallowed, `IsAllowed` is set to `true` by default, and plugins can set it to `false` to prevent the event from occurring. However, in some cases, `IsAllowed` defaults to false and plugins can set it to `true` to *allow* the event to occur. An example of this behavior is the `InteractingDoor` event. `IsAllowed` will default to `false` in this event if a player cannot open a door, however plugins may set it to `true` to allow the player to open it regardless. + +## Connecting events +Events can be connected and disconnected by using the `+=` and `-=` operators. These can be used in the plugin's `OnEnabled` and `OnDisabled` methods, respectively. +```cs +// Base plugin class +// This example assumes a method called "OnEnraging" exists in this class. For best practice, you should create a new class to handle events. +using Exiled.Events; +public override void OnEnabled() +{ + Scp096.Enraging += OnEnraging; // Scp096 is the event handler, while Enraging is the name of the event. The += operator connects this event to the provided method. +} +public override void OnDisabled() +{ + Scp096.Enraging -= OnEnraging; // The -= operator disconnects this event from the provided method. +} +// Some other class +using Exiled.Events.EventArgs; +public void OnEnraging(EnragingEventArgs ev) // ev is the arguments for the event. Every event has a different argument class with different parameters, so make sure to check its documentation. +{ + Log.Info(ev.Player.Nickname + " has just been enraged!"); +} +``` \ No newline at end of file diff --git a/EXILED/docs/articles/plugins/mec.md b/EXILED/docs/articles/plugins/mec.md new file mode 100644 index 000000000..af80eb0c7 --- /dev/null +++ b/EXILED/docs/articles/plugins/mec.md @@ -0,0 +1,49 @@ +--- +title: MEC (More Effective Coroutines) +--- + +This tutorial assumes that you are familiar with C# and with setting up a plugin in the EXILED framework. See the Plugin Structure tutorial if you are unfamiliar with setting up a plugin using **EXILED**. + +# MEC (More Effective Coroutines) +If you are unfamiliar with MEC, this will be a very brief and simple primer to get you started. **MEC Coroutines** are basically timed methods, that support waiting periods of time before continuing execution, without interrupting/sleeping the main game thread. MEC coroutines are safe to use with Unity, unlike traditional threading, which *will* crash the server. + +MEC is useful for plugins which require a pre-defined timeout between execution. As an example, an automatic nuke plugin would want to pause for a certain amount of seconds before activating the warhead. A supply drop plugin would want to wait in certain intervals before executing a supply drop. Both of these are possible with MEC. + +## Setup +Unlike other API provided by SCP:SL, MEC requires a reference to the `Assembly-CSharp-firstpass` DLL file. After referencing this file, a `using MEC;` statement allows MEC to be used. + +## Coroutine +MEC offers [tons of features](http://trinary.tech/category/mec/free/) for controlling threads. For this tutorial, we are going to look at two of them: coroutines, and delayed calls. A coroutine is a method that is executed by MEC and supports delays. These methods must return type `IEnumerator` and must be called by `Timing.RunCoroutine(Method())`. An example can be seen below, using an infinite loop with a 5 second delay. + +```cs +using MEC; +using Exiled.API.Features; +public void SomeMethod() +{ + Timing.RunCoroutine(MyCoroutine()); +} +public IEnumerator MyCoroutine() +{ + for (;;) //repeat the loop infinitely + { + Log.Info("Hey, I'm a infinite loop!"); //Call Log.Info to print a line to the game console/server logs. + yield return Timing.WaitForSeconds(5f); //Tells the coroutine to wait 5 seconds before continuing. Since this is at the end of the loop, it effectively stalls the loop from repeating for 5 seconds. + } +} +``` +This example prints, "Hey, I'm an infinite loop!" every 5 seconds infinitely. Coroutines can have multiple `yield return` statements. + +## Delayed Calls +A simpler method of running an action after a delay is using `Timing.CallDelayed(float, Action)`, which executes code after a given number of seconds passes. This method does not require a coroutine to be created, hence why it's useful. An example can be seen below, logging a message 5 seconds after the method is called. +```cs +using MEC; +using Exiled.API.Features; +public void SomeMethod() +{ + Timing.CallDelayed(5f, () => // Execute the provided method 5 seconds late. + { + Log.Info("This log was printed 5 seconds late!"); + }) +} +``` +It is ***strongly*** recommended that you do some googling, or ask around **[in the EXILED Discord server](https://discord.gg/PyUkWTg)** if you are unfamiliar with MEC and would like to learn more, get advice, or need help. Questions, no matter how 'stupid' they are, will always be answered as helpfully and clearly as possible for plugin developers to excel. Better code is better for everyone. diff --git a/EXILED/docs/articles/plugins/structure.md b/EXILED/docs/articles/plugins/structure.md new file mode 100644 index 000000000..7a0d5997d --- /dev/null +++ b/EXILED/docs/articles/plugins/structure.md @@ -0,0 +1,172 @@ +--- +title: Plugin Structure +--- + +This tutorial assumes that you are familiar with C#. + +### Plugin Structure +In order to be loaded onto the framework, *every* plugin must follow a certain structure and inherit from certain members. If this is not achieved, the plugin will not execute. This tutorial will explain the proper setup for a plugin on the EXILED framework. + +## Plugin Core +Every plugin must have a .cs file that consists of the plugin class itself. This file (and the class itself) are typically simply named "Plugin"; however, any name is appropriate for the main plugin class. This example will use "Plugin" as the name of the class. + +After the main file is created, the Plugin class must be declared as a plugin, so that the EXILED framework loads it. This can be done by inheriting the `Plugin` class, provided in the `Exiled.API.Features` namespace. + +The following example shows how to properly inherit the class. However, notice the `Config` class inside of the angled brackets. This class must be created and must inherit from `IConfig`, which is part of the `Exiled.API.Interfaces` namespace. Upon the creation of the Config class, the interface will require you to add an `IsEnabled` property. +```cs +namespace MyPluginNamespace +{ + using Exiled.API.Features; + public class Plugin : Plugin + { + // This plugin will now be recognized by the EXILED framework! + } + // It is strongly encouraged to create a separate file for your Config class. + using Exiled.API.Interfaces; + public class Config : IConfig + { + public bool IsEnabled { get; set; } + } +} +``` +By creating the `Config` class and including it in the angled brackets, the rest of the plugin's code, as well as the EXILED framework, will recognize that the class resembles configuration for server owners. For more information about setting up configuration, see the Configuration section below. + +## OnEnabled and OnDisabled +The plugin is now successfully loaded onto the framework. However, it doesn't actually do anything; no functionality has been assigned. The `Plugin` class provides two overridable methods in order to give the plugin functionality: `OnEnabled` and `OnDisabled`. These two methods do exactly as they sound: Execute when the plugin is enabled/loaded, and when it is disabled. + +The following example shows how to utilize these methods to send a message to the console. +```cs +namespace MyPluginNamespace +{ + using Exiled.API.Features; + public class Plugin : Plugin + { + public override void OnEnabled() + { + Log.Info("My plugin has been enabled!"); + } + public override void OnDisabled() + { + Log.Info("My plugin has been disabled!"); + } + } + // Config.cs file + using Exiled.API.Interfaces; + public class Config : IConfig + { + public bool IsEnabled { get; set; } + } +} +``` +All of the code for the plugin *must* be enabled in the OnEnabled method, and *must* be disabled on the OnDisabled method. It is important that these two methods execute as expected, because server hosts can enable and disable plugins as much as they'd like, and the plugin *must* be able to respond to these changes appropriately. + +## Plugin Data +In order for a plugin to be submitted for public use, the plugin must override three properties: `Name`, `Author`, and `Version`. The first two are strings, whereas the last one is a `Version` class (`using System;` is required). + +The following example shows how to properly override this data. +```cs +namespace MyPluginNamespace +{ + using System; + using Exiled.API.Features; + public class Plugin : Plugin + { + public override string Name => "My Awesome Plugin"; + public override string Author => "MyName"; + public override Version Version => new Version(1, 0, 0); + } + // ... +} +``` + +## Configuration +This section is related to creating and reading the value of configuration. + +### Creating Configs +A lot of plugins provide configuration to allow the server hosts to change various features of the plugin. Luckily, creating configuration is very simple. + +To start, take a look at your Config.cs file. +```cs +namespace MyPluginNamespace +{ + using Exiled.API.Interfaces; + public class Config : IConfig + { + public bool IsEnabled { get; set; } + } +} +``` +There is currently one config, called `IsEnabled`. As stated above, this config is required and cannot be removed. However, more config can be added. The YAML serialization allows almost any type to be added and still work, including bools, ints, arrays of anything, enums, and even whole classes! + +In the following example, a config file with three configs is created. +```cs +namespace MyPluginNamespace +{ + using Exiled.API.Interfaces; + public class Config : IConfig + { + public bool IsEnabled { get; set; } + public bool MyBoolConfig { get; set; } + public string MyStringConfig { get; set; } + public int MyIntConfig { get; set; } = 5; // Set to 5 by default. + } +} +``` +To server hosts, the functionality of these configs might be confusing at first. So, the `System.ComponentModel.DescriptionAttribute` can be used to provide a description for each config! +```cs +namespace MyPluginNamespace +{ + using System.ComponentModel; + using Exiled.API.Interfaces; + public class Config : IConfig + { + [Description("Whether or not the plugin is enabled.")] + public bool IsEnabled { get; set; } + [Description("Config that must be true or false!")] + public bool MyBoolConfig { get; set; } + [Description("Config that must be a string!")] + public string MyStringConfig { get; set; } + [Description("Config that must be a number! Defaults to 5.")] + public int MyIntConfig { get; set; } = 5; + } +} +``` + +### Reading Configs +> [!NOTE] +> You do not need to read the value of the `IsEnabled` config; EXILED will automatically prevent your plugin from executing if its `IsEnabled` config is set to false. + + +Reading configuration is more simple than creating it. The base `Plugin` class provides a property, called `Config`, which can be used to access these values. + +In the following example, our config from the previous class is displayed when the plugin starts. +```cs +namespace MyPluginNamespace +{ + using Exiled.API.Features; + public class Plugin : Plugin + { + public override void OnEnabled() + { + Log.Info("Boolean config: " + Config.MyBoolConfig); + Log.Info("String config: " + Config.MyStringConfig); + Log.Info("Int config: " + Config.MyIntConfig); + } + } + // Config.cs file + using System.ComponentModel; + using Exiled.API.Interfaces; + public class Config : IConfig + { + [Description("Whether or not the plugin is enabled.")] + public bool IsEnabled { get; set; } + [Description("Config that must be true or false!")] + public bool MyBoolConfig { get; set; } + [Description("Config that must be a string!")] + public string MyStringConfig { get; set; } + [Description("Config that must be a number! Defaults to 5.")] + public int MyIntConfig { get; set; } = 5; + } +} +``` + diff --git a/EXILED/docs/articles/toc.yml b/EXILED/docs/articles/toc.yml new file mode 100644 index 000000000..5b863000c --- /dev/null +++ b/EXILED/docs/articles/toc.yml @@ -0,0 +1,21 @@ +- name: Introduction + href: index.md +- name: Installation + href: installation/index.md + items: + - name: Automatic (Linux) + href: installation/automatic/linux.md + - name: Automatic (Windows) + href: installation/automatic/windows.md + - name: Manual + href: installation/manual.md +- name: Plugin Development + items: + - name: Plugin Structure + href: plugins/structure.md + - name: More Effective Coroutines + href: plugins/mec.md + - name: Events + href: plugins/events.md +- name: Contributing + href: contributing/index.md diff --git a/EXILED/docs/assets/exiled.png b/EXILED/docs/assets/exiled.png new file mode 100644 index 0000000000000000000000000000000000000000..b80bc81af4252754719707448abd06dc0aa7353a GIT binary patch literal 852 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 literal 0 HcmV?d00001 diff --git a/EXILED/docs/docfx.json b/EXILED/docs/docfx.json new file mode 100644 index 000000000..a84191683 --- /dev/null +++ b/EXILED/docs/docfx.json @@ -0,0 +1,60 @@ +{ + "metadata": [ + { + "src": [ + { + "files": [ + "**/*.csproj" + ], + "exclude": [ + "**/bin/**", + "**/obj/**" + ], + "src": "../" + } + ], + "dest": "api", + "filter": "filterConfig.yml", + "namespaceLayout": "nested", + } + ], + "build": { + "globalMetadata": { + "_appTitle": "EXILED", + "_appLogoPath": "assets/exiled.png", + "_appFaviconPath": "assets/favicon.ico", + "_enableSearch": true, + "_lang": "en", + "_gitContribute": { + "repo": "https://github.com/Exiled-Official/EXILED", + "branch": "dev" + } + }, + "template": ["default", "modern"], + "content": [ + { + "files": [ + "api/**.yml", + "api/index.md", + "toc.yml", + "*.md" + ] + }, + { + "files": [ + "articles/toc.yml", + "articles/**.md" + ] + } + ], + "resource": [ + { + "files": [ + "assets/**" + ] + } + ], + "dest": "_site", + "docfx": "SGVsbG8sIHRoaXMgd2FzIG1hZGUgYnkgamVzdXNxYywgaG9wZSB5b3UgYXJlIG5vdCBjb3B5aW5nIHRoaXMgYmVjYXVzZSBpdCB3b3VsZCBiZSBoaWxhcmlvdXMg8J+YrfCfmK3wn5it8J+YrQ==" + } +} diff --git a/EXILED/docs/filterConfig.yml b/EXILED/docs/filterConfig.yml new file mode 100644 index 000000000..1fa0a3ca9 --- /dev/null +++ b/EXILED/docs/filterConfig.yml @@ -0,0 +1,10 @@ +apiRules: + - exclude: + uidRegex: Exiled.Updater + type: Namespace + - exclude: + uidRegex: Exiled.Example + type: Namespace + - exclude: + uidRegex: Exiled.CreditTags + type: Namespace diff --git a/EXILED/docs/index.md b/EXILED/docs/index.md new file mode 100644 index 000000000..58917327b --- /dev/null +++ b/EXILED/docs/index.md @@ -0,0 +1,16 @@ +--- +title: Home +--- +# Exiled +Join our [Discord](https://discord.gg/PyUkWTg) for support. + +EXILED is a plugin framework for SCP: Secret Laboratory servers. It offers an event system for developers to hook into in order to manipulate or change game code or implement their own functions. + +## Support +We consistently deliver updates and releases to address bugs and introduce new features or contributions swiftly. + +## Community +We encourage developers to contribute actively rather than solely relying on Exiled, thereby boosting project activity. + +## Features +We offer diverse features, providing users with flexibility. These features are optional, catering to various needs. diff --git a/EXILED/docs/toc.yml b/EXILED/docs/toc.yml new file mode 100644 index 000000000..bbebe92c1 --- /dev/null +++ b/EXILED/docs/toc.yml @@ -0,0 +1,6 @@ +- name: Articles + href: articles/ +- name: API Documentation + href: api/Exiled.html +- name: Repository + href: https://github.com/Exiled-Official/EXILED From 4ae0e0230bb1a97b540667fa17ba9335216aa369 Mon Sep 17 00:00:00 2001 From: Misaka-ZeroTwo <45165615+Misaka-ZeroTwo@users.noreply.github.com> Date: Tue, 23 Jul 2024 18:37:41 +0800 Subject: [PATCH 03/28] [CustomItems, Loader] Fix Null references (#135) Co-authored-by: Nameless <85962933+Misfiy@users.noreply.github.com> --- EXILED/Exiled.CustomItems/API/Features/CustomArmor.cs | 2 +- EXILED/Exiled.Loader/LoaderPlugin.cs | 6 ++++++ 2 files changed, 7 insertions(+), 1 deletion(-) diff --git a/EXILED/Exiled.CustomItems/API/Features/CustomArmor.cs b/EXILED/Exiled.CustomItems/API/Features/CustomArmor.cs index b41051f12..b50954d64 100644 --- a/EXILED/Exiled.CustomItems/API/Features/CustomArmor.cs +++ b/EXILED/Exiled.CustomItems/API/Features/CustomArmor.cs @@ -30,7 +30,7 @@ public override ItemType Type get => base.Type; set { - if (!value.IsArmor() && (value != ItemType.None)) + if (value != ItemType.None && !value.IsArmor()) throw new ArgumentOutOfRangeException("Type", value, "Invalid armor type."); base.Type = value; diff --git a/EXILED/Exiled.Loader/LoaderPlugin.cs b/EXILED/Exiled.Loader/LoaderPlugin.cs index 23dc888e2..ea9977fb4 100644 --- a/EXILED/Exiled.Loader/LoaderPlugin.cs +++ b/EXILED/Exiled.Loader/LoaderPlugin.cs @@ -38,6 +38,12 @@ public class LoaderPlugin [PluginPriority(byte.MinValue)] public void Enable() { + if (Config == null) + { + Log.Error("Detected null config, EXILED will not be loaded."); + return; + } + if (!Config.IsEnabled) { Log.Info("EXILED is disabled on this server via config."); From f28433e4d11f5dd49db6c87e1dd010c69473cd38 Mon Sep 17 00:00:00 2001 From: Jesus QC <69375249+Jesus-QC@users.noreply.github.com> Date: Wed, 24 Jul 2024 10:35:43 +0200 Subject: [PATCH 04/28] fetch (#136) Co-authored-by: Nameless <85962933+Misfiy@users.noreply.github.com> Co-authored-by: Misaka-ZeroTwo <45165615+Misaka-ZeroTwo@users.noreply.github.com> --- .github/README.md | 1 + 1 file changed, 1 insertion(+) diff --git a/.github/README.md b/.github/README.md index 76ea43932..038283f47 100644 --- a/.github/README.md +++ b/.github/README.md @@ -1,3 +1,4 @@ +
Exiled SCPSL, SCP Secret Laboratory Exiled, Exiled SCP: Secret Laboratory, Modding Framework, Mods, Exiled Mod SCPSL

Exiled

EXtended In-runtime Library for External Development
From 5eb907718d39e7fd92ce83e53c7f175e9c0e91ad Mon Sep 17 00:00:00 2001 From: Jesus QC <69375249+Jesus-QC@users.noreply.github.com> Date: Wed, 24 Jul 2024 10:36:28 +0200 Subject: [PATCH 05/28] Update README.md --- .github/README.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/.github/README.md b/.github/README.md index 038283f47..4da34bd0b 100644 --- a/.github/README.md +++ b/.github/README.md @@ -112,5 +112,5 @@ Localized READMEs
-
This repo is a fork of Exiled-Team/EXILED after the old repository was taken hostage by the old lead developer.
+
This repo is a fork of Exiled-Team/EXILED after changes in project leadership.
You can access the commit this update was forked from here.
From 1ddf14c57abbdae3782d898c0fff93cc23a9a05b Mon Sep 17 00:00:00 2001 From: Jesus QC <69375249+Jesus-QC@users.noreply.github.com> Date: Wed, 24 Jul 2024 10:37:45 +0200 Subject: [PATCH 06/28] ccbysa3 (#137) Co-authored-by: Nameless <85962933+Misfiy@users.noreply.github.com> Co-authored-by: Misaka-ZeroTwo <45165615+Misaka-ZeroTwo@users.noreply.github.com> From abae896c23573678cd52e88a4975b5606346b346 Mon Sep 17 00:00:00 2001 From: Misaka-ZeroTwo <45165615+Misaka-ZeroTwo@users.noreply.github.com> Date: Fri, 26 Jul 2024 00:19:35 +0800 Subject: [PATCH 07/28] Update main.yml --- .github/workflows/main.yml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/.github/workflows/main.yml b/.github/workflows/main.yml index 7be77c41a..6f9bc0f85 100644 --- a/.github/workflows/main.yml +++ b/.github/workflows/main.yml @@ -13,7 +13,7 @@ defaults: working-directory: ./EXILED env: - EXILED_REFERENCES_URL: https://Exiled-Official.github.io/SL-References/Master.zip + EXILED_REFERENCES_URL: https://exmod-team.github.io/SL-References/Master.zip EXILED_REFERENCES_PATH: ${{ github.workspace }}/EXILED/References jobs: From 8d7dab9e1b01d22d5d0b20e42b22c6c4f3d09f53 Mon Sep 17 00:00:00 2001 From: Misaka-ZeroTwo <45165615+Misaka-ZeroTwo@users.noreply.github.com> Date: Fri, 26 Jul 2024 00:20:50 +0800 Subject: [PATCH 08/28] Update release.yml --- .github/workflows/release.yml | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/.github/workflows/release.yml b/.github/workflows/release.yml index bcbe907cc..efdac4cc8 100644 --- a/.github/workflows/release.yml +++ b/.github/workflows/release.yml @@ -11,9 +11,9 @@ defaults: working-directory: ./EXILED env: - EXILED_REFERENCES_URL: https://Exiled-Official.github.io/SL-References/Dev.zip + EXILED_REFERENCES_URL: https://exmod-team.github.io/SL-References/Dev.zip EXILED_REFERENCES_PATH: ${{ github.workspace }}/EXILED/References - EXILED_DLL_ARCHIVER_URL: https://github.com/Exiled-Official/EXILED-DLL-Archiver/releases/latest/download/EXILED-DLL-Archiver.exe + EXILED_DLL_ARCHIVER_URL: https://github.com/ExMod-Team/EXILED-DLL-Archiver/releases/latest/download/EXILED-DLL-Archiver.exe jobs: build: From 475db8c32b3e2d0ce0b0014b1cee25828063cfa1 Mon Sep 17 00:00:00 2001 From: Misaka-ZeroTwo <45165615+Misaka-ZeroTwo@users.noreply.github.com> Date: Fri, 26 Jul 2024 00:22:48 +0800 Subject: [PATCH 09/28] Update dev.yml --- .github/workflows/dev.yml | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/.github/workflows/dev.yml b/.github/workflows/dev.yml index 6a9486427..c1f7fe301 100644 --- a/.github/workflows/dev.yml +++ b/.github/workflows/dev.yml @@ -14,9 +14,9 @@ defaults: working-directory: ./EXILED env: - EXILED_REFERENCES_URL: https://Exiled-Official.github.io/SL-References/Dev.zip + EXILED_REFERENCES_URL: https://exmod-team.github.io/SL-Reference/Dev.zip EXILED_REFERENCES_PATH: ${{ github.workspace }}/EXILED/References - EXILED_DLL_ARCHIVER_URL: https://github.com/Exiled-Official/EXILED-DLL-Archiver/releases/latest/download/EXILED-DLL-Archiver.exe + EXILED_DLL_ARCHIVER_URL: https://github.com/ExMod-Team/EXILED-DLL-Archiver/releases/latest/download/EXILED-DLL-Archiver.exe jobs: From 4e7406bc6facb4d23ce1f3137577d7e31a48c863 Mon Sep 17 00:00:00 2001 From: Misaka-ZeroTwo <45165615+Misaka-ZeroTwo@users.noreply.github.com> Date: Fri, 26 Jul 2024 00:31:24 +0800 Subject: [PATCH 10/28] Update Updater.cs --- EXILED/Exiled.Loader/Updater.cs | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/EXILED/Exiled.Loader/Updater.cs b/EXILED/Exiled.Loader/Updater.cs index 6990c1812..fb0636570 100644 --- a/EXILED/Exiled.Loader/Updater.cs +++ b/EXILED/Exiled.Loader/Updater.cs @@ -31,7 +31,7 @@ namespace Exiled.Loader /// internal sealed class Updater { - private const long REPOID = 828620622; + private const long REPOID = 833723500; private const string INSTALLER_ASSET_NAME_LINUX = "Exiled.Installer-Linux"; private const string INSTALLER_ASSET_NAME_WIN = "Exiled.Installer-Win.exe"; @@ -332,4 +332,4 @@ private bool FindAsset(string assetName, Release release, out ReleaseAsset asset return false; } } -} \ No newline at end of file +} From dfed0ee07c6e4380105d2477ef27142406ef249a Mon Sep 17 00:00:00 2001 From: Misaka-ZeroTwo <45165615+Misaka-ZeroTwo@users.noreply.github.com> Date: Fri, 26 Jul 2024 00:31:46 +0800 Subject: [PATCH 11/28] Update Program.cs --- EXILED/Exiled.Installer/Program.cs | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/EXILED/Exiled.Installer/Program.cs b/EXILED/Exiled.Installer/Program.cs index 34912cc51..559c17c82 100644 --- a/EXILED/Exiled.Installer/Program.cs +++ b/EXILED/Exiled.Installer/Program.cs @@ -42,7 +42,7 @@ internal enum PathResolution internal static class Program { - private const long RepoID = 828620622; + private const long RepoID = 833723500; private const string ExiledAssetName = "exiled.tar.gz"; // This is the lowest version the installer will check to install @@ -303,4 +303,4 @@ private static Release FindRelease(CommandSettings args, IEnumerable re return enumerable.First(); } } -} \ No newline at end of file +} From 0b108104c391b3622b1b196a082b6fcea632444a Mon Sep 17 00:00:00 2001 From: Misaka-ZeroTwo <45165615+Misaka-ZeroTwo@users.noreply.github.com> Date: Fri, 26 Jul 2024 01:33:28 +0800 Subject: [PATCH 12/28] Update dev.yml --- .github/workflows/dev.yml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/.github/workflows/dev.yml b/.github/workflows/dev.yml index c1f7fe301..a608aa15a 100644 --- a/.github/workflows/dev.yml +++ b/.github/workflows/dev.yml @@ -14,7 +14,7 @@ defaults: working-directory: ./EXILED env: - EXILED_REFERENCES_URL: https://exmod-team.github.io/SL-Reference/Dev.zip + EXILED_REFERENCES_URL: https://exmod-team.github.io/SL-References/Dev.zip EXILED_REFERENCES_PATH: ${{ github.workspace }}/EXILED/References EXILED_DLL_ARCHIVER_URL: https://github.com/ExMod-Team/EXILED-DLL-Archiver/releases/latest/download/EXILED-DLL-Archiver.exe From 42b541e4602f28313d1a6a9fb1f1c006660585d4 Mon Sep 17 00:00:00 2001 From: Misaka-ZeroTwo <45165615+Misaka-ZeroTwo@users.noreply.github.com> Date: Fri, 26 Jul 2024 17:39:39 +0800 Subject: [PATCH 13/28] Update labeler.yml --- .github/labeler.yml | 13 ++++++------- 1 file changed, 6 insertions(+), 7 deletions(-) diff --git a/.github/labeler.yml b/.github/labeler.yml index 34ff31f3f..5098459b0 100644 --- a/.github/labeler.yml +++ b/.github/labeler.yml @@ -13,29 +13,28 @@ Scripts: # Add the 'Scripts' label regarding-events: # Add the 'Events' label - changed-files: - - any-glob-to-any-file: Exiled.Events/** # Any Modifications to events + - any-glob-to-any-file: EXILED/Exiled.Events/** # Any Modifications to events regarding-api: # Add the 'API' label - changed-files: - - any-glob-to-any-file: Exiled.API/** # Any modifications to the API + - any-glob-to-any-file: EXILED/Exiled.API/** # Any modifications to the API regarding-transpiler: # Add the 'transpiler' label - changed-files: - - any-glob-to-any-file: Exiled.Events/Patches/**/* # Any modifications to transpiler files + - any-glob-to-any-file: EXILED/Exiled.Events/Patches/**/* # Any modifications to transpiler files CustomModules: # Add the 'CustomModules' label - changed-files: - - any-glob-to-any-file: Exiled.CustomModules/** # Any modifications to CustomModules + - any-glob-to-any-file: EXILED/Exiled.CustomModules/** # Any modifications to CustomModules Installer: # Add the 'Installer' label - changed-files: - - any-glob-to-any-file: Exiled.Installer/** # Any modifications to the Installer + - any-glob-to-any-file: EXILED/Exiled.Installer/** # Any modifications to the Installer Localization: # Add the 'Localization' label - changed-files: - - any-glob-to-any-file: Localization/** # Any modifications to Localization + - any-glob-to-any-file: EXILED/Localization/** # Any modifications to Localization GitHub_Actions: # Add the 'GitHub' label - changed-files: - any-glob-to-any-file: .github/** # Any modifications to github related files - From 92af4ce0a4e98085e2a9e5e266845530c1b99625 Mon Sep 17 00:00:00 2001 From: Misaka-ZeroTwo <45165615+Misaka-ZeroTwo@users.noreply.github.com> Date: Fri, 26 Jul 2024 17:39:56 +0800 Subject: [PATCH 14/28] Update labeler.yml --- .github/labeler.yml | 13 ++++++------- 1 file changed, 6 insertions(+), 7 deletions(-) diff --git a/.github/labeler.yml b/.github/labeler.yml index 34ff31f3f..5098459b0 100644 --- a/.github/labeler.yml +++ b/.github/labeler.yml @@ -13,29 +13,28 @@ Scripts: # Add the 'Scripts' label regarding-events: # Add the 'Events' label - changed-files: - - any-glob-to-any-file: Exiled.Events/** # Any Modifications to events + - any-glob-to-any-file: EXILED/Exiled.Events/** # Any Modifications to events regarding-api: # Add the 'API' label - changed-files: - - any-glob-to-any-file: Exiled.API/** # Any modifications to the API + - any-glob-to-any-file: EXILED/Exiled.API/** # Any modifications to the API regarding-transpiler: # Add the 'transpiler' label - changed-files: - - any-glob-to-any-file: Exiled.Events/Patches/**/* # Any modifications to transpiler files + - any-glob-to-any-file: EXILED/Exiled.Events/Patches/**/* # Any modifications to transpiler files CustomModules: # Add the 'CustomModules' label - changed-files: - - any-glob-to-any-file: Exiled.CustomModules/** # Any modifications to CustomModules + - any-glob-to-any-file: EXILED/Exiled.CustomModules/** # Any modifications to CustomModules Installer: # Add the 'Installer' label - changed-files: - - any-glob-to-any-file: Exiled.Installer/** # Any modifications to the Installer + - any-glob-to-any-file: EXILED/Exiled.Installer/** # Any modifications to the Installer Localization: # Add the 'Localization' label - changed-files: - - any-glob-to-any-file: Localization/** # Any modifications to Localization + - any-glob-to-any-file: EXILED/Localization/** # Any modifications to Localization GitHub_Actions: # Add the 'GitHub' label - changed-files: - any-glob-to-any-file: .github/** # Any modifications to github related files - From fd3840aac37e308cdb4efde92ec01d19da91b188 Mon Sep 17 00:00:00 2001 From: Misaka-ZeroTwo <45165615+Misaka-ZeroTwo@users.noreply.github.com> Date: Wed, 31 Jul 2024 19:07:27 +0800 Subject: [PATCH 15/28] Merge to dev (#8) --- .github/workflows/main.yml | 2 +- .github/workflows/release.yml | 4 ++-- EXILED/Exiled.Installer/Program.cs | 4 ++-- EXILED/Exiled.Loader/Updater.cs | 4 ++-- 4 files changed, 7 insertions(+), 7 deletions(-) diff --git a/.github/workflows/main.yml b/.github/workflows/main.yml index 7be77c41a..6f9bc0f85 100644 --- a/.github/workflows/main.yml +++ b/.github/workflows/main.yml @@ -13,7 +13,7 @@ defaults: working-directory: ./EXILED env: - EXILED_REFERENCES_URL: https://Exiled-Official.github.io/SL-References/Master.zip + EXILED_REFERENCES_URL: https://exmod-team.github.io/SL-References/Master.zip EXILED_REFERENCES_PATH: ${{ github.workspace }}/EXILED/References jobs: diff --git a/.github/workflows/release.yml b/.github/workflows/release.yml index bcbe907cc..efdac4cc8 100644 --- a/.github/workflows/release.yml +++ b/.github/workflows/release.yml @@ -11,9 +11,9 @@ defaults: working-directory: ./EXILED env: - EXILED_REFERENCES_URL: https://Exiled-Official.github.io/SL-References/Dev.zip + EXILED_REFERENCES_URL: https://exmod-team.github.io/SL-References/Dev.zip EXILED_REFERENCES_PATH: ${{ github.workspace }}/EXILED/References - EXILED_DLL_ARCHIVER_URL: https://github.com/Exiled-Official/EXILED-DLL-Archiver/releases/latest/download/EXILED-DLL-Archiver.exe + EXILED_DLL_ARCHIVER_URL: https://github.com/ExMod-Team/EXILED-DLL-Archiver/releases/latest/download/EXILED-DLL-Archiver.exe jobs: build: diff --git a/EXILED/Exiled.Installer/Program.cs b/EXILED/Exiled.Installer/Program.cs index 34912cc51..559c17c82 100644 --- a/EXILED/Exiled.Installer/Program.cs +++ b/EXILED/Exiled.Installer/Program.cs @@ -42,7 +42,7 @@ internal enum PathResolution internal static class Program { - private const long RepoID = 828620622; + private const long RepoID = 833723500; private const string ExiledAssetName = "exiled.tar.gz"; // This is the lowest version the installer will check to install @@ -303,4 +303,4 @@ private static Release FindRelease(CommandSettings args, IEnumerable re return enumerable.First(); } } -} \ No newline at end of file +} diff --git a/EXILED/Exiled.Loader/Updater.cs b/EXILED/Exiled.Loader/Updater.cs index 6990c1812..fb0636570 100644 --- a/EXILED/Exiled.Loader/Updater.cs +++ b/EXILED/Exiled.Loader/Updater.cs @@ -31,7 +31,7 @@ namespace Exiled.Loader /// internal sealed class Updater { - private const long REPOID = 828620622; + private const long REPOID = 833723500; private const string INSTALLER_ASSET_NAME_LINUX = "Exiled.Installer-Linux"; private const string INSTALLER_ASSET_NAME_WIN = "Exiled.Installer-Win.exe"; @@ -332,4 +332,4 @@ private bool FindAsset(string assetName, Release release, out ReleaseAsset asset return false; } } -} \ No newline at end of file +} From 21dae1226880e687150a61e43d6a202c38bfa991 Mon Sep 17 00:00:00 2001 From: Yamato Date: Wed, 31 Jul 2024 19:37:54 +0200 Subject: [PATCH 16/28] This will not be used --- .../Generic/Scp049API/CallAbilityDuration.cs | 63 ---------- .../Scp049API/SenseAbilityBaseCooldown.cs | 64 ---------- .../Scp049API/SenseAbilityReducedCooldown.cs | 64 ---------- .../Scp106API/CooldownReductionReward.cs | 67 ----------- .../Patches/Generic/Scp106API/CustomAttack.cs | 111 ------------------ .../Scp106API/HunterAtlastCostPerMetter.cs | 67 ----------- .../Scp106API/SinkholeAbilityCooldown.cs | 67 ----------- .../Generic/Scp106API/StalkVigorUse.cs | 84 ------------- .../Generic/Scp106API/VigorRegeneration.cs | 66 ----------- 9 files changed, 653 deletions(-) delete mode 100644 EXILED/Exiled.Events/Patches/Generic/Scp049API/CallAbilityDuration.cs delete mode 100644 EXILED/Exiled.Events/Patches/Generic/Scp049API/SenseAbilityBaseCooldown.cs delete mode 100644 EXILED/Exiled.Events/Patches/Generic/Scp049API/SenseAbilityReducedCooldown.cs delete mode 100644 EXILED/Exiled.Events/Patches/Generic/Scp106API/CooldownReductionReward.cs delete mode 100644 EXILED/Exiled.Events/Patches/Generic/Scp106API/CustomAttack.cs delete mode 100644 EXILED/Exiled.Events/Patches/Generic/Scp106API/HunterAtlastCostPerMetter.cs delete mode 100644 EXILED/Exiled.Events/Patches/Generic/Scp106API/SinkholeAbilityCooldown.cs delete mode 100644 EXILED/Exiled.Events/Patches/Generic/Scp106API/StalkVigorUse.cs delete mode 100644 EXILED/Exiled.Events/Patches/Generic/Scp106API/VigorRegeneration.cs diff --git a/EXILED/Exiled.Events/Patches/Generic/Scp049API/CallAbilityDuration.cs b/EXILED/Exiled.Events/Patches/Generic/Scp049API/CallAbilityDuration.cs deleted file mode 100644 index ddfb45adb..000000000 --- a/EXILED/Exiled.Events/Patches/Generic/Scp049API/CallAbilityDuration.cs +++ /dev/null @@ -1,63 +0,0 @@ -// ----------------------------------------------------------------------- -// -// Copyright (c) Exiled Team. All rights reserved. -// Licensed under the CC BY-SA 3.0 license. -// -// ----------------------------------------------------------------------- - -namespace Exiled.Events.Patches.Generic.Scp079API -{ - using System.Collections.Generic; - using System.Reflection.Emit; - - using API.Features.Pools; - using Exiled.API.Features; - using HarmonyLib; - using PlayerRoles.PlayableScps.Scp049; - using PlayerRoles.Subroutines; - - using static HarmonyLib.AccessTools; - - using BaseScp049Role = PlayerRoles.PlayableScps.Scp049.Scp049Role; - using Scp049Role = API.Features.Roles.Scp049Role; - - /// - /// Patches . - /// Adds the property. - /// - // [HarmonyPatch(typeof(Scp049CallAbility), nameof(Scp049CallAbility.ServerProcessCmd))] - internal class CallAbilityDuration - { - private static IEnumerable Transpiler(IEnumerable instructions, ILGenerator generator) - { - List newInstructions = ListPool.Pool.Get(instructions); - - LocalBuilder scp049Role = generator.DeclareLocal(typeof(Scp049Role)); - - // replace "this.Duration.Trigger(20.0)" with "this.Duration.Trigger((Player.Get(base.Owner).Role as Scp049Role).CallAbilityDuration)" - int offset = -1; - int index = newInstructions.FindIndex(instruction => instruction.operand == (object)Method(typeof(AbilityCooldown), nameof(AbilityCooldown.Trigger))) + offset; - newInstructions.RemoveAt(index); - - newInstructions.InsertRange( - index, - new CodeInstruction[] - { - // Player.Get(base.Owner).Role - new(OpCodes.Ldarg_0), - new(OpCodes.Call, PropertyGetter(typeof(StandardSubroutine), nameof(StandardSubroutine.Owner))), - new(OpCodes.Call, Method(typeof(Player), nameof(Player.Get), new[] { typeof(ReferenceHub) })), - new(OpCodes.Callvirt, PropertyGetter(typeof(Player), nameof(Player.Role))), - - // (Player.Get(base.Owner).Role as Scp049Role).CallAbilityDuration - new(OpCodes.Isinst, typeof(Scp049Role)), - new(OpCodes.Callvirt, PropertyGetter(typeof(Scp049Role), nameof(Scp049Role.CallAbilityDuration))), - }); - - for (int z = 0; z < newInstructions.Count; z++) - yield return newInstructions[z]; - - ListPool.Pool.Return(newInstructions); - } - } -} \ No newline at end of file diff --git a/EXILED/Exiled.Events/Patches/Generic/Scp049API/SenseAbilityBaseCooldown.cs b/EXILED/Exiled.Events/Patches/Generic/Scp049API/SenseAbilityBaseCooldown.cs deleted file mode 100644 index a70583b5f..000000000 --- a/EXILED/Exiled.Events/Patches/Generic/Scp049API/SenseAbilityBaseCooldown.cs +++ /dev/null @@ -1,64 +0,0 @@ -// ----------------------------------------------------------------------- -// -// Copyright (c) Exiled Team. All rights reserved. -// Licensed under the CC BY-SA 3.0 license. -// -// ----------------------------------------------------------------------- - -namespace Exiled.Events.Patches.Generic.Scp079API -{ - using System.Collections.Generic; - using System.Reflection.Emit; - - using API.Features.Pools; - using Exiled.API.Features; - - using HarmonyLib; - using PlayerRoles.PlayableScps.Scp049; - using PlayerRoles.Subroutines; - - using static HarmonyLib.AccessTools; - - using BaseScp049Role = PlayerRoles.PlayableScps.Scp049.Scp049Role; - using Scp049Role = API.Features.Roles.Scp049Role; - - /// - /// Patches . - /// Adds the property. - /// - // [HarmonyPatch(typeof(Scp049SenseAbility), nameof(Scp049SenseAbility.ServerProcessKilledPlayer))] - internal class SenseAbilityBaseCooldown - { - private static IEnumerable Transpiler(IEnumerable instructions, ILGenerator generator) - { - List newInstructions = ListPool.Pool.Get(instructions); - - LocalBuilder scp049Role = generator.DeclareLocal(typeof(Scp049Role)); - - // replace "this.Duration.Trigger(40.0)" with "this.Duration.Trigger((Player.Get(base.Owner).Role as Scp049Role).SenseAbilityBaseCooldown)" - int offset = -1; - int index = newInstructions.FindIndex(instruction => instruction.operand == (object)Method(typeof(AbilityCooldown), nameof(AbilityCooldown.Trigger))) + offset; - newInstructions.RemoveAt(index); - - newInstructions.InsertRange( - index, - new CodeInstruction[] - { - // Player.Get(base.Owner).Role - new(OpCodes.Ldarg_0), - new(OpCodes.Call, PropertyGetter(typeof(StandardSubroutine), nameof(StandardSubroutine.Owner))), - new(OpCodes.Call, Method(typeof(Player), nameof(Player.Get), new[] { typeof(ReferenceHub) })), - new(OpCodes.Callvirt, PropertyGetter(typeof(Player), nameof(Player.Role))), - - // (Player.Get(base.Owner).Role as Scp049Role).SenseAbilityBaseCooldown - new(OpCodes.Isinst, typeof(Scp049Role)), - new(OpCodes.Callvirt, PropertyGetter(typeof(Scp049Role), nameof(Scp049Role.SenseAbilityBaseCooldown))), - }); - - for (int z = 0; z < newInstructions.Count; z++) - yield return newInstructions[z]; - - ListPool.Pool.Return(newInstructions); - } - } -} \ No newline at end of file diff --git a/EXILED/Exiled.Events/Patches/Generic/Scp049API/SenseAbilityReducedCooldown.cs b/EXILED/Exiled.Events/Patches/Generic/Scp049API/SenseAbilityReducedCooldown.cs deleted file mode 100644 index 88c8333a1..000000000 --- a/EXILED/Exiled.Events/Patches/Generic/Scp049API/SenseAbilityReducedCooldown.cs +++ /dev/null @@ -1,64 +0,0 @@ -// ----------------------------------------------------------------------- -// -// Copyright (c) Exiled Team. All rights reserved. -// Licensed under the CC BY-SA 3.0 license. -// -// ----------------------------------------------------------------------- - -namespace Exiled.Events.Patches.Generic.Scp079API -{ - using System.Collections.Generic; - using System.Reflection.Emit; - - using API.Features.Pools; - using Exiled.API.Features; - - using HarmonyLib; - using PlayerRoles.PlayableScps.Scp049; - using PlayerRoles.Subroutines; - - using static HarmonyLib.AccessTools; - - using BaseScp049Role = PlayerRoles.PlayableScps.Scp049.Scp049Role; - using Scp049Role = API.Features.Roles.Scp049Role; - - /// - /// Patches . - /// Adds the property. - /// - // [HarmonyPatch(typeof(Scp049SenseAbility), nameof(Scp049SenseAbility.ServerLoseTarget))] - internal class SenseAbilityReducedCooldown - { - private static IEnumerable Transpiler(IEnumerable instructions, ILGenerator generator) - { - List newInstructions = ListPool.Pool.Get(instructions); - - LocalBuilder scp049Role = generator.DeclareLocal(typeof(Scp049Role)); - - // replace "this.Duration.Trigger(40.0)" with "this.Duration.Trigger((Player.Get(base.Owner).Role as Scp049Role).SenseAbilityReducedCooldown)" - int offset = -1; - int index = newInstructions.FindIndex(instruction => instruction.operand == (object)Method(typeof(AbilityCooldown), nameof(AbilityCooldown.Trigger))) + offset; - newInstructions.RemoveAt(index); - - newInstructions.InsertRange( - index, - new CodeInstruction[] - { - // Player.Get(base.Owner).Role - new(OpCodes.Ldarg_0), - new(OpCodes.Call, PropertyGetter(typeof(StandardSubroutine), nameof(StandardSubroutine.Owner))), - new(OpCodes.Call, Method(typeof(Player), nameof(Player.Get), new[] { typeof(ReferenceHub) })), - new(OpCodes.Callvirt, PropertyGetter(typeof(Player), nameof(Player.Role))), - - // (Player.Get(base.Owner).Role as Scp049Role).SenseAbilityReducedCooldown - new(OpCodes.Isinst, typeof(Scp049Role)), - new(OpCodes.Callvirt, PropertyGetter(typeof(Scp049Role), nameof(Scp049Role.SenseAbilityReducedCooldown))), - }); - - for (int z = 0; z < newInstructions.Count; z++) - yield return newInstructions[z]; - - ListPool.Pool.Return(newInstructions); - } - } -} \ No newline at end of file diff --git a/EXILED/Exiled.Events/Patches/Generic/Scp106API/CooldownReductionReward.cs b/EXILED/Exiled.Events/Patches/Generic/Scp106API/CooldownReductionReward.cs deleted file mode 100644 index 4f509aad2..000000000 --- a/EXILED/Exiled.Events/Patches/Generic/Scp106API/CooldownReductionReward.cs +++ /dev/null @@ -1,67 +0,0 @@ -// ----------------------------------------------------------------------- -// -// Copyright (c) Exiled Team. All rights reserved. -// Licensed under the CC BY-SA 3.0 license. -// -// ----------------------------------------------------------------------- - -namespace Exiled.Events.Patches.Generic.Scp106API -{ - using System.Collections.Generic; - using System.Reflection; - using System.Reflection.Emit; - - using API.Features.Pools; - using Exiled.API.Features; - using HarmonyLib; - using PlayerRoles.PlayableScps.Scp106; - using PlayerRoles.Subroutines; - - using static HarmonyLib.AccessTools; - - using BaseScp106Role = PlayerRoles.PlayableScps.Scp106.Scp106Role; - using Scp106Role = API.Features.Roles.Scp106Role; - - /// - /// Patches . - /// Adds the property. - /// - // [HarmonyPatch(typeof(Scp106Attack), nameof(Scp106Attack.ReduceSinkholeCooldown))] - internal class CooldownReductionReward - { - private static IEnumerable Transpiler(IEnumerable instructions, ILGenerator generator) - { - List newInstructions = ListPool.Pool.Get(instructions); - - LocalBuilder scp049Role = generator.DeclareLocal(typeof(Scp106Role)); - - // replace "base.ScpRole.Sinkhole.Cooldown.NextUse -= 5.0; - // with - // Scp106Role scp106Role = Player.Get(this.Owner).Role.As() - // replace "base.ScpRole.Sinkhole.Cooldown.NextUse -= scp106Role.CooldownReductionReward; - int offset = 0; - int index = newInstructions.FindLastIndex(instruction => instruction.opcode == OpCodes.Ldc_R4) + offset; - newInstructions.RemoveAt(index); - - newInstructions.InsertRange( - index, - new CodeInstruction[] - { - // Player.Get(base.Owner).Role - new(OpCodes.Ldarg_0), - new(OpCodes.Call, PropertyGetter(typeof(StandardSubroutine), nameof(StandardSubroutine.Owner))), - new(OpCodes.Call, Method(typeof(Player), nameof(Player.Get), new[] { typeof(ReferenceHub) })), - new(OpCodes.Callvirt, PropertyGetter(typeof(Player), nameof(Player.Role))), - - // (Player.Get(base.Owner).Role as Scp106Role).CooldownReductionReward - new(OpCodes.Isinst, typeof(Scp106Role)), - new(OpCodes.Callvirt, PropertyGetter(typeof(Scp106Role), nameof(Scp106Role.CooldownReductionReward))), - }); - - for (int z = 0; z < newInstructions.Count; z++) - yield return newInstructions[z]; - - ListPool.Pool.Return(newInstructions); - } - } -} diff --git a/EXILED/Exiled.Events/Patches/Generic/Scp106API/CustomAttack.cs b/EXILED/Exiled.Events/Patches/Generic/Scp106API/CustomAttack.cs deleted file mode 100644 index f6469919a..000000000 --- a/EXILED/Exiled.Events/Patches/Generic/Scp106API/CustomAttack.cs +++ /dev/null @@ -1,111 +0,0 @@ -// ----------------------------------------------------------------------- -// -// Copyright (c) Exiled Team. All rights reserved. -// Licensed under the CC BY-SA 3.0 license. -// -// ----------------------------------------------------------------------- - -namespace Exiled.Events.Patches.Generic.Scp106API -{ - using System.Collections.Generic; - using System.Reflection.Emit; - - using API.Features.Pools; - using Exiled.API.Features; - using HarmonyLib; - using PlayerRoles.PlayableScps.Scp106; - using PlayerRoles.Subroutines; - - using static HarmonyLib.AccessTools; - - using BaseScp106Role = PlayerRoles.PlayableScps.Scp106.Scp106Role; - using Scp106Role = API.Features.Roles.Scp106Role; - - /// - /// Patches . - /// Adds the , , property. - /// - // [HarmonyPatch(typeof(Scp106Attack), nameof(Scp106Attack.ServerShoot))] - internal class CustomAttack - { - private static IEnumerable Transpiler(IEnumerable instructions, ILGenerator generator) - { - List newInstructions = ListPool.Pool.Get(instructions); - - LocalBuilder scp049Role = generator.DeclareLocal(typeof(Scp106Role)); - - // replace "base.Vigor.VigorAmount += 0.3f;" - // with - // Scp106Role scp106Role = Player.Get(this.Owner).Role.As() - // "base.Vigor.VigorAmount += scp106Role.VigorCaptureReward;" - int offset = 0; - int index = newInstructions.FindIndex(instruction => instruction.operand == (object)Scp106Attack.VigorCaptureReward) + offset; - newInstructions.RemoveAt(index); - - newInstructions.InsertRange( - index, - new CodeInstruction[] - { - // Player.Get(base.Owner).Role - new(OpCodes.Ldarg_0), - new(OpCodes.Call, PropertyGetter(typeof(StandardSubroutine), nameof(StandardSubroutine.Owner))), - new(OpCodes.Call, Method(typeof(Player), nameof(Player.Get), new[] { typeof(ReferenceHub) })), - new(OpCodes.Callvirt, PropertyGetter(typeof(Player), nameof(Player.Role))), - - // (Player.Get(base.Owner).Role as Scp106Role).AttackDamage - new(OpCodes.Isinst, typeof(Scp106Role)), - new(OpCodes.Callvirt, PropertyGetter(typeof(Scp106Role), nameof(Scp106Role.VigorCaptureReward))), - }); - - // replace "base.Vigor.VigorAmount += 0.3f;" - // with - // Scp106Role scp106Role = Player.Get(this.Owner).Role.As() - // "base.Vigor.VigorAmount += scp106Role.VigorCaptureReward;" - offset = 0; - index = newInstructions.FindIndex(instruction => instruction.operand == (object)Scp106Attack.VigorCaptureReward) + offset; - newInstructions.RemoveAt(index); - - newInstructions.InsertRange( - index, - new CodeInstruction[] - { - // Player.Get(base.Owner).Role - new(OpCodes.Ldarg_0), - new(OpCodes.Call, PropertyGetter(typeof(StandardSubroutine), nameof(StandardSubroutine.Owner))), - new(OpCodes.Call, Method(typeof(Player), nameof(Player.Get), new[] { typeof(ReferenceHub) })), - new(OpCodes.Callvirt, PropertyGetter(typeof(Player), nameof(Player.Role))), - - // (Player.Get(base.Owner).Role as Scp106Role).AttackDamage - new(OpCodes.Isinst, typeof(Scp106Role)), - new(OpCodes.Callvirt, PropertyGetter(typeof(Scp106Role), nameof(Scp106Role.VigorCaptureReward))), - }); - - // replace "playerEffectsController.EnableEffect(20f, false);" - // with - // Scp106Role scp106Role = Player.Get(this.Owner).Role.As() - // "playerEffectsController.EnableEffect(scp106Role.CorrodingTime, false);" - offset = 0; - index = newInstructions.FindLastIndex(instruction => instruction.opcode == OpCodes.Ldc_R4) + offset; - newInstructions.RemoveAt(index); - - newInstructions.InsertRange( - index, - new CodeInstruction[] - { - // Player.Get(base.Owner).Role - new(OpCodes.Ldarg_0), - new(OpCodes.Call, PropertyGetter(typeof(StandardSubroutine), nameof(StandardSubroutine.Owner))), - new(OpCodes.Call, Method(typeof(Player), nameof(Player.Get), new[] { typeof(ReferenceHub) })), - new(OpCodes.Callvirt, PropertyGetter(typeof(Player), nameof(Player.Role))), - - // (Player.Get(base.Owner).Role as Scp106Role).CorrodingTime - new(OpCodes.Isinst, typeof(Scp106Role)), - new(OpCodes.Callvirt, PropertyGetter(typeof(Scp106Role), nameof(Scp106Role.CorrodingTime))), - }); - for (int z = 0; z < newInstructions.Count; z++) - yield return newInstructions[z]; - - ListPool.Pool.Return(newInstructions); - } - } -} diff --git a/EXILED/Exiled.Events/Patches/Generic/Scp106API/HunterAtlastCostPerMetter.cs b/EXILED/Exiled.Events/Patches/Generic/Scp106API/HunterAtlastCostPerMetter.cs deleted file mode 100644 index d85ac0151..000000000 --- a/EXILED/Exiled.Events/Patches/Generic/Scp106API/HunterAtlastCostPerMetter.cs +++ /dev/null @@ -1,67 +0,0 @@ -// ----------------------------------------------------------------------- -// -// Copyright (c) Exiled Team. All rights reserved. -// Licensed under the CC BY-SA 3.0 license. -// -// ----------------------------------------------------------------------- - -namespace Exiled.Events.Patches.Generic.Scp106API -{ - using System.Collections.Generic; - using System.Reflection; - using System.Reflection.Emit; - - using API.Features.Pools; - using Exiled.API.Features; - using HarmonyLib; - using PlayerRoles.PlayableScps.Scp106; - using PlayerRoles.Subroutines; - - using static HarmonyLib.AccessTools; - - using BaseScp106Role = PlayerRoles.PlayableScps.Scp106.Scp106Role; - using Scp106Role = API.Features.Roles.Scp106Role; - - /// - /// Patches . - /// Adds the property. - /// - // [HarmonyPatch(typeof(Scp106HuntersAtlasAbility), nameof(Scp106HuntersAtlasAbility.ServerProcessCmd))] - internal class HunterAtlastCostPerMetter - { - private static IEnumerable Transpiler(IEnumerable instructions, ILGenerator generator) - { - List newInstructions = ListPool.Pool.Get(instructions); - - LocalBuilder scp049Role = generator.DeclareLocal(typeof(Scp106Role)); - - // replace "num = (position2 - this._syncPos).MagnitudeIgnoreY() * 0.019f;" - // with - // Scp106Role scp106Role = Player.Get(this.Owner).Role.As() - // replace "num = (position2 - this._syncPos).MagnitudeIgnoreY() * scp106Role.HuntersAtlasCostPerMeter;" - int offset = 0; - int index = newInstructions.FindLastIndex(instruction => instruction.opcode == OpCodes.Ldc_R4) + offset; - newInstructions.RemoveAt(index); - - newInstructions.InsertRange( - index, - new CodeInstruction[] - { - // Player.Get(base.Owner).Role - new(OpCodes.Ldarg_0), - new(OpCodes.Call, PropertyGetter(typeof(StandardSubroutine), nameof(StandardSubroutine.Owner))), - new(OpCodes.Call, Method(typeof(Player), nameof(Player.Get), new[] { typeof(ReferenceHub) })), - new(OpCodes.Callvirt, PropertyGetter(typeof(Player), nameof(Player.Role))), - - // (Player.Get(base.Owner).Role as Scp106Role).HuntersAtlasCostPerMeter - new(OpCodes.Isinst, typeof(Scp106Role)), - new(OpCodes.Callvirt, PropertyGetter(typeof(Scp106Role), nameof(Scp106Role.HuntersAtlasCostPerMeter))), - }); - - for (int z = 0; z < newInstructions.Count; z++) - yield return newInstructions[z]; - - ListPool.Pool.Return(newInstructions); - } - } -} diff --git a/EXILED/Exiled.Events/Patches/Generic/Scp106API/SinkholeAbilityCooldown.cs b/EXILED/Exiled.Events/Patches/Generic/Scp106API/SinkholeAbilityCooldown.cs deleted file mode 100644 index 519fef858..000000000 --- a/EXILED/Exiled.Events/Patches/Generic/Scp106API/SinkholeAbilityCooldown.cs +++ /dev/null @@ -1,67 +0,0 @@ -// ----------------------------------------------------------------------- -// -// Copyright (c) Exiled Team. All rights reserved. -// Licensed under the CC BY-SA 3.0 license. -// -// ----------------------------------------------------------------------- - -namespace Exiled.Events.Patches.Generic.Scp106API -{ - using System.Collections.Generic; - using System.Reflection; - using System.Reflection.Emit; - - using API.Features.Pools; - using Exiled.API.Features; - using HarmonyLib; - using PlayerRoles.PlayableScps.Scp106; - using PlayerRoles.Subroutines; - - using static HarmonyLib.AccessTools; - - using BaseScp106Role = PlayerRoles.PlayableScps.Scp106.Scp106Role; - using Scp106Role = API.Features.Roles.Scp106Role; - - /// - /// Patches . - /// Adds the property. - /// - // [HarmonyPatch(typeof(Scp106Attack), nameof(Scp106Attack.ReduceSinkholeCooldown))] - internal class SinkholeAbilityCooldown - { - private static IEnumerable Transpiler(IEnumerable instructions, ILGenerator generator) - { - List newInstructions = ListPool.Pool.Get(instructions); - - LocalBuilder scp049Role = generator.DeclareLocal(typeof(Scp106Role)); - - // replace "this.Cooldown.Trigger(20.0);" - // with - // Scp106Role scp106Role = Player.Get(this.Owner).Role.As() - // replace "this.Cooldown.Trigger(scp106Role.SinkholeCooldownDuration);" - int offset = 0; - int index = newInstructions.FindLastIndex(instruction => instruction.opcode == OpCodes.Ldc_R4) + offset; - newInstructions.RemoveAt(index); - - newInstructions.InsertRange( - index, - new CodeInstruction[] - { - // Player.Get(base.Owner).Role - new(OpCodes.Ldarg_0), - new(OpCodes.Call, PropertyGetter(typeof(StandardSubroutine), nameof(StandardSubroutine.Owner))), - new(OpCodes.Call, Method(typeof(Player), nameof(Player.Get), new[] { typeof(ReferenceHub) })), - new(OpCodes.Callvirt, PropertyGetter(typeof(Player), nameof(Player.Role))), - - // (Player.Get(base.Owner).Role as Scp106Role).SinkholeCooldownDuration - new(OpCodes.Isinst, typeof(Scp106Role)), - new(OpCodes.Callvirt, PropertyGetter(typeof(Scp106Role), nameof(Scp106Role.SinkholeCooldownDuration))), - }); - - for (int z = 0; z < newInstructions.Count; z++) - yield return newInstructions[z]; - - ListPool.Pool.Return(newInstructions); - } - } -} diff --git a/EXILED/Exiled.Events/Patches/Generic/Scp106API/StalkVigorUse.cs b/EXILED/Exiled.Events/Patches/Generic/Scp106API/StalkVigorUse.cs deleted file mode 100644 index 38b7a9e53..000000000 --- a/EXILED/Exiled.Events/Patches/Generic/Scp106API/StalkVigorUse.cs +++ /dev/null @@ -1,84 +0,0 @@ -// ----------------------------------------------------------------------- -// -// Copyright (c) Exiled Team. All rights reserved. -// Licensed under the CC BY-SA 3.0 license. -// -// ----------------------------------------------------------------------- - -namespace Exiled.Events.Patches.Generic.Scp106API -{ - using System.Collections.Generic; - using System.Reflection.Emit; - - using API.Features.Pools; - using Exiled.API.Features; - using HarmonyLib; - using PlayerRoles.PlayableScps.Scp106; - using PlayerRoles.Subroutines; - - using static HarmonyLib.AccessTools; - - using BaseScp106Role = PlayerRoles.PlayableScps.Scp106.Scp106Role; - using Scp106Role = API.Features.Roles.Scp106Role; - - /// - /// Patches . - /// Adds the and property. - /// - // [HarmonyPatch(typeof(Scp106StalkAbility), nameof(Scp106StalkAbility.UpdateServerside))] - internal class StalkVigorUse - { - private static IEnumerable Transpiler(IEnumerable instructions, ILGenerator generator) - { - List newInstructions = ListPool.Pool.Get(instructions); - - LocalBuilder scp049Role = generator.DeclareLocal(typeof(Scp106Role)); - - // replace "float num = base.ScpRole.FpcModule.Motor.MovementDetected ? 0.09f : 0.06f;" - // with - // Scp106Role scp106Role = Player.Get(this.Owner).Role.As() - // "float num = base.ScpRole.FpcModule.Motor.MovementDetected ? scp106Role.VigorStalkCostMoving : scp106Role.VigorStalkCostStationary;" - int offset = 0; - int index = newInstructions.FindIndex(instruction => instruction.opcode == OpCodes.Ldc_R4) + offset; - newInstructions.RemoveAt(index); - - newInstructions.InsertRange( - index, - new CodeInstruction[] - { - // Player.Get(base.Owner).Role - new(OpCodes.Ldarg_0), - new(OpCodes.Call, PropertyGetter(typeof(StandardSubroutine), nameof(StandardSubroutine.Owner))), - new(OpCodes.Call, Method(typeof(Player), nameof(Player.Get), new[] { typeof(ReferenceHub) })), - new(OpCodes.Callvirt, PropertyGetter(typeof(Player), nameof(Player.Role))), - - // (Player.Get(base.Owner).Role as Scp106Role).VigorStalkCostMoving - new(OpCodes.Isinst, typeof(Scp106Role)), - new(OpCodes.Callvirt, PropertyGetter(typeof(Scp106Role), nameof(Scp106Role.VigorStalkCostMoving))), - }); - - offset = 0; - index = newInstructions.FindIndex(instruction => instruction.opcode == OpCodes.Ldc_R4) + offset; - newInstructions.RemoveAt(index); - - newInstructions.InsertRange( - index, - new CodeInstruction[] - { - // Player.Get(base.Owner).Role - new(OpCodes.Ldarg_0), - new(OpCodes.Call, PropertyGetter(typeof(StandardSubroutine), nameof(StandardSubroutine.Owner))), - new(OpCodes.Call, Method(typeof(Player), nameof(Player.Get), new[] { typeof(ReferenceHub) })), - new(OpCodes.Callvirt, PropertyGetter(typeof(Player), nameof(Player.Role))), - - // (Player.Get(base.Owner).Role as Scp106Role).VigorStalkCostStationary - new(OpCodes.Isinst, typeof(Scp106Role)), - new(OpCodes.Callvirt, PropertyGetter(typeof(Scp106Role), nameof(Scp106Role.VigorStalkCostStationary))), - }); - for (int z = 0; z < newInstructions.Count; z++) - yield return newInstructions[z]; - - ListPool.Pool.Return(newInstructions); - } - } -} diff --git a/EXILED/Exiled.Events/Patches/Generic/Scp106API/VigorRegeneration.cs b/EXILED/Exiled.Events/Patches/Generic/Scp106API/VigorRegeneration.cs deleted file mode 100644 index f14fd51d1..000000000 --- a/EXILED/Exiled.Events/Patches/Generic/Scp106API/VigorRegeneration.cs +++ /dev/null @@ -1,66 +0,0 @@ -// ----------------------------------------------------------------------- -// -// Copyright (c) Exiled Team. All rights reserved. -// Licensed under the CC BY-SA 3.0 license. -// -// ----------------------------------------------------------------------- - -namespace Exiled.Events.Patches.Generic.Scp106API -{ - using System.Collections.Generic; - using System.Reflection.Emit; - - using API.Features.Pools; - using Exiled.API.Features; - using HarmonyLib; - using PlayerRoles.PlayableScps.Scp106; - using PlayerRoles.Subroutines; - - using static HarmonyLib.AccessTools; - - using BaseScp106Role = PlayerRoles.PlayableScps.Scp106.Scp106Role; - using Scp106Role = API.Features.Roles.Scp106Role; - - /// - /// Patches . - /// Adds the property. - /// - // [HarmonyPatch(typeof(Scp106StalkAbility), nameof(Scp106StalkAbility.UpdateMovementState))] - internal class VigorRegeneration - { - private static IEnumerable Transpiler(IEnumerable instructions, ILGenerator generator) - { - List newInstructions = ListPool.Pool.Get(instructions); - - LocalBuilder scp049Role = generator.DeclareLocal(typeof(Scp106Role)); - - // replace "base.Vigor.VigorAmount += 0.03f * Time.deltaTime;" - // with - // Scp106Role scp106Role = Player.Get(this.Owner).Role.As() - // "base.Vigor.VigorAmount += scp106Role.VigorRegeneration * Time.deltaTime;" - int offset = -4; - int index = newInstructions.FindIndex(instruction => instruction.operand == (object)PropertySetter(typeof(Scp106VigorAbilityBase), nameof(Scp106VigorAbilityBase.VigorAmount))) + offset; - newInstructions.RemoveAt(index); - - newInstructions.InsertRange( - index, - new CodeInstruction[] - { - // Player.Get(base.Owner).Role - new(OpCodes.Ldarg_0), - new(OpCodes.Call, PropertyGetter(typeof(StandardSubroutine), nameof(StandardSubroutine.Owner))), - new(OpCodes.Call, Method(typeof(Player), nameof(Player.Get), new[] { typeof(ReferenceHub) })), - new(OpCodes.Callvirt, PropertyGetter(typeof(Player), nameof(Player.Role))), - - // (Player.Get(base.Owner).Role as Scp106Role).VigorRegeneration - new(OpCodes.Isinst, typeof(Scp106Role)), - new(OpCodes.Callvirt, PropertyGetter(typeof(Scp106Role), nameof(Scp106Role.VigorRegeneration))), - }); - - for (int z = 0; z < newInstructions.Count; z++) - yield return newInstructions[z]; - - ListPool.Pool.Return(newInstructions); - } - } -} From bd63934fd1e27c66f9766d7edf08033c63580c4e Mon Sep 17 00:00:00 2001 From: Yamato <66829532+louis1706@users.noreply.github.com> Date: Thu, 1 Aug 2024 00:22:18 +0200 Subject: [PATCH 17/28] This will not be used (#13) --- .../Generic/Scp049API/CallAbilityDuration.cs | 63 ---------- .../Scp049API/SenseAbilityBaseCooldown.cs | 64 ---------- .../Scp049API/SenseAbilityReducedCooldown.cs | 64 ---------- .../Scp106API/CooldownReductionReward.cs | 67 ----------- .../Patches/Generic/Scp106API/CustomAttack.cs | 111 ------------------ .../Scp106API/HunterAtlastCostPerMetter.cs | 67 ----------- .../Scp106API/SinkholeAbilityCooldown.cs | 67 ----------- .../Generic/Scp106API/StalkVigorUse.cs | 84 ------------- .../Generic/Scp106API/VigorRegeneration.cs | 66 ----------- 9 files changed, 653 deletions(-) delete mode 100644 EXILED/Exiled.Events/Patches/Generic/Scp049API/CallAbilityDuration.cs delete mode 100644 EXILED/Exiled.Events/Patches/Generic/Scp049API/SenseAbilityBaseCooldown.cs delete mode 100644 EXILED/Exiled.Events/Patches/Generic/Scp049API/SenseAbilityReducedCooldown.cs delete mode 100644 EXILED/Exiled.Events/Patches/Generic/Scp106API/CooldownReductionReward.cs delete mode 100644 EXILED/Exiled.Events/Patches/Generic/Scp106API/CustomAttack.cs delete mode 100644 EXILED/Exiled.Events/Patches/Generic/Scp106API/HunterAtlastCostPerMetter.cs delete mode 100644 EXILED/Exiled.Events/Patches/Generic/Scp106API/SinkholeAbilityCooldown.cs delete mode 100644 EXILED/Exiled.Events/Patches/Generic/Scp106API/StalkVigorUse.cs delete mode 100644 EXILED/Exiled.Events/Patches/Generic/Scp106API/VigorRegeneration.cs diff --git a/EXILED/Exiled.Events/Patches/Generic/Scp049API/CallAbilityDuration.cs b/EXILED/Exiled.Events/Patches/Generic/Scp049API/CallAbilityDuration.cs deleted file mode 100644 index ddfb45adb..000000000 --- a/EXILED/Exiled.Events/Patches/Generic/Scp049API/CallAbilityDuration.cs +++ /dev/null @@ -1,63 +0,0 @@ -// ----------------------------------------------------------------------- -// -// Copyright (c) Exiled Team. All rights reserved. -// Licensed under the CC BY-SA 3.0 license. -// -// ----------------------------------------------------------------------- - -namespace Exiled.Events.Patches.Generic.Scp079API -{ - using System.Collections.Generic; - using System.Reflection.Emit; - - using API.Features.Pools; - using Exiled.API.Features; - using HarmonyLib; - using PlayerRoles.PlayableScps.Scp049; - using PlayerRoles.Subroutines; - - using static HarmonyLib.AccessTools; - - using BaseScp049Role = PlayerRoles.PlayableScps.Scp049.Scp049Role; - using Scp049Role = API.Features.Roles.Scp049Role; - - /// - /// Patches . - /// Adds the property. - /// - // [HarmonyPatch(typeof(Scp049CallAbility), nameof(Scp049CallAbility.ServerProcessCmd))] - internal class CallAbilityDuration - { - private static IEnumerable Transpiler(IEnumerable instructions, ILGenerator generator) - { - List newInstructions = ListPool.Pool.Get(instructions); - - LocalBuilder scp049Role = generator.DeclareLocal(typeof(Scp049Role)); - - // replace "this.Duration.Trigger(20.0)" with "this.Duration.Trigger((Player.Get(base.Owner).Role as Scp049Role).CallAbilityDuration)" - int offset = -1; - int index = newInstructions.FindIndex(instruction => instruction.operand == (object)Method(typeof(AbilityCooldown), nameof(AbilityCooldown.Trigger))) + offset; - newInstructions.RemoveAt(index); - - newInstructions.InsertRange( - index, - new CodeInstruction[] - { - // Player.Get(base.Owner).Role - new(OpCodes.Ldarg_0), - new(OpCodes.Call, PropertyGetter(typeof(StandardSubroutine), nameof(StandardSubroutine.Owner))), - new(OpCodes.Call, Method(typeof(Player), nameof(Player.Get), new[] { typeof(ReferenceHub) })), - new(OpCodes.Callvirt, PropertyGetter(typeof(Player), nameof(Player.Role))), - - // (Player.Get(base.Owner).Role as Scp049Role).CallAbilityDuration - new(OpCodes.Isinst, typeof(Scp049Role)), - new(OpCodes.Callvirt, PropertyGetter(typeof(Scp049Role), nameof(Scp049Role.CallAbilityDuration))), - }); - - for (int z = 0; z < newInstructions.Count; z++) - yield return newInstructions[z]; - - ListPool.Pool.Return(newInstructions); - } - } -} \ No newline at end of file diff --git a/EXILED/Exiled.Events/Patches/Generic/Scp049API/SenseAbilityBaseCooldown.cs b/EXILED/Exiled.Events/Patches/Generic/Scp049API/SenseAbilityBaseCooldown.cs deleted file mode 100644 index a70583b5f..000000000 --- a/EXILED/Exiled.Events/Patches/Generic/Scp049API/SenseAbilityBaseCooldown.cs +++ /dev/null @@ -1,64 +0,0 @@ -// ----------------------------------------------------------------------- -// -// Copyright (c) Exiled Team. All rights reserved. -// Licensed under the CC BY-SA 3.0 license. -// -// ----------------------------------------------------------------------- - -namespace Exiled.Events.Patches.Generic.Scp079API -{ - using System.Collections.Generic; - using System.Reflection.Emit; - - using API.Features.Pools; - using Exiled.API.Features; - - using HarmonyLib; - using PlayerRoles.PlayableScps.Scp049; - using PlayerRoles.Subroutines; - - using static HarmonyLib.AccessTools; - - using BaseScp049Role = PlayerRoles.PlayableScps.Scp049.Scp049Role; - using Scp049Role = API.Features.Roles.Scp049Role; - - /// - /// Patches . - /// Adds the property. - /// - // [HarmonyPatch(typeof(Scp049SenseAbility), nameof(Scp049SenseAbility.ServerProcessKilledPlayer))] - internal class SenseAbilityBaseCooldown - { - private static IEnumerable Transpiler(IEnumerable instructions, ILGenerator generator) - { - List newInstructions = ListPool.Pool.Get(instructions); - - LocalBuilder scp049Role = generator.DeclareLocal(typeof(Scp049Role)); - - // replace "this.Duration.Trigger(40.0)" with "this.Duration.Trigger((Player.Get(base.Owner).Role as Scp049Role).SenseAbilityBaseCooldown)" - int offset = -1; - int index = newInstructions.FindIndex(instruction => instruction.operand == (object)Method(typeof(AbilityCooldown), nameof(AbilityCooldown.Trigger))) + offset; - newInstructions.RemoveAt(index); - - newInstructions.InsertRange( - index, - new CodeInstruction[] - { - // Player.Get(base.Owner).Role - new(OpCodes.Ldarg_0), - new(OpCodes.Call, PropertyGetter(typeof(StandardSubroutine), nameof(StandardSubroutine.Owner))), - new(OpCodes.Call, Method(typeof(Player), nameof(Player.Get), new[] { typeof(ReferenceHub) })), - new(OpCodes.Callvirt, PropertyGetter(typeof(Player), nameof(Player.Role))), - - // (Player.Get(base.Owner).Role as Scp049Role).SenseAbilityBaseCooldown - new(OpCodes.Isinst, typeof(Scp049Role)), - new(OpCodes.Callvirt, PropertyGetter(typeof(Scp049Role), nameof(Scp049Role.SenseAbilityBaseCooldown))), - }); - - for (int z = 0; z < newInstructions.Count; z++) - yield return newInstructions[z]; - - ListPool.Pool.Return(newInstructions); - } - } -} \ No newline at end of file diff --git a/EXILED/Exiled.Events/Patches/Generic/Scp049API/SenseAbilityReducedCooldown.cs b/EXILED/Exiled.Events/Patches/Generic/Scp049API/SenseAbilityReducedCooldown.cs deleted file mode 100644 index 88c8333a1..000000000 --- a/EXILED/Exiled.Events/Patches/Generic/Scp049API/SenseAbilityReducedCooldown.cs +++ /dev/null @@ -1,64 +0,0 @@ -// ----------------------------------------------------------------------- -// -// Copyright (c) Exiled Team. All rights reserved. -// Licensed under the CC BY-SA 3.0 license. -// -// ----------------------------------------------------------------------- - -namespace Exiled.Events.Patches.Generic.Scp079API -{ - using System.Collections.Generic; - using System.Reflection.Emit; - - using API.Features.Pools; - using Exiled.API.Features; - - using HarmonyLib; - using PlayerRoles.PlayableScps.Scp049; - using PlayerRoles.Subroutines; - - using static HarmonyLib.AccessTools; - - using BaseScp049Role = PlayerRoles.PlayableScps.Scp049.Scp049Role; - using Scp049Role = API.Features.Roles.Scp049Role; - - /// - /// Patches . - /// Adds the property. - /// - // [HarmonyPatch(typeof(Scp049SenseAbility), nameof(Scp049SenseAbility.ServerLoseTarget))] - internal class SenseAbilityReducedCooldown - { - private static IEnumerable Transpiler(IEnumerable instructions, ILGenerator generator) - { - List newInstructions = ListPool.Pool.Get(instructions); - - LocalBuilder scp049Role = generator.DeclareLocal(typeof(Scp049Role)); - - // replace "this.Duration.Trigger(40.0)" with "this.Duration.Trigger((Player.Get(base.Owner).Role as Scp049Role).SenseAbilityReducedCooldown)" - int offset = -1; - int index = newInstructions.FindIndex(instruction => instruction.operand == (object)Method(typeof(AbilityCooldown), nameof(AbilityCooldown.Trigger))) + offset; - newInstructions.RemoveAt(index); - - newInstructions.InsertRange( - index, - new CodeInstruction[] - { - // Player.Get(base.Owner).Role - new(OpCodes.Ldarg_0), - new(OpCodes.Call, PropertyGetter(typeof(StandardSubroutine), nameof(StandardSubroutine.Owner))), - new(OpCodes.Call, Method(typeof(Player), nameof(Player.Get), new[] { typeof(ReferenceHub) })), - new(OpCodes.Callvirt, PropertyGetter(typeof(Player), nameof(Player.Role))), - - // (Player.Get(base.Owner).Role as Scp049Role).SenseAbilityReducedCooldown - new(OpCodes.Isinst, typeof(Scp049Role)), - new(OpCodes.Callvirt, PropertyGetter(typeof(Scp049Role), nameof(Scp049Role.SenseAbilityReducedCooldown))), - }); - - for (int z = 0; z < newInstructions.Count; z++) - yield return newInstructions[z]; - - ListPool.Pool.Return(newInstructions); - } - } -} \ No newline at end of file diff --git a/EXILED/Exiled.Events/Patches/Generic/Scp106API/CooldownReductionReward.cs b/EXILED/Exiled.Events/Patches/Generic/Scp106API/CooldownReductionReward.cs deleted file mode 100644 index 4f509aad2..000000000 --- a/EXILED/Exiled.Events/Patches/Generic/Scp106API/CooldownReductionReward.cs +++ /dev/null @@ -1,67 +0,0 @@ -// ----------------------------------------------------------------------- -// -// Copyright (c) Exiled Team. All rights reserved. -// Licensed under the CC BY-SA 3.0 license. -// -// ----------------------------------------------------------------------- - -namespace Exiled.Events.Patches.Generic.Scp106API -{ - using System.Collections.Generic; - using System.Reflection; - using System.Reflection.Emit; - - using API.Features.Pools; - using Exiled.API.Features; - using HarmonyLib; - using PlayerRoles.PlayableScps.Scp106; - using PlayerRoles.Subroutines; - - using static HarmonyLib.AccessTools; - - using BaseScp106Role = PlayerRoles.PlayableScps.Scp106.Scp106Role; - using Scp106Role = API.Features.Roles.Scp106Role; - - /// - /// Patches . - /// Adds the property. - /// - // [HarmonyPatch(typeof(Scp106Attack), nameof(Scp106Attack.ReduceSinkholeCooldown))] - internal class CooldownReductionReward - { - private static IEnumerable Transpiler(IEnumerable instructions, ILGenerator generator) - { - List newInstructions = ListPool.Pool.Get(instructions); - - LocalBuilder scp049Role = generator.DeclareLocal(typeof(Scp106Role)); - - // replace "base.ScpRole.Sinkhole.Cooldown.NextUse -= 5.0; - // with - // Scp106Role scp106Role = Player.Get(this.Owner).Role.As() - // replace "base.ScpRole.Sinkhole.Cooldown.NextUse -= scp106Role.CooldownReductionReward; - int offset = 0; - int index = newInstructions.FindLastIndex(instruction => instruction.opcode == OpCodes.Ldc_R4) + offset; - newInstructions.RemoveAt(index); - - newInstructions.InsertRange( - index, - new CodeInstruction[] - { - // Player.Get(base.Owner).Role - new(OpCodes.Ldarg_0), - new(OpCodes.Call, PropertyGetter(typeof(StandardSubroutine), nameof(StandardSubroutine.Owner))), - new(OpCodes.Call, Method(typeof(Player), nameof(Player.Get), new[] { typeof(ReferenceHub) })), - new(OpCodes.Callvirt, PropertyGetter(typeof(Player), nameof(Player.Role))), - - // (Player.Get(base.Owner).Role as Scp106Role).CooldownReductionReward - new(OpCodes.Isinst, typeof(Scp106Role)), - new(OpCodes.Callvirt, PropertyGetter(typeof(Scp106Role), nameof(Scp106Role.CooldownReductionReward))), - }); - - for (int z = 0; z < newInstructions.Count; z++) - yield return newInstructions[z]; - - ListPool.Pool.Return(newInstructions); - } - } -} diff --git a/EXILED/Exiled.Events/Patches/Generic/Scp106API/CustomAttack.cs b/EXILED/Exiled.Events/Patches/Generic/Scp106API/CustomAttack.cs deleted file mode 100644 index f6469919a..000000000 --- a/EXILED/Exiled.Events/Patches/Generic/Scp106API/CustomAttack.cs +++ /dev/null @@ -1,111 +0,0 @@ -// ----------------------------------------------------------------------- -// -// Copyright (c) Exiled Team. All rights reserved. -// Licensed under the CC BY-SA 3.0 license. -// -// ----------------------------------------------------------------------- - -namespace Exiled.Events.Patches.Generic.Scp106API -{ - using System.Collections.Generic; - using System.Reflection.Emit; - - using API.Features.Pools; - using Exiled.API.Features; - using HarmonyLib; - using PlayerRoles.PlayableScps.Scp106; - using PlayerRoles.Subroutines; - - using static HarmonyLib.AccessTools; - - using BaseScp106Role = PlayerRoles.PlayableScps.Scp106.Scp106Role; - using Scp106Role = API.Features.Roles.Scp106Role; - - /// - /// Patches . - /// Adds the , , property. - /// - // [HarmonyPatch(typeof(Scp106Attack), nameof(Scp106Attack.ServerShoot))] - internal class CustomAttack - { - private static IEnumerable Transpiler(IEnumerable instructions, ILGenerator generator) - { - List newInstructions = ListPool.Pool.Get(instructions); - - LocalBuilder scp049Role = generator.DeclareLocal(typeof(Scp106Role)); - - // replace "base.Vigor.VigorAmount += 0.3f;" - // with - // Scp106Role scp106Role = Player.Get(this.Owner).Role.As() - // "base.Vigor.VigorAmount += scp106Role.VigorCaptureReward;" - int offset = 0; - int index = newInstructions.FindIndex(instruction => instruction.operand == (object)Scp106Attack.VigorCaptureReward) + offset; - newInstructions.RemoveAt(index); - - newInstructions.InsertRange( - index, - new CodeInstruction[] - { - // Player.Get(base.Owner).Role - new(OpCodes.Ldarg_0), - new(OpCodes.Call, PropertyGetter(typeof(StandardSubroutine), nameof(StandardSubroutine.Owner))), - new(OpCodes.Call, Method(typeof(Player), nameof(Player.Get), new[] { typeof(ReferenceHub) })), - new(OpCodes.Callvirt, PropertyGetter(typeof(Player), nameof(Player.Role))), - - // (Player.Get(base.Owner).Role as Scp106Role).AttackDamage - new(OpCodes.Isinst, typeof(Scp106Role)), - new(OpCodes.Callvirt, PropertyGetter(typeof(Scp106Role), nameof(Scp106Role.VigorCaptureReward))), - }); - - // replace "base.Vigor.VigorAmount += 0.3f;" - // with - // Scp106Role scp106Role = Player.Get(this.Owner).Role.As() - // "base.Vigor.VigorAmount += scp106Role.VigorCaptureReward;" - offset = 0; - index = newInstructions.FindIndex(instruction => instruction.operand == (object)Scp106Attack.VigorCaptureReward) + offset; - newInstructions.RemoveAt(index); - - newInstructions.InsertRange( - index, - new CodeInstruction[] - { - // Player.Get(base.Owner).Role - new(OpCodes.Ldarg_0), - new(OpCodes.Call, PropertyGetter(typeof(StandardSubroutine), nameof(StandardSubroutine.Owner))), - new(OpCodes.Call, Method(typeof(Player), nameof(Player.Get), new[] { typeof(ReferenceHub) })), - new(OpCodes.Callvirt, PropertyGetter(typeof(Player), nameof(Player.Role))), - - // (Player.Get(base.Owner).Role as Scp106Role).AttackDamage - new(OpCodes.Isinst, typeof(Scp106Role)), - new(OpCodes.Callvirt, PropertyGetter(typeof(Scp106Role), nameof(Scp106Role.VigorCaptureReward))), - }); - - // replace "playerEffectsController.EnableEffect(20f, false);" - // with - // Scp106Role scp106Role = Player.Get(this.Owner).Role.As() - // "playerEffectsController.EnableEffect(scp106Role.CorrodingTime, false);" - offset = 0; - index = newInstructions.FindLastIndex(instruction => instruction.opcode == OpCodes.Ldc_R4) + offset; - newInstructions.RemoveAt(index); - - newInstructions.InsertRange( - index, - new CodeInstruction[] - { - // Player.Get(base.Owner).Role - new(OpCodes.Ldarg_0), - new(OpCodes.Call, PropertyGetter(typeof(StandardSubroutine), nameof(StandardSubroutine.Owner))), - new(OpCodes.Call, Method(typeof(Player), nameof(Player.Get), new[] { typeof(ReferenceHub) })), - new(OpCodes.Callvirt, PropertyGetter(typeof(Player), nameof(Player.Role))), - - // (Player.Get(base.Owner).Role as Scp106Role).CorrodingTime - new(OpCodes.Isinst, typeof(Scp106Role)), - new(OpCodes.Callvirt, PropertyGetter(typeof(Scp106Role), nameof(Scp106Role.CorrodingTime))), - }); - for (int z = 0; z < newInstructions.Count; z++) - yield return newInstructions[z]; - - ListPool.Pool.Return(newInstructions); - } - } -} diff --git a/EXILED/Exiled.Events/Patches/Generic/Scp106API/HunterAtlastCostPerMetter.cs b/EXILED/Exiled.Events/Patches/Generic/Scp106API/HunterAtlastCostPerMetter.cs deleted file mode 100644 index d85ac0151..000000000 --- a/EXILED/Exiled.Events/Patches/Generic/Scp106API/HunterAtlastCostPerMetter.cs +++ /dev/null @@ -1,67 +0,0 @@ -// ----------------------------------------------------------------------- -// -// Copyright (c) Exiled Team. All rights reserved. -// Licensed under the CC BY-SA 3.0 license. -// -// ----------------------------------------------------------------------- - -namespace Exiled.Events.Patches.Generic.Scp106API -{ - using System.Collections.Generic; - using System.Reflection; - using System.Reflection.Emit; - - using API.Features.Pools; - using Exiled.API.Features; - using HarmonyLib; - using PlayerRoles.PlayableScps.Scp106; - using PlayerRoles.Subroutines; - - using static HarmonyLib.AccessTools; - - using BaseScp106Role = PlayerRoles.PlayableScps.Scp106.Scp106Role; - using Scp106Role = API.Features.Roles.Scp106Role; - - /// - /// Patches . - /// Adds the property. - /// - // [HarmonyPatch(typeof(Scp106HuntersAtlasAbility), nameof(Scp106HuntersAtlasAbility.ServerProcessCmd))] - internal class HunterAtlastCostPerMetter - { - private static IEnumerable Transpiler(IEnumerable instructions, ILGenerator generator) - { - List newInstructions = ListPool.Pool.Get(instructions); - - LocalBuilder scp049Role = generator.DeclareLocal(typeof(Scp106Role)); - - // replace "num = (position2 - this._syncPos).MagnitudeIgnoreY() * 0.019f;" - // with - // Scp106Role scp106Role = Player.Get(this.Owner).Role.As() - // replace "num = (position2 - this._syncPos).MagnitudeIgnoreY() * scp106Role.HuntersAtlasCostPerMeter;" - int offset = 0; - int index = newInstructions.FindLastIndex(instruction => instruction.opcode == OpCodes.Ldc_R4) + offset; - newInstructions.RemoveAt(index); - - newInstructions.InsertRange( - index, - new CodeInstruction[] - { - // Player.Get(base.Owner).Role - new(OpCodes.Ldarg_0), - new(OpCodes.Call, PropertyGetter(typeof(StandardSubroutine), nameof(StandardSubroutine.Owner))), - new(OpCodes.Call, Method(typeof(Player), nameof(Player.Get), new[] { typeof(ReferenceHub) })), - new(OpCodes.Callvirt, PropertyGetter(typeof(Player), nameof(Player.Role))), - - // (Player.Get(base.Owner).Role as Scp106Role).HuntersAtlasCostPerMeter - new(OpCodes.Isinst, typeof(Scp106Role)), - new(OpCodes.Callvirt, PropertyGetter(typeof(Scp106Role), nameof(Scp106Role.HuntersAtlasCostPerMeter))), - }); - - for (int z = 0; z < newInstructions.Count; z++) - yield return newInstructions[z]; - - ListPool.Pool.Return(newInstructions); - } - } -} diff --git a/EXILED/Exiled.Events/Patches/Generic/Scp106API/SinkholeAbilityCooldown.cs b/EXILED/Exiled.Events/Patches/Generic/Scp106API/SinkholeAbilityCooldown.cs deleted file mode 100644 index 519fef858..000000000 --- a/EXILED/Exiled.Events/Patches/Generic/Scp106API/SinkholeAbilityCooldown.cs +++ /dev/null @@ -1,67 +0,0 @@ -// ----------------------------------------------------------------------- -// -// Copyright (c) Exiled Team. All rights reserved. -// Licensed under the CC BY-SA 3.0 license. -// -// ----------------------------------------------------------------------- - -namespace Exiled.Events.Patches.Generic.Scp106API -{ - using System.Collections.Generic; - using System.Reflection; - using System.Reflection.Emit; - - using API.Features.Pools; - using Exiled.API.Features; - using HarmonyLib; - using PlayerRoles.PlayableScps.Scp106; - using PlayerRoles.Subroutines; - - using static HarmonyLib.AccessTools; - - using BaseScp106Role = PlayerRoles.PlayableScps.Scp106.Scp106Role; - using Scp106Role = API.Features.Roles.Scp106Role; - - /// - /// Patches . - /// Adds the property. - /// - // [HarmonyPatch(typeof(Scp106Attack), nameof(Scp106Attack.ReduceSinkholeCooldown))] - internal class SinkholeAbilityCooldown - { - private static IEnumerable Transpiler(IEnumerable instructions, ILGenerator generator) - { - List newInstructions = ListPool.Pool.Get(instructions); - - LocalBuilder scp049Role = generator.DeclareLocal(typeof(Scp106Role)); - - // replace "this.Cooldown.Trigger(20.0);" - // with - // Scp106Role scp106Role = Player.Get(this.Owner).Role.As() - // replace "this.Cooldown.Trigger(scp106Role.SinkholeCooldownDuration);" - int offset = 0; - int index = newInstructions.FindLastIndex(instruction => instruction.opcode == OpCodes.Ldc_R4) + offset; - newInstructions.RemoveAt(index); - - newInstructions.InsertRange( - index, - new CodeInstruction[] - { - // Player.Get(base.Owner).Role - new(OpCodes.Ldarg_0), - new(OpCodes.Call, PropertyGetter(typeof(StandardSubroutine), nameof(StandardSubroutine.Owner))), - new(OpCodes.Call, Method(typeof(Player), nameof(Player.Get), new[] { typeof(ReferenceHub) })), - new(OpCodes.Callvirt, PropertyGetter(typeof(Player), nameof(Player.Role))), - - // (Player.Get(base.Owner).Role as Scp106Role).SinkholeCooldownDuration - new(OpCodes.Isinst, typeof(Scp106Role)), - new(OpCodes.Callvirt, PropertyGetter(typeof(Scp106Role), nameof(Scp106Role.SinkholeCooldownDuration))), - }); - - for (int z = 0; z < newInstructions.Count; z++) - yield return newInstructions[z]; - - ListPool.Pool.Return(newInstructions); - } - } -} diff --git a/EXILED/Exiled.Events/Patches/Generic/Scp106API/StalkVigorUse.cs b/EXILED/Exiled.Events/Patches/Generic/Scp106API/StalkVigorUse.cs deleted file mode 100644 index 38b7a9e53..000000000 --- a/EXILED/Exiled.Events/Patches/Generic/Scp106API/StalkVigorUse.cs +++ /dev/null @@ -1,84 +0,0 @@ -// ----------------------------------------------------------------------- -// -// Copyright (c) Exiled Team. All rights reserved. -// Licensed under the CC BY-SA 3.0 license. -// -// ----------------------------------------------------------------------- - -namespace Exiled.Events.Patches.Generic.Scp106API -{ - using System.Collections.Generic; - using System.Reflection.Emit; - - using API.Features.Pools; - using Exiled.API.Features; - using HarmonyLib; - using PlayerRoles.PlayableScps.Scp106; - using PlayerRoles.Subroutines; - - using static HarmonyLib.AccessTools; - - using BaseScp106Role = PlayerRoles.PlayableScps.Scp106.Scp106Role; - using Scp106Role = API.Features.Roles.Scp106Role; - - /// - /// Patches . - /// Adds the and property. - /// - // [HarmonyPatch(typeof(Scp106StalkAbility), nameof(Scp106StalkAbility.UpdateServerside))] - internal class StalkVigorUse - { - private static IEnumerable Transpiler(IEnumerable instructions, ILGenerator generator) - { - List newInstructions = ListPool.Pool.Get(instructions); - - LocalBuilder scp049Role = generator.DeclareLocal(typeof(Scp106Role)); - - // replace "float num = base.ScpRole.FpcModule.Motor.MovementDetected ? 0.09f : 0.06f;" - // with - // Scp106Role scp106Role = Player.Get(this.Owner).Role.As() - // "float num = base.ScpRole.FpcModule.Motor.MovementDetected ? scp106Role.VigorStalkCostMoving : scp106Role.VigorStalkCostStationary;" - int offset = 0; - int index = newInstructions.FindIndex(instruction => instruction.opcode == OpCodes.Ldc_R4) + offset; - newInstructions.RemoveAt(index); - - newInstructions.InsertRange( - index, - new CodeInstruction[] - { - // Player.Get(base.Owner).Role - new(OpCodes.Ldarg_0), - new(OpCodes.Call, PropertyGetter(typeof(StandardSubroutine), nameof(StandardSubroutine.Owner))), - new(OpCodes.Call, Method(typeof(Player), nameof(Player.Get), new[] { typeof(ReferenceHub) })), - new(OpCodes.Callvirt, PropertyGetter(typeof(Player), nameof(Player.Role))), - - // (Player.Get(base.Owner).Role as Scp106Role).VigorStalkCostMoving - new(OpCodes.Isinst, typeof(Scp106Role)), - new(OpCodes.Callvirt, PropertyGetter(typeof(Scp106Role), nameof(Scp106Role.VigorStalkCostMoving))), - }); - - offset = 0; - index = newInstructions.FindIndex(instruction => instruction.opcode == OpCodes.Ldc_R4) + offset; - newInstructions.RemoveAt(index); - - newInstructions.InsertRange( - index, - new CodeInstruction[] - { - // Player.Get(base.Owner).Role - new(OpCodes.Ldarg_0), - new(OpCodes.Call, PropertyGetter(typeof(StandardSubroutine), nameof(StandardSubroutine.Owner))), - new(OpCodes.Call, Method(typeof(Player), nameof(Player.Get), new[] { typeof(ReferenceHub) })), - new(OpCodes.Callvirt, PropertyGetter(typeof(Player), nameof(Player.Role))), - - // (Player.Get(base.Owner).Role as Scp106Role).VigorStalkCostStationary - new(OpCodes.Isinst, typeof(Scp106Role)), - new(OpCodes.Callvirt, PropertyGetter(typeof(Scp106Role), nameof(Scp106Role.VigorStalkCostStationary))), - }); - for (int z = 0; z < newInstructions.Count; z++) - yield return newInstructions[z]; - - ListPool.Pool.Return(newInstructions); - } - } -} diff --git a/EXILED/Exiled.Events/Patches/Generic/Scp106API/VigorRegeneration.cs b/EXILED/Exiled.Events/Patches/Generic/Scp106API/VigorRegeneration.cs deleted file mode 100644 index f14fd51d1..000000000 --- a/EXILED/Exiled.Events/Patches/Generic/Scp106API/VigorRegeneration.cs +++ /dev/null @@ -1,66 +0,0 @@ -// ----------------------------------------------------------------------- -// -// Copyright (c) Exiled Team. All rights reserved. -// Licensed under the CC BY-SA 3.0 license. -// -// ----------------------------------------------------------------------- - -namespace Exiled.Events.Patches.Generic.Scp106API -{ - using System.Collections.Generic; - using System.Reflection.Emit; - - using API.Features.Pools; - using Exiled.API.Features; - using HarmonyLib; - using PlayerRoles.PlayableScps.Scp106; - using PlayerRoles.Subroutines; - - using static HarmonyLib.AccessTools; - - using BaseScp106Role = PlayerRoles.PlayableScps.Scp106.Scp106Role; - using Scp106Role = API.Features.Roles.Scp106Role; - - /// - /// Patches . - /// Adds the property. - /// - // [HarmonyPatch(typeof(Scp106StalkAbility), nameof(Scp106StalkAbility.UpdateMovementState))] - internal class VigorRegeneration - { - private static IEnumerable Transpiler(IEnumerable instructions, ILGenerator generator) - { - List newInstructions = ListPool.Pool.Get(instructions); - - LocalBuilder scp049Role = generator.DeclareLocal(typeof(Scp106Role)); - - // replace "base.Vigor.VigorAmount += 0.03f * Time.deltaTime;" - // with - // Scp106Role scp106Role = Player.Get(this.Owner).Role.As() - // "base.Vigor.VigorAmount += scp106Role.VigorRegeneration * Time.deltaTime;" - int offset = -4; - int index = newInstructions.FindIndex(instruction => instruction.operand == (object)PropertySetter(typeof(Scp106VigorAbilityBase), nameof(Scp106VigorAbilityBase.VigorAmount))) + offset; - newInstructions.RemoveAt(index); - - newInstructions.InsertRange( - index, - new CodeInstruction[] - { - // Player.Get(base.Owner).Role - new(OpCodes.Ldarg_0), - new(OpCodes.Call, PropertyGetter(typeof(StandardSubroutine), nameof(StandardSubroutine.Owner))), - new(OpCodes.Call, Method(typeof(Player), nameof(Player.Get), new[] { typeof(ReferenceHub) })), - new(OpCodes.Callvirt, PropertyGetter(typeof(Player), nameof(Player.Role))), - - // (Player.Get(base.Owner).Role as Scp106Role).VigorRegeneration - new(OpCodes.Isinst, typeof(Scp106Role)), - new(OpCodes.Callvirt, PropertyGetter(typeof(Scp106Role), nameof(Scp106Role.VigorRegeneration))), - }); - - for (int z = 0; z < newInstructions.Count; z++) - yield return newInstructions[z]; - - ListPool.Pool.Return(newInstructions); - } - } -} From 4654bf21815cb2a478d63c1e978f2f6e28a12119 Mon Sep 17 00:00:00 2001 From: x3rt Date: Wed, 31 Jul 2024 16:26:25 -0600 Subject: [PATCH 18/28] Clear Ammo before Clearing Items (#4) --- EXILED/Exiled.API/Features/Player.cs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/EXILED/Exiled.API/Features/Player.cs b/EXILED/Exiled.API/Features/Player.cs index 4991e13d4..def165726 100644 --- a/EXILED/Exiled.API/Features/Player.cs +++ b/EXILED/Exiled.API/Features/Player.cs @@ -2728,8 +2728,8 @@ public void ResetInventory(IEnumerable newItems) /// public void ClearInventory(bool destroy = true) { - ClearItems(destroy); ClearAmmo(); + ClearItems(destroy); } /// From 596a425645cfd7e23360fd92da89616ce64aed01 Mon Sep 17 00:00:00 2001 From: Jesus QC <69375249+Jesus-QC@users.noreply.github.com> Date: Thu, 1 Aug 2024 01:21:28 +0200 Subject: [PATCH 19/28] fetching master (#138) Co-authored-by: Nameless <85962933+Misfiy@users.noreply.github.com> Co-authored-by: Misaka-ZeroTwo <45165615+Misaka-ZeroTwo@users.noreply.github.com> --- .github/labeler.yml | 13 ++++++------- .github/workflows/main.yml | 2 +- .github/workflows/release.yml | 4 ++-- EXILED/Exiled.Installer/Program.cs | 4 ++-- EXILED/Exiled.Loader/Updater.cs | 4 ++-- 5 files changed, 13 insertions(+), 14 deletions(-) diff --git a/.github/labeler.yml b/.github/labeler.yml index 34ff31f3f..5098459b0 100644 --- a/.github/labeler.yml +++ b/.github/labeler.yml @@ -13,29 +13,28 @@ Scripts: # Add the 'Scripts' label regarding-events: # Add the 'Events' label - changed-files: - - any-glob-to-any-file: Exiled.Events/** # Any Modifications to events + - any-glob-to-any-file: EXILED/Exiled.Events/** # Any Modifications to events regarding-api: # Add the 'API' label - changed-files: - - any-glob-to-any-file: Exiled.API/** # Any modifications to the API + - any-glob-to-any-file: EXILED/Exiled.API/** # Any modifications to the API regarding-transpiler: # Add the 'transpiler' label - changed-files: - - any-glob-to-any-file: Exiled.Events/Patches/**/* # Any modifications to transpiler files + - any-glob-to-any-file: EXILED/Exiled.Events/Patches/**/* # Any modifications to transpiler files CustomModules: # Add the 'CustomModules' label - changed-files: - - any-glob-to-any-file: Exiled.CustomModules/** # Any modifications to CustomModules + - any-glob-to-any-file: EXILED/Exiled.CustomModules/** # Any modifications to CustomModules Installer: # Add the 'Installer' label - changed-files: - - any-glob-to-any-file: Exiled.Installer/** # Any modifications to the Installer + - any-glob-to-any-file: EXILED/Exiled.Installer/** # Any modifications to the Installer Localization: # Add the 'Localization' label - changed-files: - - any-glob-to-any-file: Localization/** # Any modifications to Localization + - any-glob-to-any-file: EXILED/Localization/** # Any modifications to Localization GitHub_Actions: # Add the 'GitHub' label - changed-files: - any-glob-to-any-file: .github/** # Any modifications to github related files - diff --git a/.github/workflows/main.yml b/.github/workflows/main.yml index 7be77c41a..6f9bc0f85 100644 --- a/.github/workflows/main.yml +++ b/.github/workflows/main.yml @@ -13,7 +13,7 @@ defaults: working-directory: ./EXILED env: - EXILED_REFERENCES_URL: https://Exiled-Official.github.io/SL-References/Master.zip + EXILED_REFERENCES_URL: https://exmod-team.github.io/SL-References/Master.zip EXILED_REFERENCES_PATH: ${{ github.workspace }}/EXILED/References jobs: diff --git a/.github/workflows/release.yml b/.github/workflows/release.yml index bcbe907cc..efdac4cc8 100644 --- a/.github/workflows/release.yml +++ b/.github/workflows/release.yml @@ -11,9 +11,9 @@ defaults: working-directory: ./EXILED env: - EXILED_REFERENCES_URL: https://Exiled-Official.github.io/SL-References/Dev.zip + EXILED_REFERENCES_URL: https://exmod-team.github.io/SL-References/Dev.zip EXILED_REFERENCES_PATH: ${{ github.workspace }}/EXILED/References - EXILED_DLL_ARCHIVER_URL: https://github.com/Exiled-Official/EXILED-DLL-Archiver/releases/latest/download/EXILED-DLL-Archiver.exe + EXILED_DLL_ARCHIVER_URL: https://github.com/ExMod-Team/EXILED-DLL-Archiver/releases/latest/download/EXILED-DLL-Archiver.exe jobs: build: diff --git a/EXILED/Exiled.Installer/Program.cs b/EXILED/Exiled.Installer/Program.cs index 34912cc51..559c17c82 100644 --- a/EXILED/Exiled.Installer/Program.cs +++ b/EXILED/Exiled.Installer/Program.cs @@ -42,7 +42,7 @@ internal enum PathResolution internal static class Program { - private const long RepoID = 828620622; + private const long RepoID = 833723500; private const string ExiledAssetName = "exiled.tar.gz"; // This is the lowest version the installer will check to install @@ -303,4 +303,4 @@ private static Release FindRelease(CommandSettings args, IEnumerable re return enumerable.First(); } } -} \ No newline at end of file +} diff --git a/EXILED/Exiled.Loader/Updater.cs b/EXILED/Exiled.Loader/Updater.cs index 6990c1812..fb0636570 100644 --- a/EXILED/Exiled.Loader/Updater.cs +++ b/EXILED/Exiled.Loader/Updater.cs @@ -31,7 +31,7 @@ namespace Exiled.Loader /// internal sealed class Updater { - private const long REPOID = 828620622; + private const long REPOID = 833723500; private const string INSTALLER_ASSET_NAME_LINUX = "Exiled.Installer-Linux"; private const string INSTALLER_ASSET_NAME_WIN = "Exiled.Installer-Win.exe"; @@ -332,4 +332,4 @@ private bool FindAsset(string assetName, Release release, out ReleaseAsset asset return false; } } -} \ No newline at end of file +} From 2b0276b62ba06808e4ccf900ef58152f889d55b6 Mon Sep 17 00:00:00 2001 From: Misaka-ZeroTwo <45165615+Misaka-ZeroTwo@users.noreply.github.com> Date: Thu, 1 Aug 2024 20:49:03 +0800 Subject: [PATCH 20/28] Update labeler.yml --- .github/labeler.yml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/.github/labeler.yml b/.github/labeler.yml index 5098459b0..97048dd23 100644 --- a/.github/labeler.yml +++ b/.github/labeler.yml @@ -35,6 +35,6 @@ Localization: # Add the 'Localization' label - changed-files: - any-glob-to-any-file: EXILED/Localization/** # Any modifications to Localization -GitHub_Actions: # Add the 'GitHub' label +GitHub: # Add the 'GitHub' label - changed-files: - any-glob-to-any-file: .github/** # Any modifications to github related files From 04bffe85addfc161051d32bb41fc2828062d21d1 Mon Sep 17 00:00:00 2001 From: Misaka-ZeroTwo <45165615+Misaka-ZeroTwo@users.noreply.github.com> Date: Thu, 1 Aug 2024 20:49:20 +0800 Subject: [PATCH 21/28] Update labeler.yml --- .github/labeler.yml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/.github/labeler.yml b/.github/labeler.yml index 5098459b0..97048dd23 100644 --- a/.github/labeler.yml +++ b/.github/labeler.yml @@ -35,6 +35,6 @@ Localization: # Add the 'Localization' label - changed-files: - any-glob-to-any-file: EXILED/Localization/** # Any modifications to Localization -GitHub_Actions: # Add the 'GitHub' label +GitHub: # Add the 'GitHub' label - changed-files: - any-glob-to-any-file: .github/** # Any modifications to github related files From 0698e6ee9f55adae1f2e37375226842b3986fef4 Mon Sep 17 00:00:00 2001 From: ZeroTwo <63092138+NotZer0Two@users.noreply.github.com> Date: Thu, 1 Aug 2024 19:41:18 +0200 Subject: [PATCH 22/28] `[Exiled::API]` Added WhitelistedPlayers, SetIntercomDisplayTextForTargetOnly and ResetIntercomDisplayText (#6) * Sync Changes * Suggestion Co-authored-by: Misaka-ZeroTwo <45165615+Misaka-ZeroTwo@users.noreply.github.com> --------- Co-authored-by: Misaka-ZeroTwo <45165615+Misaka-ZeroTwo@users.noreply.github.com> --- EXILED/Exiled.API/Extensions/MirrorExtensions.cs | 13 +++++++++++++ EXILED/Exiled.API/Features/Server.cs | 5 +++++ 2 files changed, 18 insertions(+) diff --git a/EXILED/Exiled.API/Extensions/MirrorExtensions.cs b/EXILED/Exiled.API/Extensions/MirrorExtensions.cs index 8b30327d4..2dd66766c 100644 --- a/EXILED/Exiled.API/Extensions/MirrorExtensions.cs +++ b/EXILED/Exiled.API/Extensions/MirrorExtensions.cs @@ -25,6 +25,7 @@ namespace Exiled.API.Extensions using PlayerRoles; using PlayerRoles.FirstPersonControl; using PlayerRoles.PlayableScps.Scp049.Zombies; + using PlayerRoles.Voice; using RelativePositioning; using Respawning; @@ -181,6 +182,18 @@ public static void PlayGunSound(this Player player, Vector3 position, ItemType i player.Connection.Send(message); } + /// + /// Sets that only the player can see. + /// + /// Only this player can see Display Text. + /// Text displayed to the player. + public static void SetIntercomDisplayTextForTargetOnly(this Player target, string text) => target.SendFakeSyncVar(IntercomDisplay._singleton.netIdentity, typeof(IntercomDisplay), nameof(IntercomDisplay.Network_overrideText), text); + + /// + /// Resync . + /// + public static void ResetIntercomDisplayText() => ResyncSyncVar(IntercomDisplay._singleton.netIdentity, typeof(IntercomDisplay), nameof(IntercomDisplay.Network_overrideText)); + /// /// Sets of a that only the player can see. /// diff --git a/EXILED/Exiled.API/Features/Server.cs b/EXILED/Exiled.API/Features/Server.cs index 26cf64c98..908096434 100644 --- a/EXILED/Exiled.API/Features/Server.cs +++ b/EXILED/Exiled.API/Features/Server.cs @@ -178,6 +178,11 @@ public static bool IsWhitelisted set => ServerConsole.WhiteListEnabled = value; } + /// + /// Gets the list of user IDs of players currently whitelisted. + /// + public static HashSet WhitelistedPlayers => WhiteList.Users; + /// /// Gets a value indicating whether or not this server is verified. /// From 2e1686e120528c4d7dfaf7b6f1ec7d369ad33a26 Mon Sep 17 00:00:00 2001 From: Misaka-ZeroTwo <45165615+Misaka-ZeroTwo@users.noreply.github.com> Date: Fri, 2 Aug 2024 01:46:22 +0800 Subject: [PATCH 23/28] Fix ChargingJailbird (#2) * Update ChargingJailbirdEventArgs.cs * Update JailbirdPatch.cs * Update dev.yml * Update labeler.yml --- .../EventArgs/Item/ChargingJailbirdEventArgs.cs | 11 ++++++++++- .../Patches/Events/Item/JailbirdPatch.cs | 5 +---- 2 files changed, 11 insertions(+), 5 deletions(-) diff --git a/EXILED/Exiled.Events/EventArgs/Item/ChargingJailbirdEventArgs.cs b/EXILED/Exiled.Events/EventArgs/Item/ChargingJailbirdEventArgs.cs index 1b17a1bb0..38f6ea7f8 100644 --- a/EXILED/Exiled.Events/EventArgs/Item/ChargingJailbirdEventArgs.cs +++ b/EXILED/Exiled.Events/EventArgs/Item/ChargingJailbirdEventArgs.cs @@ -7,6 +7,8 @@ namespace Exiled.Events.EventArgs.Item { + using System; + using Exiled.API.Features; using Exiled.API.Features.Items; using Exiled.Events.EventArgs.Interfaces; @@ -26,7 +28,9 @@ public ChargingJailbirdEventArgs(ReferenceHub player, InventorySystem.Items.Item { Player = Player.Get(player); Item = Item.Get(swingItem); +#pragma warning disable CS0618 IsAllowed = isAllowed; +#pragma warning restore CS0618 } /// @@ -42,6 +46,11 @@ public ChargingJailbirdEventArgs(ReferenceHub player, InventorySystem.Items.Item /// /// Gets or sets a value indicating whether or not the Jailbird can be charged. /// - public bool IsAllowed { get; set; } + public bool IsAllowed + { + get; + [Obsolete("This event cannot be denied as it will cause desync.")] + set; + } } } diff --git a/EXILED/Exiled.Events/Patches/Events/Item/JailbirdPatch.cs b/EXILED/Exiled.Events/Patches/Events/Item/JailbirdPatch.cs index ec33236e0..1f8489fd3 100644 --- a/EXILED/Exiled.Events/Patches/Events/Item/JailbirdPatch.cs +++ b/EXILED/Exiled.Events/Patches/Events/Item/JailbirdPatch.cs @@ -88,10 +88,7 @@ private static bool HandleJailbird(JailbirdItem instance, JailbirdMessageType me ChargingJailbirdEventArgs ev = new(instance.Owner, instance); Item.OnChargingJailbird(ev); - if (ev.IsAllowed) - return true; - instance.SendRpc(JailbirdMessageType.ChargeFailed, null); - return false; + return true; } default: From ef07853c3740c51f5379be7c4a96d377811af77f Mon Sep 17 00:00:00 2001 From: VALERA771 <72030575+VALERA771@users.noreply.github.com> Date: Thu, 1 Aug 2024 22:10:58 +0300 Subject: [PATCH 24/28] Adding auto assignment to pr (#7) * Create auto-assigning.yml * Update and rename labeler.yml to pull_request_opened.yml * Delete .github/workflows/auto-assigning.yml --- .github/workflows/{labeler.yml => pull_request_opened.yml} | 4 ++++ 1 file changed, 4 insertions(+) rename .github/workflows/{labeler.yml => pull_request_opened.yml} (79%) diff --git a/.github/workflows/labeler.yml b/.github/workflows/pull_request_opened.yml similarity index 79% rename from .github/workflows/labeler.yml rename to .github/workflows/pull_request_opened.yml index 0486bfaec..aa26845fb 100644 --- a/.github/workflows/labeler.yml +++ b/.github/workflows/pull_request_opened.yml @@ -20,3 +20,7 @@ jobs: repo-token: ${{ secrets.GITHUB_TOKEN }} configuration-path: .github/labeler.yml sync-labels: true + assign-author: + runs-on: ubuntu-latest + steps: + - uses: toshimaru/auto-author-assign@v2.1.1 From e6661e8f27e23a47591cba79d08e477490d2284f Mon Sep 17 00:00:00 2001 From: Jesus QC <69375249+Jesus-QC@users.noreply.github.com> Date: Thu, 1 Aug 2024 21:31:13 +0200 Subject: [PATCH 25/28] Update dev.yml --- .github/workflows/dev.yml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/.github/workflows/dev.yml b/.github/workflows/dev.yml index 6a9486427..fc2b53f4f 100644 --- a/.github/workflows/dev.yml +++ b/.github/workflows/dev.yml @@ -14,7 +14,7 @@ defaults: working-directory: ./EXILED env: - EXILED_REFERENCES_URL: https://Exiled-Official.github.io/SL-References/Dev.zip + EXILED_REFERENCES_URL: https://exmod-team.github.io/SL-References/Master.zip EXILED_REFERENCES_PATH: ${{ github.workspace }}/EXILED/References EXILED_DLL_ARCHIVER_URL: https://github.com/Exiled-Official/EXILED-DLL-Archiver/releases/latest/download/EXILED-DLL-Archiver.exe From fe05d8dd6026365e9b1215913ffd8200d0c6823c Mon Sep 17 00:00:00 2001 From: Jesus QC <69375249+Jesus-QC@users.noreply.github.com> Date: Thu, 1 Aug 2024 21:31:50 +0200 Subject: [PATCH 26/28] fixed docs pipeline --- .github/workflows/docs.yml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/.github/workflows/docs.yml b/.github/workflows/docs.yml index 351cdd3be..df73ad9a5 100644 --- a/.github/workflows/docs.yml +++ b/.github/workflows/docs.yml @@ -12,7 +12,7 @@ permissions: id-token: write env: - EXILED_REFERENCES_URL: https://Exiled-Official.github.io/SL-References/Dev.zip + EXILED_REFERENCES_URL: https://exmod-team.github.io/SL-References/Master.zip EXILED_REFERENCES_PATH: ${{ github.workspace }}/EXILED/References # Allow only one concurrent deployment, skipping runs queued between the run in-progress and latest queued. From 5783c17177f406792b3b4f83a5a0f46ed4b1089a Mon Sep 17 00:00:00 2001 From: Misaka-ZeroTwo <45165615+Misaka-ZeroTwo@users.noreply.github.com> Date: Fri, 2 Aug 2024 05:24:38 +0800 Subject: [PATCH 27/28] Pull request template (#10) * Create pull_request_template.md * Update pull_request_template.md * Update pull_request_template.md * Update pull_request_template.md * Update pull_request_template.md --- .github/pull_request_template.md | 35 ++++++++++++++++++++++++++++++++ 1 file changed, 35 insertions(+) create mode 100644 .github/pull_request_template.md diff --git a/.github/pull_request_template.md b/.github/pull_request_template.md new file mode 100644 index 000000000..032dc22c6 --- /dev/null +++ b/.github/pull_request_template.md @@ -0,0 +1,35 @@ +## Description +**Describe the changes** + + +**What is the current behavior?** (You can also link to an open issue here) + + +**What is the new behavior?** (if this is a feature change) + + +**Does this PR introduce a breaking change?** (What changes might users need to make in their application due to this PR?) + + +**Other information**: + +
+ +## Types of changes + +- [ ] Bug fix (non-breaking change which fixes an issue) +- [ ] New feature (non-breaking change which adds functionality) +- [ ] Breaking change (fix or feature that would cause existing functionality to change) +- [ ] Documentations +
+ +## Submission checklist + +- [ ] I have checked the project can be compiled +- [ ] I have tested my changes and it worked as expected + +### Patches (if there are any changes related to Harmony patches) +- [ ] I have checked no IL patching errors in the console + +### Other +- [ ] Still requires more testing From 0b577df72c4956d5dff1c9e9087cfa6b52674d39 Mon Sep 17 00:00:00 2001 From: Alex Rouse <123724383+ALEXWARELLC@users.noreply.github.com> Date: Fri, 2 Aug 2024 18:29:22 +0800 Subject: [PATCH 28/28] Possible fix for broken GitHub Action. (#25) --- .github/workflows/pull_request_opened.yml | 3 +++ 1 file changed, 3 insertions(+) diff --git a/.github/workflows/pull_request_opened.yml b/.github/workflows/pull_request_opened.yml index aa26845fb..a54bed971 100644 --- a/.github/workflows/pull_request_opened.yml +++ b/.github/workflows/pull_request_opened.yml @@ -22,5 +22,8 @@ jobs: sync-labels: true assign-author: runs-on: ubuntu-latest + permissions: + pull-requests: write + steps: - uses: toshimaru/auto-author-assign@v2.1.1