#plugins-dev-chat
1 messages ยท Page 31 of 1
Magic
wdym modified
new position
it's only cached within one update
it won't be changed during that update
it's why I clear the cache at the start of the update
Ok so
you cache the target
and from there if they have it just sent it
or the reciver?
because both could be
I cache this
if we have a relative position for the target's position, we use it
else we create & cache it
yes its so complicated
because there's like thousands of class
for this
I'll be honest
I don't like relative positioning
I find it somewhat overkill for what it's meant to achieve
You can always round up to 3rd one in float
not even necessary
Example here i don't even see what you mention
And isn't big, 12 byte (4,4,4)
Decimal
With higher player counts
but can't you optimize it even more
if you check the position is the same instead of clearing it
16*3 
I don't know the specifics about the relative positioning in detail enough to know if doing so could cause issues
so I opted to cache per-frame
If we could eliminate the transform getter that would be poggies
safest option which gives huge results anyway
You should open source it so we can contribute to SecretFine
Or LabFine
Btw can be done by sending extra bool here with isinvisible so it doesnt sends the default of the data
If I get permission from the head honchos at Brights mayhaps
If he does
In the meantime you've got all the info to reproduce it yourself
i will try to contribute it
Let's gooo
because it could be a game changer
but wait
now that i think about it
i did similar thing
when i was working on the 100 players for lars
caching defo helps for 100 players but round robin adds a lot to it as well
Honestly bro if you can open it, i will try to contribute because i found some stuff myself in the past that lagged the server
and i've managed to make a server with 100 player moving randomly to 5 tps to just 40
Doubt the plugin will be open source, but I might be able to get permission for some gists
It's not too complicated
just alot of thinking and time
Next up on my list is adaptive update rates
Goal is 30 TPS minimum @ 48 players on a single-core server
buy better hosting 
optimization by transpiler 
Slowly getting it there bit by bit
SINGLe CORE?
yeah
Pentium
trust me i did optimize primitives
and they are quite a pain
Not like the game needs 32 cores per server
Ye i know u did that
i got yesterday 10fps more on a 100k schematic
so a win is a win
that is already implemented
How do u delete a non networked go?
Object.Destroy?
secret :3
I mean
they are all client side
100% of all of the primitives are client side
only like ServerSide one with Components aren't
probs a mirror message
yes
Hey all client, destroy this game object

trust me 90% of the stuff is unknown shit i do
Gatekeepers
and 10% is optimizing
I cannot release it
And 99% you don't know that to do
nor talk in a specific way
im just optimizing so much that its even hard to make more optimization
at some point it will be impossible
fr

you gave me an idea
I NEED those FPS
i want to run 100M primitives
in one server
now im in half
so only 50M is the max before ram runs out
and server cpu explodes
You can if the server gets disbanded 
Just don't send all at once
nope :3
I implemented a different approch
I spawned like 10*RoomCount coins and server froze for like 10sec
my server doesn't even freeze
60 tps
stable
with 200k primitives in total
:3
50M makes the server at 50 TPS
Well those are client side not server
server are 3/4

and even those are optimized :3
I just don't have anything else to optimize
I optimized it so much
that its impossible
Animations
never
possile
BUT
i've made a way
that i can run a version of them
actually with client side ones :3
public sealed class MapGenerator : IDisposable
{
private GameObject _mapParent;
private CoroutineHandle? _handle;
public event Action OnCompleted;
public float Progress { get; private set; } = -1;
private void InvokeCompleted()
{
Progress = 1;
OnCompleted?.Invoke();
}
private void SpawnMapInstantly()
{
_mapParent = API.SpawnObjects(Map.Objects, MapSpawnPosition);
Logger.Info($"Successfully loaded map {Map.Name}");
InvokeCompleted();
}
private void SpawnMapPeriodically()
{
Logger.Info($"Periodically loading map {Map.Name}");
_mapParent = API.CreateObjects(Map.Objects, MapSpawnPosition);
_handle = Timing.RunCoroutine(SpawnPeriodically());
}
private IEnumerator<float> SpawnPeriodically()
{
yield return Timing.WaitForSeconds(1f);
var components = _mapParent.GetComponentsInChildren<NetworkIdentity>();
var total = (float) components.Length;
for (var i = 0; i < components.Length; i++)
{
var identity = components[i];
Progress = i / total;
var o = identity.gameObject;
if (!identity.TryGetComponent<slocObjectData>(out var data) || data.ShouldBeSpawnedOnClient)
NetworkServer.Spawn(o);
if (i % 100 == 0)
yield return Timing.WaitForSeconds(0.1f);
}
Logger.Info($"Successfully loaded map {Map.Name}");
InvokeCompleted();
}
}
The illusion of slow loading
Looks better with the progressbar though
Me when i
VAL |DATING
What
The I in validating isn't really shown
Same in loading something cuts off cus of the font
trying something for the luls
skipping the update of all dummies
p much zero benefits for normal gameplay since you (generally) don't use em
dummy.gameObject.SetActive(false)
but funny


wish we had access to a profiler
would make hunting and patching performance issues so much easier
idk why that couldn't be a thing
not like PDBs would be an issue considering it's already unobfuscated C#
Already made it a suggestion
Ye its already ifdeffed out
Huh
and then make SL Server in another language
Ah
c++ scp sl server
Have fun 
Nah it's AnsiC
Make the server in JavaScript
: ๐ฅ
in brainfuck
more of a hassle than just patching the oddities out and reporting anything that needs clientside changes to NW
Remove client
Remove Central Server
It will be server side ๐ฅ
no SL
Zig
fortnite
So uhh which one is the observer and which is the SCP
Whereee
Player is 173
Generally you can see it this way: Player is the player concerned with the event.
PlayerHurt: Player is the one that got hurt.
ScpXXX: Player is the SCP
etc etc
bit confusing at first
SSCS?
Server side central server
Ye I was just confused cause my code wasn't working then I realized I needed an !
It happens so much that I accidentally mistype and forget an exclamation mark and wonder why everything broke
the difference is that you arent adding a dupe in the 2nd image
The difference is I actually add to the fucking list in the second image lmao
The list starts empty
In the first nothing ever gets added to it
Cause it's never contained
yeah because you are checking if the player exists, but it never does
Exactly
Lmao I was like "why was my code not working" and then I realized I forgot a !
Central server are written in php so
Is it possible to change door's permission and make panel display new permissions?
is there a way to add a door to door management
when you destroy a doors gameobject thats on door management you can remove it
but is there a way to add one
With primitives maybe but there's no base game way to my knowledge
Add a DoorNametagExtension component and set the DoorName or something
Not sure if it shows up in RA
But with doorTP it works
k
For my plugin Iโm using a local sqlite database. Currently Iโm using Task.Run to perform non-blocking read/write operations. Should I be using something different like the async system unity provides or Job scheduling?
you can keep using tasks or use Unity's Awaitable
Awaitables are preferred
Does the Custom info allow new lines? If I set ci like this
line 1
line 2
``` it says that custom info doesn't match regex
check the validate method
I just don't understand regex
Like wth does this mean ^((?![\\[\\]])[\\p{L}\\p{P}\\p{Sc}\\p{N} ^=+|~`<>\\n]){0,400}$?
Hi @hearty shard I had a quick question if you're available
I got SecretAPI working, but I noticed that the HandleSettingUpdate runs once when the button is pressed, and once when it's depressed
Is there any function or method I can use to run only when the button is pressed, or should I just use a flip-flopping boolean?
if (!IsPressed)
return;
Gotcha
Sorry bit of a dumb question but I really appreciate it haha
yea no worries
there is IsPressed which is derived from SyncIsPressed afaik
negative
why you making the button depressed?
gonna make you depressed
Pretty helpful if you need to understand regexes in the future

you have to resend when setting these
so maybe i should make my settings resync when changed?
idk
id have to rework my thing since it would send the default options
idk
i hate this
im just gonna obsolete the setters
thats the solution atp
nw pls rework SSSS
this shit SUCKS
where you got CallNextFrame ?
0 > 0.1f
does the exact same thing btw LOL

set to (1/60)
120 tick, just like cs lule
does changing ev.Items in PlayerReceivingLoadoutEvent cause the loadout to change?
how to fix fucking micro freezing in visual studio while inputting text or press buttons?
used gpu
in discord same in randomly time
driver issue maybe?
latest doesn't mean the best

windows moment
is there a way to get the displayname of the player that left, when I use PlayerLeft event it returns null
Patch CustomNetworkManager.OnServerDisconnect can't check rn what to patch exactly
Im too lazy to search so
how i can make [No Reports] or other custom text in RA Players?
cedmod has built-in stuff
or
Making custom
[FakePlayers]
create a player
dont show them anywhere except RA
how i know it possible just by patch
as axwabo said, check cedmod
Copy the decompiled code for the Raplayers class
Using my solution requires no additional deps 

using the CommandSystem is much easier to maintain though
since this way, the system can break any time
wait until NW breaks a patch by compiling the game on another machine and thereforce changing a local index
the patch would likely fail
so you wouldn't see RA options
-# has happened before with commands
thats why u use CODEMATCHERS
and then search for the index
won't help if the local index changes
u can search for the index to use
If u replace the whole function u dont need it
like match a section of code around a ldarg.1 / 2 / 3
then get what instruction it is (and the operand)
yea but its futureproof
but for now, not worth it
make a .GetLoadLocal method that returns a new codeinstruction that loads the localindex and a .StoreLoadLocal and whatnot
private static IEnumerable<CodeInstruction> Transpiler(IEnumerable<CodeInstruction> instructions)
{
CodeMatcher codeMatcher = new CodeMatcher(instructions)
.MatchEndForward(
new CodeMatch(OpCodes.Ldloca_S),
new CodeMatch(OpCodes.Call),
new CodeMatch(OpCodes.Isinst))
.SetInstruction(new CodeInstruction(
OpCodes.Call,
Method(typeof(Allow3114SpawnableScpPatch), nameof(IsValidSpawnableRole))));
return codeMatcher.InstructionEnumeration();
}
i match the 3 instructions and now im on Isinst instuction
then i set that instruction
its rly not that much effort
no they're talking about copying the index
hm?
i need to extract the local index to use it
1 sec
btw i'm definitely not gonna get to it soon
i wish opcodes weren't dumb
um
Helper methods for working with SCP:SL plugins. Contribute to Axwabo/SCPSL-Helpers development by creating an account on GitHub.
oh you can't FUCk
right?
never cook again
did i ever cook?
u right
public static CodeMatcher ExtractIndex(this CodeMatcher matcher, out int index)
{
OpCode opcode = matcher.Instruction.opcode;
if (opcode == OpCodes.Ldloc_0 || opcode == OpCodes.Stloc_0)
{
index = 0;
}
else if (opcode == OpCodes.Ldloc_1 || opcode == OpCodes.Stloc_1)
{
index = 1;
}
else if (opcode == OpCodes.Ldloc_2 || opcode == OpCodes.Stloc_2)
{
index = 2;
}
else if (opcode == OpCodes.Ldloc_3 || opcode == OpCodes.Stloc_3)
{
index = 3;
}
else if (opcode == OpCodes.Ldloc || opcode == OpCodes.Stloc || opcode == OpCodes.Ldloca ||
opcode == OpCodes.Ldloc_S || opcode == OpCodes.Stloc_S || opcode == OpCodes.Ldloca_S)
{
index = (int)matcher.Instruction.operand;
}
else
{
throw new InvalidOperationException("Current instruction must be a opcode that uses a local index";
}
return matcher;
}
yeah i've thought of that
if the geniuses behind microsoft just made the opcodes a fucking enum
literally u can give enums specific values
and add extensions to them
so there is no reason to make them structs wtf
sob
thats kinda why i want to rewrite harmony
would be wonderful to make my own not stupid opcode class
OR BETTER YET IF THEY HAD FUCKING PROPER UNION TYPES
oh ik
problem is that if they ever added union types
it'd probably be like f#'s union types
you can hack them with records
which are incredibly fucked
used by 19 people? crazy
where did you get that number from
sob
in the image
else if
switch joke
u cant do switch
damn
i wish you could do switches based on that kind of stuff, or based on what flags exist inside of smth also
public static CodeMatcher ExtractIndex(this CodeMatcher matcher, out int index)
{
switch (matcher.Instruction.opcode)
{
case OpCodes.Ldloc_0:
case OpCodes.Stloc_0:
{
index = 0;
break;
}
case OpCodes.Ldloc_1:
case OpCodes.Stloc_1:
{
index = 1;
break;
}
case OpCodes.Ldloc_2:
case OpCodes.Stloc_2:
{
index = 2;
break;
}
case OpCodes.Ldloc_3:
case OpCodes.Stloc_3:
{
index = 3;
break;
}
case OpCodes.Ldloc:
case OpCodes.Stloc:
case OpCodes.Ldloca:
case OpCodes.Ldloc_S:
case OpCodes.Stloc_S:
case OpCodes.Ldloca_S:
{
index = (int)matcher.Instruction.operand;
break;
}
default:
{
throw new InvalidOperationException("Current instruction must be a opcode that uses a local index";
}
}
return matcher;
}
fully can
Thats just a static property no?
yea
Can't do a pattern matching switch?
F
GPT once again did not cook well...
me when not constant value

Dw copilot isn't doing much better
guys What PlayerRoles ฤฐs deleted ?
or exiled problem?
or I'm dumb?
sorry for plugin name
reference assembly-csharp
um
from a guy
my guess
is that because some opcodes are made up of effectively two parts
they didn't want opcodes that weren't to be made up of two parts too
It's OpCode.
is there a way to detect when scp-3114 changes skin?
huh
through patching, probs
The is enums for opcodes
opcode is a struct not an enum
Yes i know but there is an enum too
is it a harmony one
like do u have a link to what enum ur talking about
Not on pc ask tomorrow
also til
harmony has a method to do this lol
GeneralExtensions.LocalIndex
also
you can defo make a switch with the right enum
OpCodeValues
if you publicize it heh
is that stdlib or harmony
System.Reflection.Emit
๐
although i would love some very specific dictionary methods
IN PARTICULAR
why is there no swap method
for stuff like this
if (dictionary.Swap(key, value, out var oldValue))
{
oldValue.CleanUp();
}
being able to wipe out an entire method and overwrite it with the IL I want is bliss
how many methods are u wiping out wtf
just needed to return a value instead of conditionally multiplying it first
once I'm done with actual work I'll probably hunt down other ways to make 48 player servers run @ 30TPS minimum on limited resources
ALSO if we had CollectionsMarshal i could make this only one op too but nooo
wtf is that
unsafe operations on collections
want...
I want to murder you!
WHAT THE HELL
UwU
@scenic trout left a review https://github.com/northwood-studios/LabAPI/pull/152
Text toys aren't detected by raycasts or RaycastHit are they?
shouldn't be
They are on different layer on server
Damn, so there's no way to tell if the player is looking at a text toy?
Ngl, i forgot layermask was a thing
send the error
Any higher version than 4.8.X is not guarantee to work
might be able to get away with using .net standard 2.1 max for a dependency but I doubt you can make a plugin in anything but 4.8
im wanna c# 13 by default bruh
Edit csproj
each times find project in files and edit csproj
Then make project template for SL plugins
1984
Outside of the FpcServerPositionDistributor are there any known hot paths for servers
although I do have an idea I wanna try next
tick aggregation
probably more around the time I run out of other avenues I can try though
public static bool HasKeycardPermission(
this Player player,
DoorPermissionFlags permissions,
bool requiresAllPermissions = false)
{
if (player.HasEffect<AmnesiaVision>())
return false;
return requiresAllPermissions
? player.Items.Any(item =>
item is KeycardItem keycard && keycard.Base.GetPermissions(player as IDoorPermissionRequester)
.HasFlag(permissions))
: player.Items.Any(item =>
item is KeycardItem keycard &&
(keycard.Base.GetPermissions(player as IDoorPermissionRequester) & permissions) != 0);
}```
Hi! Why is that if I have a ChaosKeycard then it returns false but with anything else keycard true?
item.Base
Found it ๐
C# should have a has keyword to get properties that you know may exist smh
What
propose this and it will come in like 5 years
you heard me
Just create an SDK-style template for yourself
I think they want the same thing as keycard is { IsCustom: true } but with has and it doesn't need to have those properties
so like in JS you can just do keycard[AmmoType]
and just ball it keycard has { AmmoType: AmmoType.Something }
which is obviously false cause keycard doesn't have AmmoType
mfw C# is a statically typed language and doesn't have dynamically typed language features
Just use dynamic then
yes this is exactly what i want, which i dont think is possible rn :c
I do not think it'll be tbh, as others stated, it is a dynamic language feature
You should type check and cast
30 dummies
Note that this is dev build sooo
Yea
btw is that creategame or dedicated server
interesting that the cullingSubcontroller is that expensive
on the server?
its required to animate the hitboxes
^
considering the fact cheaters clearing don't give a damn about the hitboxes, I'm being brutally honest: why?
SL isn't a competitive esports shooter
Why not stop at a simple capsule collider check
uuh
Perhaps we should add check if there is any event handler registered before firing "every frame events"
Eves fault
do you still have that open, how expensive is the animator if you change the role of all the dummies to SCP049
iirc scp049s hitbox is a single capsule
you can but i believe you wont get much gains
no i think you just have todo 1.2.3.4.5
any gain is a good gain atp
if it doesn't affect gameplay i'm pretty much throwing it out
it depends i know for humans you will have to deal with head hitboxes and what not
does the client let the server know what hitbox it hit
dont think so
me when some classes require a type generic to simply get some simple data
wtf
How is getSpeed slower than raycast
(pretty sure that grounded use raycast)
Oh I see why
any chance of NW simplifying the shooting netcode in the future
because it's wildly overkill for a casual game like SL
games like Valorant don't even simulate animations on the server until a shot is made in the direction of the player
i cant really speak for NW
fair enough
just that i'm looking through it all and just thinking that the codebase would fit a more competitive game better than SL
and SL's needs don't justify the performance hits
i had a look and hitreg is fully server side, client only sends their pos/rot and main target pos/rot
bummer
I can probably still simplify the logic
calculate where the player's head would be approximately based on their pitch
additionally the backtracker stuff actually moves players which does transform updates etc
would be cheaper to just use the saved backtracked position/rotation and bounds to determine if it would plausibly hit
and then the player would just report the hit (like it already does) giving the server a very cheap way to check
Can you tell me what the name of the hitreg message is
Just so I can take note and put it on my optimization patches list
ShotBacktrackData
[ERROR] [LabApi] System.TypeLoadException: Could not load type of field 'Sex.Core.Plugin:_handlers' (1) due to: Could not load file or assembly 'System.Collections, Version=8.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a' or one of its dependencies.
at (wrapper managed-to-native) System.RuntimeType.GetConstructors_native(System.RuntimeType,System.Reflection.BindingFlags)
at System.RuntimeType.GetConstructors_internal (System.Reflection.BindingFlags bindingAttr, System.RuntimeType reflectedType) [0x00008] in <069d7b80a3914a08b6825aa362b07f5e>:0
at System.RuntimeType.GetConstructorCandidates (System.String name, System.Reflection.BindingFlags bindingAttr, System.Reflection.CallingConventions callConv, System.Type[] types, System.Boolean allowPrefixLookup) [0x00047] in <069d7b80a3914a08b6825aa362b07f5e>:0
at System.RuntimeType.GetConstructors (System.Reflection.BindingFlags bindingAttr) [0x00000] in <069d7b80a3914a08b6825aa362b07f5e>:0
at System.RuntimeType.GetDefaultConstructor () [0x0002c] in <069d7b80a3914a08b6825aa362b07f5e>:0
at System.RuntimeType.CreateInstanceMono (System.Boolean nonPublic, System.Boolean wrapExceptions) [0x00000] in <069d7b80a3914a08b6825aa362b07f5e>:0
at System.RuntimeType.CreateInstanceSlow (System.Boolean publicOnly, System.Boolean wrapExceptions, System.Boolean skipCheckThis, System.Boolean fillCache) [0x00009] in <069d7b80a3914a08b6825aa362b07f5e>:0
at System.RuntimeType.CreateInstanceDefaultCtor (System.Boolean publicOnly, System.Boolean skipCheckThis, System.Boolean fillCache, System.Boolean wrapExceptions, System.Threading.StackCrawlMark& stackMark) [0x00027] in <069d7b80a3914a08b6825aa362b07f5e>:0
at System.Activator.CreateInstance (System.Type type, System.Boolean nonPublic, System.Boolean wrapExceptions) [0x00020] in <069d7b80a3914a08b6825aa362b07f5e>:0
at System.Activator.CreateInstance (System.Type type, System.Boolean nonPublic) [0x00000] in <069d7b80a3914a08b6825aa362b07f5e>:0
at System.Activator.CreateInstance (System.Type type) [0x00000] in <069d7b80a3914a08b6825aa362b07f5e>:0
at LabApi.Loader.PluginLoader.InstantiatePlugins (System.Type[] types, System.Reflection.Assembly assembly, System.String filePath) [0x0001c] in <bea7f403b90e4786abd99fa819db9853>:0
at LabApi.Loader.PluginLoader.LoadPlugins (System.Collections.Generic.IEnumerable`1[T] files) [0x000ed] in <bea7f403b90e4786abd99fa819db9853>:0
nice plugin name
make sure you put System.Collections.dll into your LabAPI\dependencies\global folder
where i can get this .dll?
Build your plugin it'll be in your build folder
if you use it
uh wait
what .NET version are you using
all files
8
yeah nah
?
that won't work
you gotta target .NET Fx 4.8 or potentially .NET Standard 2.1 (and that's already unsure)
(You do not need to change from dotnet8, just change target)
Edit the .csproj and just add <TargetFramework>net48</TargetFramework> in the PropertyGroup
alright todo list:
- Throw out the whole animation stuff on the server (CullingSubcontroller)
- Patch the backtracker stuff not to move players, but instead use some sort of proxy capsule/bounds check. Idk how I'll patch it yet but I'll figure it out. This sort of thing is easier done in the original codebase lol.
- Patch hitreg to determine if it was headshot or not based on approximate position of the player's head instead of hitting the hitboxes directly. As well as using capsule bounds for plausibility. Don't care about being accurate or not, not an esports shooter.
- FpcMotor.GetSpeed is evil
also open ended question but do grenades affect the same gameobject multiple times in ExplosionGrenade.Explode
Physics.OverlapSphere returns Collider[] but some pickups seem to have multiple colliders?
how can I make it possible to open csproj by double-clicking on the project name as in net 8?
Damageable cache list or something
Use Rider
no
Actually that doesn't work
bruh
Just select it and press the keybind
You might be right there
funny
How come my Ubuntu installation of JetBrains Rider only goes up to C# 9.0 while my Windows laptop has the latest version if they're both 2025.1.2
Doyou have the new sdk
how i can change .net framework 4.8 c# version for all projects?
In your ide settings
impossible
Why ?
choosen automatically
Wdym ?
just modify .csproj <LangVersion>latest</LangVersion>
Thing is, if i set it to c# 11, then both c#11 and #10 show up as an option in the IDE
But it just refuses to compile
No I don't
Cam you show your csproj?
Thats the issue then
Bruh
If you dont have the sdk why would you think targeting to that langLevel would work
Because I forgot I had to delete it earlier
And Linux doesn't exactly work perfectly with dotnet
yyyeaaaaa
that happens
seems like a bit of a stretch
me when i make sl plugins on macos
Why
there is an installscript ๐ญ and some distrib has package for these
Whyyy
it's easy
macos is great
nah
why not
yah
i use macos daily
so much nicer to code on than windows
lol
only problem is i cant test til im on windows lol
it feels nicer ok
because you paid for it?
does the word job scare you by chance? /j
nah
ok good

so many people tell me to censor it smh
but it feels nicer to woke up at 13

i am!
no
noway
where i can get it?
Found this file in C:\Windows\WinSxS\amd64_system.valuetuple_cc7b13ffcd2ddd51_4.0.15912.0_none_d1891ed46ba50223
not sure if it's still compatible
plugin prob isnt on net framework 4.8
where this?
System.IO.FileNotFoundException: Could not load file or assembly 'System.Runtime.InteropServices.RuntimeInformation, Version=4.0.2.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a' or one of its dependencies.
use DBLite
Im honestly loosing my mind
- name: Download SCP SL References
uses: killers0992/scpsl.downloadfiles@master
with:
branch: 'public'
filesToDownload: "UnityEngine.dll,UnityEngine.AnimationModule.dll,UnityEngine.AssetBundleModule.dll,UnityEngine.CoreModule.dll,UnityEngine.IMGUIModule.dll,UnityEngine.PhysicsModule.dll,Mirror.dll,LabApi.dll,CommandSystem.Core.dll,Assembly-CSharp.dll,Unity.TextMeshPro.dll"
It doesn't find LabApi even tho it should, only missing one
public static void AddSeason(DB_Season season)
{
using var database = new LiteDatabase(DataBaseName);
var SeasonCollection = database.GetCollection<DB_Season>(DB_SeasonName);
if (SeasonCollection == null)
return;
SeasonCollection.Upsert(season);
}
why here null check?
how then i can make from null to exists
it automaticly creates a new I think
try installing through nuget
creates new ye, null check for that doesnt need
How do you check if a player died cause of PocketCorroding
It's just UniversalDamageHandler, this was the only solution I found lol
foreach (var effect in args.Player.ActiveEffects)
{
if (effect.name == "PocketCorroding")
{
}
}
But this is not 100% accurate
if (effect is PocketCorroding)
True but isn't there a better way
player have activeeffects?
Yes
I suppose I can go
if (args.DamageHandler is not FirearmDamageHandler)
{
foreach (var effect in args.Player.ActiveEffects)
{
if (effect is PocketCorroding)
{
}
}
}
You might die getting shot in the pocket dimension
if (args.Player.ActiveEffects.Any(ef => ef is PocketCorroding))
could also do the job
if (args.Player.HasEffect<PocketCorroding>())
{
}
How to disable 939's aoe claw and lunge damage?
?```cs
public void OnScp939Attacking(Scp939AttackingEventArgs args)
{
args.Damage = 0f;
}
is the returning of the Dedicated Server player object intended for Player.List?
ive been using it for a long time and i havent seen it return the server itself
but now im starting to get the object
use ReadyList
or Player.Get()
Yes
!player.IsHost excludes the server, right?
You can use ReadyList or Players.Get()
You'll probably end up patching a handful of stuff dealing with the host player
Never using Player.List has fixed it entirely for me
It does reduce it by a lot but we still got some exceptions that kicked the dedicated server player
Ended up just patching out anything that could kick the dedicated server player
Been running good ever since
Idk what u were doing then
no idea
couldn't figure it out, so I just patched the methods that were throwing exceptions to ignore the host player
Is there a method for a player to check if it is in a specified room or not?
Player.Room?
Player.Room == Room.Get? I don't know if it is the right way to do this
What room are you looking for
GateA or GateB
Also got a question about voice chat, sending voice packets to/from "human" SCPs to actual SCPs, but the voice ends up being very saturated/garbled. Any idea what would cause that? I'm literally just taking the VoiceMessage and sending it back to other players.
Uhh
Its fine for me
R u modifying it
if (Player.Room is {Name: RoomNames.GateA or RoomNames.GateB}) probs works
Or delaying it or anything
nope, just copying the data over and sending it
I tried that
andd?
Didn't work
yeah guess I could use the existing message, was just that way when I saw the code
Yea modifying it isnt needed
Well
Copying
That wouldn't cause the static though right

no clue
It works for me
But not for you
and i dont copy i just change the type to proximity rather than scpchat
for human SCPs I send it via roundsummary to SCPs
actually I sent it via roundsummary both ways
Than there is something wrong in my code if it works for you lemme check
Not you
Talking to the other guy
@severe cave send your code
oh mb
and yea show code
is this good? player.Room.Name == RoomName.EzGateA
no good?
from this logic
Room can be null
then player.Room != null this should work?
silly eve
Awh
playing games again
ahh I think I might know why
Ur a gamer?
I don't prevent the regular voice packet from being received
maybe it's causing garbled nonsense from being duplicated
That would do it
Me? Never.
easy fix
damn
I'm only posing as one
what the
whats up
yeah that was it
works fine now
dunno why prox chat affects this even when the SCP isn't in proximity of the player but w/e
Can someone tell me what these all mean? What is a hazardous environment?
thanks
Is there now a way to send multi line hints? Iโve tried several ways but none of them worked
xx\nhh
yea just \n
also if you want hints to overlap for whatever reason you can just do <line-height=0%>\n</line-height>
fWHO WANT 10K DOLLAR
Give it
Gamble it
sry i stole it
Damn
anyone else get a weird bug with 173 sometimes moving silently?
haven't seen that
those restrictions on custominfo are wild, no wonder i haven't done something with it in like 2 years
this just shouldn't reject Xname\n<color=#DC143C>disappointed</color>
They're pretty useless
color is very restricted
pretty annoying when you can just apply a server tag with color
Exiled has a list
arbitrary restrictions be like
did NW say why it was restricted
iirc to prevent you faking a nw role
its fair
why am i not surprised
Obviously not
I just have very specific views on the whole global badges & VSR and more
off topic for this channel anyway so I won't bring them here heh
Theyre trying to rework it
So stuff can be allowed more
While still keeping nw stuff special
fair
(aka they wanna make it the background instead of the color of the text)
although
Its been in work for a while so idk when that happens
I'm just mostly not impressed when vanity stuff like this impacts modding
eh its fine
at least imo idrc
can still use the group colors + black and white
(just no group colors for ne specific ones)
thats mostly fine
My POV is that SL is a game inspired from a gamemode on a sandbox moddable game, so it stings when modding is affected by certain choices like this
i feel like this take kind of ignores the shit nw has given us
Doesn't mean I don't appreciate some of the stuff we get with SL
I'm using these specific colors
The problem is with rejection rules, you can't mix untagged text (text with role color) with tagged text (text with custom allowed color) in custominfo ig
And role colors aren't allowed in custominfo...
Has anyone succeeded in patching the Player ctor to get rid of the duplicate key exception spam
nvm got it
I would rather if you could give us replication steps..
I think they're referring to duplicate user IDs
Dummies for example
Nah
Huh
Basically it seems like Player.AddPlayer is called multiple times
Which is called by ReferenceHub.Start
I'm trying to figure out why that's the case
ReferenceHub.GetHashCode is the gameObject so the only way I see this happening is if the game object had multiple reference hubs applied to it
Either way, the way I fixed it was replacing new Player() in Player.AddPlayer with Player.Get()
Player.Get will call the player ctor if it doesn't exist in the player dictionary
I might have a hunch as to why it happens, gimme ten mins
I can't see a reason why it'd happen, but it does
The exception is mostly on player connection
Don't have any specific repro steps
[log] ArgumentException: An item with the same key has already been added. Key: ReferenceHub (Name='Player [connId=22]', NetID='58326', PlayerID='54')
[log] at System.Collections.Generic.Dictionary`2[TKey,TValue].TryInsert (TKey key, TValue value, System.Collections.Generic.InsertionBehavior behavior) [0x0015a] in <069d7b80a3914a08b6825aa362b07f5e>:0
[log] at System.Collections.Generic.Dictionary`2[TKey,TValue].Add (TKey key, TValue value) [0x00000] in <069d7b80a3914a08b6825aa362b07f5e>:0
[log] at LabApi.Features.Wrappers.Player..ctor (ReferenceHub referenceHub) [0x0000b] in <bea7f403b90e4786abd99fa819db9853>:0
[log] at LabApi.Features.Wrappers.Player.AddPlayer (ReferenceHub referenceHub) [0x00008] in <bea7f403b90e4786abd99fa819db9853>:0
[log] at (wrapper delegate-invoke) System.Action`1[ReferenceHub].invoke_void_T(ReferenceHub)
[log] at ReferenceHub.Start () [0x00009] in <8db1ca0fe9a6484084cda320b139932c>:0
it was something i looked into and i believe it could be caused by calling Player.Get() before the ReferenceHub.Start(). theres an internal PR for implementing away that avoids recreating the wrapper for those cases
Doesn't Start run immediately after initialization for an active component?
that might be awake
that's Awake
Start is called on the first frame after the object is enabled
leaving time to set properties on components
fun
Hmmmmm
Do you subscribe to on connecting event or something?
Like that one that fires when player wants to join
I suspect it is cause we are using the CustomDataStore
I encounter this as well and my suspicion lies in fetching the Player CustomDataStore in OnPlayerJoined
PreAuthenticating?
Yes
I was on a train at the time so I cannot test it
Perhaps it has to do something with it
hmmm it doesn't give a reference hub
Do you get the Player object some other way?
don't think so
vonat :3
bruh moment
Okay so line 1\nline 2 doesn't work in custom info. Any other ideas?
Also pasting this text from notepad even not matching regex
New line symbol
Oh
idk, but everything works for me

Do I dare say the name?
what









