Skip to content

Releases: ScriptedEvents/ScriptedEvents

Version 3.5.0 for EXILED 9.10.0

25 Oct 16:18

Choose a tag to compare

Changes

  • Updated to EXILED 9.10.0, fixing console errors

Version 3.4.0 for EXILED 9.8.0+

06 Sep 09:08

Choose a tag to compare

Bug fixes:

  • Fixed the !-- EVENT flag, courtesy of exiled devtools

Breaking changes:

  • None

Additions:

  • {STR-FLOORIFY} variable

Version 3.2.3

17 Nov 14:10

Choose a tag to compare

Version 3.2.3 is here!

Breaking changes:

  • None!

Additions:

  • New LastPlayerState feature for Left and ChangingRole events

Detailed Update Overview (Click to see the video)

Watch the video

Join our Discord server!

DISCORD

Version 3.2.2

11 Nov 21:12

Choose a tag to compare

Added

  • EFFECTIMMUNITYRULE action
  • {MAPSEED} variable

(these features were supposed to be added much earlier, but this did not happen due to our VCS issues)

Fixed

  • {CUFFER} variable not being usable as intended

Version 3.2.1

09 Nov 11:39

Choose a tag to compare

Fixes

  • TRIGGER action error on invalid event key

Additions

  • {CUFFER} variable
  • Demo scripts "HitMarker", "PeanutRun", "DogHideAndSeek" and "JoinBroadcast"

Other

  • Updated and expanded the credit system for the Scripted Events Team

Join our Discord server!

DISCORD

Version 6.6.6 (v3.2.0)

31 Oct 18:22

Choose a tag to compare

Happy Halloween! A very spooky version 6.6.6 has been released!

Changes

  • Updated to Exiled 8.13.1
  • Fixed spooky null reference exceptions
  • Updated all sample scripts to work with the current version
  • SE will scream at you if scripts with the same names exist
  • Fixed the scr exa command
  • Documentation generator will now require you to have matching plugin and documentation versions
  • Improved vague documentation generator messages

Join our Discord server!

DISCORD

Version 3.1.8

06 Oct 18:21

Choose a tag to compare

Fixed:

  • errors in server console lacking the script and line context
  • NPCs being accepted as event players in scripts using !-- EVENT flags
  • the GROUP option in {GET} variable returning an empty string instead of "NONE" when player has no group

Join our Discord server!

DISCORD

Version 3.1.7

20 Aug 13:29

Choose a tag to compare

The v3.1.7 is here to polish all the rough edges found in the v3.1.6!

Fixed:

  • argument errors not showing the error content
  • demo scripts and samples not being up to date
  • the GOTO invalid label warn being absolutely useless

Join our Discord server!

DISCORD

Version 3.1.6

18 Aug 17:59

Choose a tag to compare

Another release with another batch of amazing features and the obligatory bug fixes. Thank you all for the constant support in the development of SE!

Better EXILED event integration

A long awaited feature has finally been added; every EXILED event variable will now be available as a Scripted Events variable! But what does it change?

  • You will now be able to access a lot more information from your event

    Lists, dictionaries and arrays are currently not supported; this will be added in the next update. If you try to access a list variable you will be greeted with something similar to System.Collections.Generic.List'1[ItemType].

  • All documentation in EXILED events should line up with Scripted Events
  • Old scripts should be unaffected

Note

Scripts triggered by events start running only after the event has happened. This is important to keep in mind as EXILED event variables are usually referencing the state before the event has happened.

Tip

Try to limit the amount of unnecessary EXILED event scripts, as they may to take up to 6ms to process all of the event variables.

But that's not all!

Using the EVENT action, you can now block any deniable EXILED event! This works similar to DISABLEPLAYER action, but with much more flexibility + the event doesn't have to be a player event.

There is also a tutorial attached to the action for how to check if an event is deniable.

API finally gets some love

The API has been reworked to add new features and fix some legacy bugs.

We now also have an extensive up-to-date example of our API in action available here.

Note

Other plugins using the SE API might take some time before updating to the newer version. You can contact the respective plugin developers in order to inform them about the change, if it causes any issues.

Smart arguments

There is a new way of handling action inputs: Smart arguments! These allow you to effortlessly pass arguments to actions in ways not possible before, as well as making scripts more readable.

Here are 2 examples of smart args in action:

# look how we have to make a new variable >:(
LOCAL {CAMP_TIME} {GET:PLR:CampingTime} + 1
PLAYERDATA SET {PLR} CampingTime {CAMP_TIME}

# less syntax & doesnt create useless variables!
PLAYERDATA SET {PLR} CampingTime #1
// {GET:PLR:CampingTime} + 1
# this line is one of the reasons smart arguments were added lmao
CALL FuncIsInRange {GET:PLR:LastPosX} {GET:PLR:LastPosY} {GET:PLR:LastPosZ} {GET:EVPLAYER:POSX} {GET:EVPLAYER:POSY} {GET:EVPLAYER:POSZ} 12

# and thats how it looks with smart args
CALL FuncIsInRange #1 #2 #3 #4 #5 #6 #7
// {GET:PLR:LastPosX} 
// {GET:PLR:LastPosY} 
// {GET:PLR:LastPosZ} 
// {GET:EVPLAYER:POSX} 
// {GET:EVPLAYER:POSY} 
// {GET:EVPLAYER:POSZ} 
// 12

Warning

Smart arguments will try to perform math and condition checks before passing the value. Because of that, player variables do not work with smart arguments. This issue will be addressed in a later release.

Note

Some actions (especially third-party ones) might not fully support this feature. Please keep that in mind when using.

Value extraction from actions

Value extraction is a tool for a better way returning values using actions!

image

Variables can be named in any way, the only thing that matters is the order in which they are named. The 1st variable on the left will receive the 1st value returned by the action, the 2nd variable will get the 2nd value and so on.

Important

If there isn't any value for variables to take (like when there are too little values returned), they will not be created at all.
It's good to check if the variable was created using the {VEXISTS} variable.

As of now, this system is used only by custom actions made with the API, but going forward this will be the default system for creating variables in Scripted Events.

Full changelog

Additions

Actions

  • EVENT

    disable any event for specified players

  • SPAWNRAGDOLL

    spawn ragdolls at the specified XYZ coordinates

  • TPPLAYER action

    teleport one or more players to another player

  • DROPITEM action

    drop specified items from player inventories

Variables

  • AHP mode to {GET} variable

    check how much AHP a player has

  • VARIABLES option to {THIS} variable

    check what local variables are available

  • {STR-UPPER} variable

    make all letters in the variable uppercase

  • {STR-LOWER} variable

    make all letters in the variable lowercase

  • {STR-REMOVE} variable

    remove specified letters in the variable

  • Smart arguments
  • Variable extraction

Refactors

Note

Please ensure that all of your scripts are updated using the information below.

  • LOBBYLOCK TRUE -> LOBBY LOCK
  • LOBBYLOCK FALSE -> LOBBY UNLOCK
  • ROUNDLOCK TRUE -> ROUND LOCK
  • ROUNDLOCK FALSE -> ROUND UNLOCK
  • ROUNDSTART -> ROUND START
  • ROUNDEND -> ROUND END
  • ADDTO -> APPEND
  • {GET} variable will now return UNDEFINED instead of NONE when provided with an invalid key

Fixed

  • {GET} variable ITEMCOUNT and ITEMS keys
  • Scripts stopping when variable syntax is not used properly
  • HTTPPOST not processing variables
  • Event scripts not running after a round restart
  • API not working when used by a plugin with a priority higher than SE
  • \n not working for PRINTPLAYER action
  • Some errors not appearing when running a script from Remote Admin console

v3.0.0

26 Jun 14:16

Choose a tag to compare

Version 3.0

It's real guys. This is a HUGE release, which means likely (definitely) all of your scripts will not function after updating. Don't worry, we will be available to help on our Discord server.

Main changes

They aren't ordered in any way, just so you know :trollface:

shelp documentation generator

Tired of constantly using shelp for every single action/variable? Fear not, for now you can generate updated documentation on your PC, with descriptions and examples directly from the plugin's source code. Run shelp GENERATE in your server console to begin.
Disclaimer: This generated documentation will not update when SE updates, you'll need to re-run the generate command.

New safety system

We are glad to introduce to you our new safety system for ScriptedEvents! Thanks to it, you don't have to worry about your script crashing the server or the script randomly stopping. It's actually really simple; a tiny delay is added after every completed action. This delay is dependent on the tick speed on your server, where one action will be executed every tick. This shouldn't affect most scripts, but if you require the most performance, you can use the !-- NOSAFETY flag to remove the delay.

Multi-line comments

It's a very simple addition, but it's surprisingly helpful for creating script documentation. To enter or exit a multi-line comment, you have to use a double hashtag (##). If you leave a single double hashtag at the beginning of the script, it will be treated as the entire script being a comment. This is easier to spot if you use our VS Code extension.

##
look at
this beautiful
multi line comment!
##

PRINT hello!

Local variables

You can now use LOCAL and LOCALPLAYERVAR actions to manage variables accessible in that script only! We recommend you always use local variables unless you want the variable to be accessible in other scripts on purpose.

Custom events

Using the new TRIGGER action, you can register your own events and subscribe to other events using the !-- CUSTOMEVENT flag.

# example script 1
!-- CUSTOMEVENT test
LOG Tested!
# example script 2
LOG Testing!
TRIGGER test
output:
> Testing!
> Tested!

Folders

Instead of having one giant folder for everything, Scripted Events will now separate everything into custom subfolders. This includes Scripts, Documentation and VariableStorage folders (and Commands folder in the future).

Action and variable reworks

Close to all actions and variables were modified in some way or another. Do not assume that if a certain action still exists, it works in the exact same way. We recommend you have a good look at the new documentation before updating your scripts.

New error system

Errors should now provide you with a lot more information and be a lot more consistent. You can also get more information about them using shelp. Here is an example of the shelp SE-108 command:

=== ERROR CODE ===
ID: SE-108
The specified event '{0}' in the 'On' config was not found!
This error occurs when an invalid event name is provided in the on Exiled config. This error can be resolved by checking for typos in the name of events and referencing Exiled's list of provided events.

Argument processing

Our new ArgumentProcessor will verify if all of the action arguments provided are of the correct type before the action is executed. Together with the new error system, this will help with finding all argument related bugs in your scripts.

Functions

Functions are reusable snippets of code, allowing you to stop copy pasting the same code over and over again in different places. These are very powerful and we aim to upgrade ScriptedEvents from being a procedural programming language to a functional programming language in the future!

Function labels

Function labels work similarly to labels, but they have a defined end. When you reach the end of a function label, the script will continue execution from the last place the function was called from. Function labels use -> and <- syntax.

# example script
LOG i'm gonna call a function
GOTO Function
LOG i left a function
STOP

-> Function
LOG i'm inside of a function
<-
output:
> i'm gonna call the function
> i'm inside of the function
> i left the function

Function scripts

Function scripts are normal scripts, but they're not to be called by a player, but rather another script. You can also provide and return values to and from a function script. When values are provided to a called script, they will be encapsulated in variables like {ARG1}, {ARG2} etc.. When variables are returned from a script, they inherit their name from the function script.

# example script
CALL GetRandomPlayer {PLAYERS} 
LOG Our random player is: {GET:RANDOM_PLAYER:NAME}
# example function script GetRandomPlayer.txt
IF {!VEXISTS:ARG1}
    ERROR {THIS} - players were not provided 
    STOP
ENDIF

LOCALPLAYERVAR SET {RANDOM_PLAYER} {LIMIT:ARG1:1}
RETURN {RANDOM_PLAYER}
output:
> Our random player is: Josh

Action decorators

Action decorators are things you put after an action, which modify the behavior of said action. There are currently 2 action decorators: $IF and $FOR.

$IF action decorator

$IF allows an action to execute only if the condition provided results in TRUE.

# example script
LOG Players: {PLAYERS}
LOG players on server $IF {PLAYERS} > 0
LOG no players on server $IF {PLAYERS} = 0
output:
> Players: 0
> no players on server

$FOR action decorator

$FOR is a decorator that will repeat an action per every player in a variable, and assigning said player to its own variable. It follows the following syntax - $FOR [singlePlayerVar] IN [loopingPlayerVar], where [singlePlayerVar] is the variable which will be assigned the player currently looping through, and [loopingPlayerVar] is the variable from which the players will be looped over.

# example script
LOG Hello, {GET:PLR:NAME}! $FOR {PLR} IN {PLAYERS}
output:
> Hello, John!
> Hello, Jack!
> Hello, Josh!

Using $IF and $FOR together

These decorators are very powerful, but what if we were to combine them? Using this syntax - $IF [condition] $FOR [singlePlayerVar] IN [loopingPlayerVar] we can run a certain action per each player, but only if the condition is met for that player.

# example script
LOG All players: {DISPLAY:PLAYERS}
LOG {GET:PLR:NAME} has low hp ({GET:PLR:HP}) $IF {GET:PLR:HP} < 40 $FOR {PLR} IN {PLAYERS}
output:
> All players: Josh, Jack, John
> Jack has low hp (37)
> John has low hp (14)

This is where the functions come in

As good as that is, there is one drawback to it; readability. Fortunately, we have a solution to that! Using function labels, we can create a function that will be called for every player, and the rest of the logic can stay inside of that function. This is how it would look like when using functions:

# example script 
LOG All players: {DISPLAY:PLAYERS}
GOTO LowHealthInfo $FOR {PLR} IN {PLAYERS} 
STOP

-> LowHealthInfo
<- $IF {GET:PLR:HP} < 40

LOG {GET:PLR:NAME} has low hp ({GET:PLR:HP}) 
<-
output:
> All players: Josh, Jack, John
> Jack has low hp (37)
> John has low hp (14)

Case insensitivity

Do you hate writing all actions and variables in UPPERCASE? Constantly juggling with shift is kind of a pain, and we know it. Fortunately, version 3.0 introduces case insensitivity for actions and variables. Of course, the "recommended" way will still be writing actions and variables in uppercase, but who cares?

log we have {players} players on the server: {display:players}
output:
> we have 3 players on the server: Josh, Jack, John

New IF "statements"

Version 3.0 introduces a new way of handling IF statements! IF action now works completely differently. Instead of stopping the script if the condition evaluates to FALSE, the script will continue executing, but actions will be blocked from running. The block will be lifted after encountering an ENDIF action. There also exists a FLIPIF action, which will flip the state of the IF block, so if action execution was blocked before, it won't be after it.

Because these are not actual statements, it means that you stack them. This is tragic since it forces people to write something known as "clean code".

# example script
!-- EVENT ChangingItem

# ev item will not be provided when player changes to an empty hand
IF {VEXISTS:EVITEM}
    LOG EVITEM exists, were good to go
FLIPIF
    LOG EVITEM does not exist, stopping the script
    STOP
ENDIF

LOG simulating work here…
output (when changing to an empty hand):
> EVITEM does not exist, stopping the script

output (when changing to a valid item):
> EVITEM exists, were good to go
> simulating work here…

Indentation

If you weren't using one of the bajillion pre-release versions of 3.0, you are probably surprised to see indentation being used in SE. How does this affect the way you have to write scripts? Well, fear not, as indentation is only just pure formatting sugar! When scripts are read and cached, all indentation is removed. It exists just so quiche eaters could have some false sense of safety.

Full Changelog

We have probably missed some stuff along these like 5 months of development, so we attached the full changelog for those brave enough to try and read it.
v2.8.0...v3.0.0