#LethalLib

1 messages ¡ Page 2 of 1

eternal sphinx
#

or something like that?

tough path
#

Yeah if you wanted to do it like that.

it really depends on how you want to approach it, so right now my bundles are read using LethalExpansion rather than LethalLib rn
LethalExpansion has a single ModManifest type class that has references to all the other relevent stuff in the bundle. so it loads the bundle, looks through all the files for the ModManfiest type object and caches and uses that for references later

#

lot of ways you can structure it for yourself

eternal sphinx
#

you can create multiple references or just a single big bundle that has everything on it

#

but this AssetBundle file it like the exported result of the information/data. is there any way to modify that assetbundle to add new things on it

tough path
#

the intent of assetbundles is like imagine a mobile game like candy crush or something. instead of updating the entire build of the game they can have new levels in an assetbundle that gets pulled from a server

eternal sphinx
#

using my template which would be the best way to add a new scrap item for it?using System;

#

i tested it with the AssetBundle given and it funks

#

as i cannot modify the assetbundle

#

how do i do a new one that can also be applied like this

#

unless there is a way to like import assetsbundles to Unity directly but idk

#

like via file, not Web

tough path
#

@lofty nymph any chance the new update could be pushed on github aswell?

lofty nymph
#

I have the next update already finished, but it needs testing so i don't know when i'll be able to push

tough path
#

yeah my dumbass tried to finally start forking skullcrushers fork and I spent 3 hours fighting github to realize 0.9.0 is thunderstore build exclusive 😭

lofty nymph
#

Sorry 😭 i am horrid at remembering to use git

#

I'll probably push 0.10.0 later today, i don't have 0.9.0 as a separate commit anymore

tough path
#

thats totally fine

#

only big issue is that the oob beta needs the 0.9 changes to load properally so i didnt have a constant to test with

#

big appreciates

undone brook
#

is lethallib backwards compatible?
will a mod written on 0.7 work on a newer version?

lofty nymph
#

for the most part i try not to change function signatures

lofty nymph
#

dev branch has 0.10.0

tough path
#

thank you very much

tough path
#

@devout glacier

#

the contents of this text is exclusively through lethallib 😄

#

just gotta tell Gordion to hide

potent spoke
#

hello i was wondering if i could get some help! my scrap items only appears to the host and nobody else. is there anything i can do to fix this?

lofty nymph
#

NetworkPrefabs.RegisterNetworkPrefab(scrapItem.spawnPrefab);

tough path
#

@lofty nymph @devout glacier @radiant light @proper epoch
Excited to announce my wip fork of LethalLib successfully loaded a custom moon straight from an assetbundle. all components and SO's setup natively in Unity and bundled exclusively using the games native components

lofty nymph
#

feel free to make a pull request if you want this stuff to be part of lethallib itself, when you are happy with it

#

i've been reworking lethallib in general so any large additions / changes might as well be done now

tough path
#

Yeah I gotta clean it up abit and then talk to you and Skull about one or two fairly big changes i've made, then talk to you abit about anything we should try and generalize since I haven't looked at the item side of things whatsoever

lofty nymph
#

I mainly try to keep things as backwards compatible as possible

radiant light
lofty nymph
#

On the topic of lethallib, i'd like to setup a wiki page on the git repo for documentation if anyone is interested in contributing to that

#

i've been putting that off for too long lol

lofty nymph
#

(I do not know who else uses lethallib heavily)

solar blaze
#

Should be able to get my modjam project submitted tomorrow or next day

#

then I'll be good to help with that

lofty nymph
#

who was the person who used the dungeon api

#

uhh the scp foundation mod i think

lofty nymph
#

(oh it was badham, they got pinged already so they will see this)

tough path
#

The big goal here is to allow for modders to ship a custom moon that is as close to a vanilla one as possible, without any mandatory data/component generation or third party scripts used in the moon. from there we can figure out the best way to incorporate helpers/generation that people can optionally use

I'll pick on both as examples to be fair

one thing LethalExpansion does is use re-creations of scene components to help readability and simplify components (every script a moon needs to work has lethalexpansion variants). It's really helpful! But the way this works is when loading the custom moons, Holographic makes a new instance of the real class and manually re-assigns everything. This takes control away from the author and makes debugging difficult, aswell as making the scene hardcoded to that sdk. Stuff like this can be handled with more intricate unity stuff where you can re-serialize pre-existing components to re-organise how they look

one thing LethalLib (Atleast SkullCrusher's version) does is manually create the Moon's TerminalKeyword/Route options. This is super handy because theres very little customization involved in this and saves a good amount of time and hassle, But again this relies on the API handling it rather than the built moon itself. So instead we can just chose to make those if we don't want to build them.

#

tl;dr I want custom moons to be treated and expected as vanilla moons as close as possible unless you ask for "help"

lofty nymph
#

For lethallib my goal has mainly been to do as much the same way as zeekerss would do it as possible

#

as in create all the assets in unity from basegame components and just register them with a single call

devout glacier
#

personally my goal has been "getting it to work" and that's pretty much where it ended so that is to reaffirm that you can change whatever you like from my implementation

lofty nymph
#

my dungeon api basically works the same way, if you have a copy of dungen you can just build a dungeon like zeekerss would and register it with a dungeon call from the bundle

#

no custom unity tools or anything

devout glacier
#

that is what makes the most sense to me, honestly

tough path
#

In fairness I think 9 times out of 10 Devs will be fine generating that terminal stuff I just like knowing they don’t have to

lofty nymph
#

for terminal stuff, in all my apis (the shop stuff) the terminal nodes and keywords are optional arguments

#

if you don't supply them it generates it for you, if you do it does not

#

dunno how that works with custom moons

#

note i have not looked at skullcrushers fork

devout glacier
#

automatically generating a keyword based on the moon's name and doing everything proper based off of that would work, no?

tough path
# lofty nymph no custom unity tools or anything

Pretty much the same yeah. I’m going to introduce some cool tooling stuff in a sideproject called LethalToolkit but the idea is that everything only “masks” the untouched content / builds with basegame parity

devout glacier
#

Was gonna throw it over Eventually™️ but batby here seems to have it covered?

devout glacier
# devout glacier automatically generating a keyword based on the moon's name and doing everything...

Assuming the end user doesn't create route/keyword/cancel nodes:
-create a keyword terminal asset based on the name of the moon and assign it the route verb
-create a route node that uses the default LC route text The cost to route to <grab planet name from level asset> is [totalCost]. It is currently [currentPlanetTime] on this moon. Please CONFIRM or DENY. Then we also grab the id and use it for the DisplayPlanetInfo variable
-the cancel node just says You have cancelled the order same as LC default
and then we put everything where it needs to go, as we would if the end user DID provide these nodes

#

oh whoops I forgot the routeconfirm as well

#

well you get the idea

tough path
#

yeah

devout glacier
#

we could I suppose also make a default info node that just says something like [NO INFORMATION AVAILABLE]

lofty nymph
#

lmao

tough path
#

I'll probably make it so any moons auto pulled from bundles have their terminal stuff gen'd

#

and then if anyone wants to manually load one in with unity bundled ones they can do so via their own mod

lofty nymph
# lofty nymph lmao

itemInfo.displayText = $"[No information about this object was found.]\n\n"; lol

devout glacier
#

I believe custom enemies do the same

tough path
#

I have so much to cleanup now oh lord 😭

fresh folio
#

Anyway yeah, giving and option to the creator to input their own terminal nodes was something I wanted because it allows you to have a lot more control over the contents of said keywords

#

Unfortunately the thing that modded keywords don’t allow you to do as well is abbreviations like the base game

#

Idk why but the game hates case matching/not requiring the info keyword if it’s anything modded

#

Wonder if it can be fixed but I don’t think so

tough path
#

Really?

#

What makes you think it cant be fixed

fresh folio
#

Terminal is a mess

#

It probably can be fixed but it’s still gonna have the issue of conflicting with every base game thing by accident

tough path
#

ik its a mess haha what is the like issue though

fresh folio
#

You can’t shorten/leave off info/buy/whatever keywords to modded content but you can do that with base game things

grizzled fractal
#

is there any guide or template for making a custom interior with this?

tough path
#

thats because some of the game things have multiple terminalkeywords, no?

fresh folio
#

You have to get it word for word or in my experience the game wouldn’t call it the node

fresh folio
#

But the modded ones just throw a “this doesn’t exist” message

#

If I type in sneer it won’t pull up moonsneer it’ll say no action associated

But if you type in like bunk it’ll pull up bunker spider

tough path
#

is that not because bunker spider is bunker spider and not bunkerspider?

#

like i can do route tenebrous and also route tene and both work fine

fresh folio
#

Interesting

#

Tbf lethallib went up like 4 versions since I left so it might not have an issue anymore

tough path
#

iirc it splits keywords off from spaces

fresh folio
#

Now I wonder

#

Can you just type in the moon name to route to it?

#

Like in the base game

#

That was the other issue I was having

tough path
#

yes

#

and my custom one works too

fresh folio
#

Weird as fuck

#

Might’ve been a quirk with older versions

tough path
#

try changing moonsneer to moon sneer as a keyword

fresh folio
#

Will try it out when I get back tomorrow

#

Yeah it’s just I don’t want it snowing up like that lol

#

I think it uses node still luckily

tough path
#

Not yet

#

SCP is open source though and KayNestua has been working on some templated stuff

grizzled fractal
#

m

lofty nymph
#

i mean it works for the buy keyword without typing buy so i would assume the same is true for info

lofty nymph
tough path
#

@lofty nymph @devout glacier
Would be curious on your guys thoughts on how CustomContent (Particually CustomMoons) handle references to basegame content.
With components and stuff ofc Unity does the wonderful thing of attempting to find and restore components based on matching assembles, But it doesn't do this for assets. The big issue here are ScriptableObjects for stuff like Enemies & Scrap.

On LethalLib side, the idea I can initially think of would be to systematically scan, compare and replace references in custom content with the real vanilla ones but it is fairly gross.

Then on the Unity side of things, We'd still be bundling a ton of unused content unless we strip the base game ones.

I'd need to think about it some more but maybe the best way to handle it is to make stubbed versions of them all similar to your unity project template with them marked as a LethalLib assetbundle and then we would just have that tiny bundle inside lethalib itself? It's really gross and maybe we could try and do the swap on assetbundle build instead so the actual scenes/prefabs remain vanilla parity but bleh

devout glacier
#

personally I'm fine with doing it on the code side, maybe having the end user specify a specific index for what moon they wanna steal the monster/scrap list from

#

I guess that's pretty limited if you want to make your own enemy set

#

We could (for vanilla enemies only) define an enum or string array and then let the end user pass an array of them

#

and then the code grabs an enemy based on that enum

#

for example if the end user wants their custom moon to spawn hoarder bugs theyd do smthn like DefineCustomEnemies(new EnemyType[]{ EnemyType.HoarderBug});
and then our code would say
if (EnemyType.HoarderBug){ Moon.enemies.add(__instance.levels[0].enemies[0]) }

#

that's very pseudocode, but

#

advise the end user to keep the level file empty

#

of enemies and stuff, anyway

tough path
#

that makes assetbundle-exclusive releases unviable though

#

and functionality dependant on lethallib

devout glacier
#

sorry, lem-exclusive?

tough path
#

my brain is too burnt haha

#

fixed

devout glacier
#

aha

#

I guess with what you described it seems functionally similar to what LethalExpansion does

#

LethalLib requires some end user code for everything else, at very least you have to add things to lists

lofty nymph
#

LethalLib does use some custom scriptable objects for definitions

tough path
devout glacier
#

Fair

lofty nymph
#

i had assumed we'd just use SelectableLevel in a wrapper scriptable object

#

and use that to pass into a registry function

tough path
#

i don't understand what your saying in that reponse

lofty nymph
#

whuh?

tough path
#

like straight up haha, my brain isn't processing what you mean

lofty nymph
#

like have a custom scriptable object that contains SelectableLevel as a field inside of it

#

thats how i have done all my other definition files

tough path
#

oh and you'd be expecting that to be in the assetbundle?

lofty nymph
#

etc

#

yeah

#

well

#

i expect people to pass it to a registry function

tough path
#

in the implementation* yeah

#

ok cool because i kinda went the same route with the levels and was worried you wouldn't vibe

lofty nymph
#

i mean it is literally how i do things for other stuff like unlockables lol

tough path
#

But I'm still a little concerned on the best approch for tweaking scrap and enemy values in editor

lofty nymph
#

just use the vanilla system, you are always gonna have problems with custom scraps so just ignore it lol

tough path
#

no but when you reference vanilla stuff it's going to bundle a copy of the decompiled so

#

it doesn't know you want the one inside the game

lofty nymph
#

right

#

no addressables

tough path
#

I mean

#

we could get them

#

the game has refs for them all we can get because the vanilla levels have them all

#

but how do we do the switcheroo

lofty nymph
#

feels janky lol

tough path
#

Yes.

lofty nymph
#

only other option i can think of is a list of serializable classes which have a field for scrap name, and spawn curve or something

#

that would also automatically support custom scraps

#

normally i'd say itemID but zeekerss doesn't even use his item id system as far as i can tell

#

i should go to sleep it is 4 am

tough path
#

yes go to sleep

#

tldr @lofty nymph if it was exclusively super small so's that just contain numbers and names etc. would you consider having a small assetbundle included inside LethalLib?

#

i think thats gonna be the best way ahhh

lofty nymph
#

I'm confused what you mean

tough path
#

shit maybe we don't

#

ill stop talking until i think more

#

Your UnityProjectTemplate will need to contain stubbed versions of the vanilla scriptableobjects

#

at the very least

#

idk how custom moon devs would be doing stuff without that regardless so im assuming thats a non issue for everyone

tough path
#

very good news

radiant light
tough path
#

the terminal listings will be more tweakable in the future but rn its gap every 3 listings or gap if the levelsource is different (using assetbundle names for that rn)

night oar
#

is there a guide on how to use this somewhere?

lofty nymph
#

It has included those since the start

tough path
#

no as in like

#

all of the ones the game makes using them

lofty nymph
#

Whuh

solar blaze
#

I haven't really looked at lethal expansion so idk how it works but if there was a layer of communication between the two so that Levels.LevelTypes.All included the custom moons that would be very nice.

tough path
#

i don't know how i'd go about including lethalexpansion loaded moons in that but the wip lethallib version has that somewhat supported

lofty nymph
#

at least it includes any moons in the levels list if you use the All enum

#

it works as a bypass now

solar blaze
#

Oh neat

tough path
#

@lofty nymph Sorry I was exhausted last night and forgot to elaborate.

--On Lethal Companies End (Loading The Content)--
Basically rn my plans as a shoddy but best solution is on assetbundle load, we look through the custom contents SO references and see if any of them match the basegame ones (right now thats just name string matching). If they do match we change the custom contents reference to the real version. I really don't like auto modifying creators content like that but I don't think theres a better way. Anyway this works.

--On Unity's End (Making The Content)--
But the remaining small issue is that the SO's people will be using from the base game are actually fairly large filesize wise, because stuff like Item and EnemyType contain prefabs of that content and the assets and etc. The AssetBundles will try and bundle it all up when it immediently gets thrown out when we swap it out for the real reference.

I'm asking that in addition to the Unity Project Template having the stubbed ScriptableObject scripts It also has stubbed versions of the ScriptableObject assets with all the basic stuff like names, values etc. identical but the object and other asset references removed

#

Like for example, a custom moons SelectableLevel is where you reference all the stuff that's gonna be included. To get the real versions of these we need to swap them out with the vanilla ones on assetbundle load

#

but because these references are useless and only used for getting the one we want, we don't need the actual landmine model, turret model etc. thats in those two prefabs.

lofty nymph
#

and then use that to generate the actual level SO during registry with string matching like you said

tough path
#

yeah fair

#

we can't get around just string comparisons that much can we

lofty nymph
#

not really, you're gonna be doing it either way

#

this way just avoids having to include all the objects as part of a template

tough path
#

I would kinda prefer still having stubbed variants of all the so's the game has just to stay on the 1:1 parity as close as possible but we'll see

lofty nymph
#

i just do not feel like it would add much, if anything it would probably end up making things more confusing

#

as opposed to having a dropdown where people can select the "prefab"

#

feels less cluttered

#

imo

#

plus it would cut down on file sizes because it'd just be a string

#

rather than an entire object

#

in the end all you need is the name

tough path
#

Yeah but the dropdown would involve a custom script that the vanilla scenes don't use and im being stubborn and nitpicky haha.

We'll probably have cleaner variants of the basegame scripts but I wanna do that via unity editor stuff so it just reskins the front end of them.

Maybe (atleast in my unity toolkit) I can have a selectable toggle to try and strip the vanilla so references before build? so we can straight up use the basegame so's during content creation.

lofty nymph
tough path
#

In any case while it is gross and I'd prefer a more reliable way of doing it, my initial implementation of the reference restoring is working

LethalLib (Batby): Obtained (68/ 068) Vanilla Item References
LethalLib (Batby): Obtained (13/ 013) Vanilla Item References
LethalLib (Batby): Found 36 Item References In Custom Moon: 80 Tenebrous
LethalLib (Batby): Found 36 Matches To Vanilla Item References In Custom Moon: 80 Tenebrous Restoring!
LethalLib (Batby): Found System.Collections.Generic.List`1[SpawnableEnemyWithRarity] Enemy References In Custom Moon: 80 Tenebrous
LethalLib (Batby): Found 36 Matches To Vanilla Enemy References In Custom Moon: 80 Tenebrous Restoring!
tough path
lofty nymph
#

i prefer to take the path of least resistance lol

tough path
#

Trust me i'm a big tooling/helper nerd myself. I just want to implement the foundation of this based around the idea that we can make as much as the custom support/help as optional as possible

#

also while your here, what reference do you use for the ES3 stuff?

#

I couldn't find any that worked so i have your es3 stuff commented out rn but im worried it might be corrupting the ship main screen / save for some reason

lofty nymph
tough path
#

oh no wonder i couldnt find it haha

#

ty

thorn drift
#

do i have to worry about linking my items to an audio mixer group

#

im using lethal lib is why im asking here

solar blaze
#

I haven't been

lofty nymph
#

i've just been using the one from the ripped game assets shrug

#

no idea if it matters

thorn drift
#

oh you can just rip it

lofty nymph
#

idk if it breaks anything

thorn drift
#

what is it called?

lofty nymph
#

lol

hollow sorrel
#

Would there be any issues with how the API registers an item scrap rarity if the server & client has different rarity values?

solar blaze
hollow sorrel
#

same with shop items?

solar blaze
#

No shop items will have to be completely synced. The dev branch has a version where you can update prices during runtime though.

#

As well as remove items from the shop

lofty nymph
hollow sorrel
#

i sorta got it to work but its messy af lol

#

the thing is the terminal stuff will only for the host, works for my case since im just adding them to debug my stuff

#

theres probably a way to check if the nodes exist in the server and if they don't, just remove the keyword and remove the item from the shop list

tough path
#

im so good

lofty nymph
tough path
#

oh noo i posteds that in wrong place aha

#

😭

tough path
#

The remaining issues for new custom moon loading I gotta knockout tomorrow are

-Item Dropship fix
-Figuring out best way to restore dynamic mixer groups
-Fixing the lighting bug in ship regarding the planet preview prefab
-Very light pass on Skull’s dungen stuff to get basic configuration going for cross compat moon-dungeon mods

Then if @lofty nymph and skull vibe with my changes maybe we can get a beta or something out for peeps(?)

alpine storm
#

Is there a wiki or documentation about how to use this library?

lofty nymph
lofty nymph
#

LethalLib 0.10.0

  • [BREAKING CHANGE] Added save system patch which attempts to keep the items array in the same order, so that items don't change when you load an old save after mods have updated.
    • This is experimental and currently locked behind a config setting, may break old saves.
  • Added Intellisense comments to all API functions.
  • Added method: Enemies.RemoveEnemyFromLevels()
  • Added method: Items.RemoveScrapFromLevels()
  • Added method: Items.RemoveShopItem()
  • Added method: Items.UpdateShopItemPrice()
  • Added method: Unlockables.DisableUnlockable()
  • Added method: Unlockables.UpdateUnlockablePrice()
  • Added method: Weathers.RemoveWeather()
  • Added method: MapObjects.RemoveMapObject()
  • Added method: MapObjects.RemoveOutsideObject()
  • Added Module: ContentLoader
    • This acts as an alternative way to register content, abstracting some extra stuff away such as network registry and asset loading.
  • Added Module: Player
    • Added method: RegisterPlayerRagdoll()
    • Added method: GetRagdollIndex()
    • Added method: GetRagdoll()
  • Added Module: Utilities
    • Added method: FixMixerGroups()

https://thunderstore.io/c/lethal-company/p/Evaisa/LethalLib/

#

CC: @solar blaze

solar blaze
#

Rendering rn, this video has scrap, shop, custom behaviours, map objects, and lightly touches on a couple other things.

hollow sorrel
#

REMOVE SHOP ITEM :yippie:

lofty nymph
proper epoch
#

With plans for a dungeon tutorial on top

#

Though with 10.0 I might need to rework it a bit

tough path
#

If @proper epoch and @radiant light team up on dungen stuff they would be an unstoppable force frll

hollow sorrel
#

frr

radiant light
#

they reached out to me yesterday

#

i just wasnt working on anything cause it was my birthday lol

#

currently just recreating the tiles that zeek has in LC

#

with textures not used in the base game

#

also a bunch of the rooms zeek exported with probuilder scripts still enabled and not exported to mesh so i have to recreate a bunch of rooms which is gunna take way more time

lofty nymph
proper epoch
#

Ah fair, mine is just a tutorial on just the stuff needed to go from the plugin tutorial to having custom scrap

lofty nymph
proper epoch
#

Part of my pull request was adding a main lethal lib page so that might be a good place to put that

#

Right now it's just the preliminary stuff to get any lethal lib mod started, then the plan was branch off at the bottom into each tutorial for some part of the game

lofty nymph
#

sounds good

timid brook
solar blaze
#

oh shoot that's ripped

#

so annoying

tough path
#

@lofty nymph we could probably get the audiomixergroups in your little stubbed template right?

#

since its just variations of tweaked unity settings + itll be replaced at runtime anyway

solar blaze
#

that would be great

proper epoch
lofty nymph
#

done

#

@solar blaze i added the mixers to my unity template project

tough path
#

That's kind of what I was trying to explain a couple days ago btw. we might want all the other scriptableobject types too (Item, EnemyType, SpawnableMapObject, SpawnableOutsideObject, LevelAmbienceLibary) too all have stripped versions in the template. Since we just use them as string checks and replace them on load anyone using the assetripped versions will be bundling in a lot of unneccasary stuff due to the art and audio assets referenced in the ripped ones

lofty nymph
tough path
#

Yeah sounds good

#

we can put that in my unity project tool

hollow sorrel
#

Oh do I have to call remove shop item when the start of round starts

#

oof

solar blaze
#

After

#

So like whenever other clients sync with the hosts config you can call it

hollow sorrel
#

Ah, yeah that makes sense

radiant light
#

a remake of the start room for the installation tileset is done

hollow sorrel
#

ya'll are magicians

cloud garden
karmic obsidian
#

it it possible to copy over SFX from an existing item?

#

aka when setting it up

proper epoch
#

If you decompile the game and use the asset like that yeah, alternatively you can try to assign them via code

karmic obsidian
#

i dont want to rip assets

#

as that would mean i have to manually do that if it ever changes

proper epoch
#

You could access the existing scrap and run the reference line all the way from the game manager, to selectable level, to the scrap spawn array, to the scrap you want to pull sounds from, to the prefab, to the sound effects it has assigned to it

karmic obsidian
#

#dev-general message

#

/Assets/Plugins

lofty nymph
#

@tough path there is one other problem i can think of with the automatic bundle content loading, it makes it kind of hard to depend on and modify the content of a mod that uses it

tough path
#

whats an example?

lofty nymph
#

because said mod wouldn't have a dll

#

ig

tough path
#

Sure but if both parties rely on LethalLib we can just store that info ourselves, No?

karmic obsidian
#

@lofty nymph is there a way to check if an item is already registered?

#

Remove*Item and Register*Item could use null checks

#

and other safety checks

lofty nymph
#

Any stuff can be registered multiple times if people need to for some reason

#

any duplicate checks happen when lethallib actually registers stuff

lofty nymph
karmic obsidian
#

yeah thats what im doing rn

#

ty

alpine storm
#

Hi, I am testing with the library and trying to add random objects into the terminal, but when I try to add it, it doesn't work. In this case the error is in the "ExtensionLadderItem"

TerminalNode node = ScriptableObject.CreateInstance<TerminalNode>();
node.clearPreviousText = true;
node.displayText = "Testing the node terminal\n";
Items.RegisterShopItem(ExtensionLadderItem,null,null,node,5);

solar blaze
normal egret
tough path
radiant light
normal egret
#

Well, if unity support model ripping at runtime

#

It would be just a matter of taking a snapshot

radiant light
#

probuilder meshes dont behave like normal meshes

fresh folio
tough path
#

It is secondary

#

every aspect of the system is hooked up to take in assets manually

#

the assetbundleloader is abstracted from the actual content loading and just uses the functions any author can/would use for it

normal egret
#

Like that

#

But the other, more complex rooms will require a bit more work

radiant light
#

came out better than my rips in unity did

#

i ended up just starting a greybox for that very room funny enough

#

like 5 minutes ago

tough path
#

since we have file reading/writing perms with bepin i wonder if we could load in the facility dungeon, put it in a prefab and then write it to file

radiant light
normal egret
#

Hell i can probably remake all the rooms in blender lmao

normal egret
#

Oh god, i just realized that a lot of textures aren't properly set up what

normal egret
#

Not perfect 1:1 recreation but the door holes are at the right place

radiant light
#

but if you do actually recreate from scratch then itd be fine

#

and youre more than welcome to do so

#

and if you wanna do that - go ahead and throw me a DM as i'm working on setting up the dungen template stuff

normal egret
#

I mean, I can recreate them entirely if needed
Although if i do that, I need to create new materials that have the uv scale x:1 y:1
So that my blender export is 1:1 to what will be displayed in game

#

Right now i gotta fuck around with the blender materials to get an acurate preview

radiant light
#

if you keep polies low you can keep everything as 1 material

#

and i can probuilderize in unity

#

and material it inside unity

#

cause it doesnt need to be exactly the rooms, its basically just 'heres what roughly these rooms look like as reference'

snow inlet
#

Hi folks, I am getting this error and I am not quite sure what I am doing wrong. I have LethalLib and all its dependencies referenced but it still is causing issues. Any clue on my error? Thanks!~

safe flame
#

If you're using a mod loader like r2modman/Thunderstore Mod Manager just install the LethalLib mod in your profile and try again

snow inlet
#

Awesome, thank you so much, I'm getting a different error now, but at least it is something lol

simple sail
#

@lofty nymph Not sure if this should really go here or not but I got this error while trying to last at Kast, a moon mod that uses Lethal Lib. Not sure if it's on Kast or your mod.

#
[Error  : Unity Log] RuntimeNavMeshBuilder: Source mesh Cylinder is skipped because it does not allow read access
[Error  : Unity Log] RuntimeNavMeshBuilder: Source mesh toilet_b is skipped because it does not allow read access
[Error  : Unity Log] InvalidOperationException: Sequence contains no matching element
Stack trace:
System.Linq.Enumerable.First[TSource] (System.Collections.Generic.IEnumerable`1[T] source, System.Func`2[T,TResult] predicate) (at <dab7f68612224ba3ae40f651d44f9d4c>:IL_0011)
LethalExpansion.Patches.RoundManager_Patch.GenerateNewFloor_Prefix (RoundManager __instance) (at <e61fdeee146f454bbdb3aadbec0ef22d>:IL_00E3)
(wrapper dynamic-method) RoundManager.DMD<RoundManager::GenerateNewFloor>(RoundManager)
(wrapper dynamic-method) MonoMod.Utils.DynamicMethodDefinition.Trampoline<RoundManager::GenerateNewFloor>?1842349568(RoundManager)
LethalLib.Modules.Dungeon.RoundManager_GenerateNewFloor (On.RoundManager+orig_GenerateNewFloor orig, RoundManager self) (at O:/github/LethalLib/LethalLib/Modules/Dungeon.cs:180)
(wrapper dynamic-method) MonoMod.Utils.DynamicMethodDefinition.Hook<RoundManager::GenerateNewFloor>?-1807598776(RoundManager)
RoundManager.GenerateNewLevelClientRpc (System.Int32 randomSeed, System.Int32 levelID) (at <44743d9474784365a095189c76175301>:IL_0169)
RoundManager.__rpc_handler_1193916134 (Unity.Netcode.NetworkBehaviour target, Unity.Netcode.FastBufferReader reader, Unity.Netcode.__RpcParams rpcParams) (at <44743d9474784365a095189c76175301>:IL_0048)
(wrapper dynamic-method) Unity.Netcode.RpcMessageHelpers.DMD<Unity.Netcode.RpcMessageHelpers::Handle>(Unity.Netcode.NetworkContext&,Unity.Netcode.RpcMetadata&,Unity.Netcode.FastBufferReader&,Unity.Netcode.__RpcParams&)
Rethrow as Exception: Unhandled RPC exception!
UnityEngine.Debug:LogException(Exception)
Unity.Netcode.RpcMessageHelpers:DMD<Unity.Netcode.RpcMessageHelpers::Handle>(NetworkContext&, RpcMetadata&, FastBufferReader&, __RpcParams&)
Unity.Netcode.ClientRpcMessage:Handle(NetworkContext&)
Unity.Netcode.NetworkBehaviour:__endSendClientRpc(FastBufferWriter&, UInt32, ClientRpcParams, RpcDelivery)
RoundManager:GenerateNewLevelClientRpc(Int32, Int32)
<LoadNewLevelWait>d__106:MoveNext()
UnityEngine.SetupCoroutine:InvokeMoveNext(IEnumerator, IntPtr)

[Info   : Unity Log] RPC Table Contents
[Error  : Unity Log] InvalidOperationException: Sequence contains no matching element
Stack trace:
System.Linq.Enumerable.First[TSource] (System.Collections.Generic.IEnumerable`1[T] source, System.Func`2[T,TResult] predicate) (at <dab7f68612224ba3ae40f651d44f9d4c>:IL_0011)
LethalExpansion.Patches.RoundManager_Patch.GenerateNewFloor_Prefix (RoundManager __instance) (at <e61fdeee146f454bbdb3aadbec0ef22d>:IL_00E3)
(wrapper dynamic-method) RoundManager.DMD<RoundManager::GenerateNewFloor>(RoundManager)
(wrapper dynamic-method) MonoMod.Utils.DynamicMethodDefinition.Trampoline<RoundManager::GenerateNewFloor>?1842349568(RoundManager)
LethalLib.Modules.Dungeon.RoundManager_GenerateNewFloor (On.RoundManager+orig_GenerateNewFloor orig, RoundManager self) (at O:/github/LethalLib/LethalLib/Modules/Dungeon.cs:180)
(wrapper dynamic-method) MonoMod.Utils.DynamicMethodDefinition.Hook<RoundManager::GenerateNewFloor>?-1807598776(RoundManager)
RoundManager.GenerateNewLevelClientRpc (System.Int32 randomSeed, System.Int32 levelID) (at <44743d9474784365a095189c76175301>:IL_0169)
RoundManager+<LoadNewLevelWait>d__106.MoveNext () (at <44743d9474784365a095189c76175301>:IL_0076)
UnityEngine.SetupCoroutine.InvokeMoveNext (System.Collections.IEnumerator enumerator, System.IntPtr returnValueAddress) (at <e27997765c1848b09d8073e5d642717a>:IL_0026)

[Warning: Unity Log] [Dissonance:Network] (06:26:12.966) EventQueue: Large number of received packets pending dispatch (18). Possibly due to network congestion (last frame was 8.0753ms)
tough path
#

@tidal lark make sure your fbx's have read / write enabled

#

the runtime navmesh stuff needs it

lofty nymph
#

when you read a stacktrace the first part is where it stopped running, so usually the last mod namespace before that is where it died from

simple sail
#

Oh god, my bad. Mixed the mod names up.

#

I swear I know how this works

hollow sorrel
#

There seems to be incompatibilities with other mods when removing shop items when patching start of round to remove shop items

#

incompatibility with advanced company for example

vernal ledge
#

woah cool number

grizzled fractal
#

woah cool number

solar blaze
#

How's the custom levels integration stuff coming along?

#

Is that still in the works or did it get tubed? Can't remember who was working on that lol

tough path
#

what do you mean by intergration specifically

solar blaze
#

I thought someone was gonna merge a map API into lethal lib

#

Or is that staying as its own fork

tough path
#

Oh just as that yeah

#

so thats going to be it's own mod that's dependant on LethalLib so the level stuff can be updated fast without making LethalLib unstable

#

its going well

solar blaze
#

Oh sweet that's great to hear

#

Could you link the repo I'd like to keep a tab on it

tough path
#

I want it released asap

runic gull
#

Hello, is there any documentation/exemple about how to use the lib i struggle to find it myself

proper epoch
# runic gull Hello, is there any documentation/exemple about how to use the lib i struggle to...

for items, there's a textual guide on the wiki:
https://lethal.wiki/dev/apis/lethallib

or a video guide if you prefer that
https://www.youtube.com/watch?v=971OlPcVUHM

runic gull
#

I'm mainly interested about the entity part of the library

timid brook
#

the video should still help with getting setup to use lethallib

runic gull
#

Okay thanks

rain saddle
#

Are there any guides on making custom enemies with LethalLib?

runic gull
rain saddle
#

Does anyone know how to fix this error. I get the error when I spawn my custom enemy:
´[Error : Unity Log] NullReferenceException: Object reference not set to an instance of an object Stack trace: EntranceTeleport.Update () (at :IL_0064)´

tough path
#

the game just updated

rain saddle
#

I tried go back to v45 and I still got the error

devout glacier
#

This is worth reporting I think

#

for v49, to be clear

#

seems to be specifically to do with dungeon generation, as turning off Ooblterra's custom dungeon seems to make everything play just fine

karmic obsidian
#

v49

solar blaze
#

For me at least lol

karmic obsidian
#

i never noticed it

#

and like

#

errors = bad

solar blaze
#

I thought it was vanilla tbh

#

Happens the first time you open the terminal. Or maybe if you open it too fast

lofty nymph
#

doubt this is lethal lib tbh

solar blaze
#

Yeah vanilla

#

Just removed all mods

lofty nymph
solar blaze
#

And it happened

lofty nymph
#

the problem with these kinds of stacktraces is that lethallib will always show up in them, because it uses a hook that runs the original

#

lol

#

and it kind of destroys and attempt to trace it since it annihilates the actual line numbers

#

monomod annoyance

#

the actual error is coming form vanilla code somewhere

#

but i'd have to be able to reproduce the error in order to debug it since right now there is no way to tell where exactly it is coming from, outside of the function name

lofty nymph
devout glacier
#

as in WTO?

#

the version that produced this screenshot is a couple ahead of release but I dont think that should matter

#

I list LethalLib 0.9.0 as a dependency in that release description there but I'm using 0.10.1 (as is the current queued build) and it otherwise worked with no issues until v47 hit

lofty nymph
devout glacier
#

sure, go for it

devout glacier
lofty nymph
#

huh.. interesting

#

alright i think i know the issue

devout glacier
#

here's the code where I actually establish the dungeon if it helps

lofty nymph
#

it is probably related to the fact that the order of execution of unity callbacks changed again

#

so it is trying to generate the dungeon before the flowtypes are added

#

i think

#

actually no that makes no sense

lofty nymph
#
List<int> list = new List<int>();
for (int i = 0; i < self.currentLevel.dungeonFlowTypes.Length; i++)
{
    list.Add(self.currentLevel.dungeonFlowTypes[i].rarity);
}
int id = self.currentLevel.dungeonFlowTypes[self.GetRandomWeightedIndex(list.ToArray(), self.LevelRandom)].id;

self.dungeonGenerator.Generator.DungeonFlow = self.dungeonFlowTypes[id]; //  <---- It dies here
#

self.dungeonFlowTypes[id] does not exist..

#

but how can that be possible? because it literally gets the items from the list?

#

I'm stumped

#

there was no other changes here as far as i can tell

#

wait

#

dungeon flow id is -1

lofty nymph
devout glacier
#

on it

#

it's good MackThumbsUp

#

managed to get into the custom dungeon

#

thank you very much

lofty nymph
#

it should be independent of execution order now so shouldn't break with updates anymore

#

unless something is drastically changed

#

pushed

pliant ruin
#

aaaa LethalLib depending on LethalExpansion now causes LethalExpansion to load before LethalExpnasionCore

timid brook
#

? EDIT: oh soft dep lol

lofty nymph
#

i thought soft dependencies just caused the mod to wait for the other mod to load

pliant ruin
#

So BepInEx loads in alphabetical order, this means once it hits CirnoFumoScrap (which is before the internal name for LECore, it starts with com.) it will want to load LethalLib because it's a dependency and that means it has to load LethalExpansion which means LE now loads before LECore aaaaaaa

lofty nymph
#

lmao

pliant ruin
#

problem after problem the past week 😂

lofty nymph
#

@rare portal suggested i added it as a soft dependency for compatibility reasons

#

didn't realize it would have a cascading effect lol

pliant ruin
#

Would adding LECore as well make it load before LE again

lofty nymph
#

i.. have no idea?

pliant ruin
#

Best would be if LE added LECore as a soft dependency but I don't think Holo is around right now

lofty nymph
#

i haven't used or looked at either of these mods so i have no clue about anything in terms of compat lol

#

sounds like lethal expansion core is just a fork of lethal expansion

lofty nymph
pliant ruin
#

LECore is basically just a drop-in replacement, the problem is that mods rely on LE so you would often have to have both LE and LECore at the same time because you can't just remove LE without it forcing you to remove all the depedencies 😅

lofty nymph
#

well it seems like it would cause issues if both are installed already no?

#

wouldn't that cause lethalsdk content to be loaded twice

pliant ruin
#

LECore patches LE to not load, which is why it needs to load before it

proper epoch
#

Getting softlocked here in trying to update scpcb to the latest version (to LLL but batby mentioned something might be up here)

tough path
#

^ wasnt sure if related to the oobl issue i saw abit above

lofty nymph
#

looks like the same error

#

which i fixed with the latest lethallib update

proper epoch
lofty nymph
#

actually no, different error

#

hmm

lofty nymph
pliant ruin
#

Agreed

#

It can be fixed without it

#

I fixed it for LECore

lofty nymph
# proper epoch https://cdn.discordapp.com/attachments/1183968547353919558/1194406037059534888/i...

hmmmm interesting, the error was thrown from this code

var networkManager = UnityEngine.Object.FindObjectOfType<NetworkManager>();

RandomMapObject[] objarray = UnityEngine.Object.FindObjectsOfType<RandomMapObject>();

foreach (RandomMapObject randomMapObject in objarray)
{
    // loop through
    for(int i = 0; i < randomMapObject.spawnablePrefabs.Count; i++)
    {
        // get prefab name
        var prefabName = randomMapObject.spawnablePrefabs[i].name;

        var prefab = networkManager.NetworkConfig.Prefabs.m_Prefabs.First(x => x.Prefab.name == prefabName);

        if (prefab != null && prefab.Prefab != randomMapObject.spawnablePrefabs[i])
        {
            randomMapObject.spawnablePrefabs[i] = prefab.Prefab;
        }
    }
}

Which is supposed to link spawnable prefab to the correct game prefab

#

which means a prefab is defined in a RandomMapObject component which is not registered with the network manager

#

i guess?

#

specifically this line failed var prefab = networkManager.NetworkConfig.Prefabs.m_Prefabs.First(x => x.Prefab.name == prefabName); because it could not find the prefab (i should change it to firstordefault)

proper epoch
#

hmm, I'm still using the same dummy landmine/turretcontroller prefabs from when we were first fixing stuff

lofty nymph
#

weird..

#

i can add some logging

proper epoch
#

could it be from a random map object with no assigned elements? I had to re-apply them in moving to a v48 project

#

not impossible that I missed some, but it looks like there's a null check there

tough path
#

@lofty nymph when is that running

lofty nymph
#

RoundManager_GenerateNewFloor

tough path
#

ohhh

tough path
#

@proper epoch what are your dummy prefabs called

devout creek
#

yeah same error i was having around the roundmanager generatenewfloor

lofty nymph
#

it'll print out whatever prefab it couldn't find with this version

proper epoch
#

had an inkling something with your auto replacement might have been part of it

#

but will check 10.4 first

tough path
#

well in theory eva's one shouldn't do anything i don't think? because its just gonna set it to what it should be

lofty nymph
proper epoch
lofty nymph
#

well it won't

#

because i switched to FirstOrDefault

#

but i'll still fail in the same way

#

instead itll just log silently and ignore it

#

can you post your log after the dungeon generation

#

it should contain logs like this $"DungeonGeneration - Could not find network prefab ({prefabName})"

proper epoch
lofty nymph
#

uhh

#

huh

proper epoch
#

of note, the entrance door failed (though that might be an issue on my end), and none of the SCP doors spawned in

lofty nymph
#

that is concerning

#

oh

#

it would also log that if the prefab was already the correct prefab

#

unhelpful lmao

#

well the names are definitely correct

lofty nymph
proper epoch
lofty nymph
#

shrug

#

okay interesting

#
[Info   : LethalLib] DungeonGeneration - Prefab (Landmine) was already correctly mapped!
[Info   : LethalLib] DungeonGeneration - Could not find network prefab (TurretController)!
#

the turret is the thing it chokes on

#

i am 90% sure it was not called turretcontroller

#

but i might be wrong

cunning fractal
#

At last I have found this thread after you so gloriously triggered automod

lofty nymph
#

message too big

#

i think

cunning fractal
#

ikr

proper epoch
lofty nymph
#

i posted logs

#

good thing automod does not tell you what was wrong with a message

#

(i moderate another large discord, automod is fun)

cunning fractal
#

it was too big

#

I don't think it needs to be a thing considering it just makes things more difficult

lofty nymph
#

oh it did tell you? you know something i don't because it never gives any info when i look at whatever automod did lol

#

maybe thats just for the filters

cunning fractal
#

no it doesn't tell me but I can tell thats why I've seen big messages removed before

lofty nymph
#

lol

#

fair

#

i got automodded twice so far

#

the other one was potty mouth filter

#

:(

cunning fractal
#

santa may still bring you presents

#

you have a chance

tough path
#

@proper epoch container

#

not controller

lofty nymph
#

i knew it

tough path
lofty nymph
#

lmao i was about to check the prefabs but unity wouldn't open

#

i knew it wasn't controller

cunning fractal
#

Batby I just saw Scoopy's Variety mod for the first time using your loader and it is really dope. Makes me wanna make a dungeon.

proper epoch
#

ah, might have flipflopped the name in new proj

tough path
#

cons of auto asset replacement / LLL: you need to be specific with vanilla
pros of auto asset replacement / LLL: you get to look at vanilla
😜

lofty nymph
#

probably will be worth leaving these logs in

#

since if anyone else fucks it up it'll immediately be clear lmao

tough path
#

for reference btw eva LLL does that swap on initial load (before/around gamenetworkmanager start)

#

doesnt change anything, just so you know

lofty nymph
#

yeah, thats why it said [Info : LethalLib] DungeonGeneration - Prefab (Landmine) was already correctly mapped!

#

dungeon module is standalone thats why i have my own remap :p

proper epoch
tough path
#

pov your developing a mod that depends on an api that depends on an api

lofty nymph
#

should i make it throw a full on exception when someone fucks up the names?

tough path
#

naaa

#

cuz that means it would kill custom map objects, no?

lofty nymph
#

in which case, thats a problem

#

ig?

tough path
#

trueing i suppose

#

some generic networkmanager validation might be nice

lofty nymph
#

main reason for throwing an exception is to make sure people will notice

#

big red stacktrace moment

devout creek
#

glad i wasn't the only one with the issue with coding things lol

lofty nymph
#

okay pushed the update

devout creek
#

thank you so much it has been working better with the 0.10.3 with map generation

#

and not error out on the array line

lofty nymph
#

LethalLib 0.11.0

  • Added module: PrefabUtils
    • Added method: ClonePrefab()
    • Added method: CreatePrefab()
  • Added method: NetworkPrefabs.CreateNetworkPrefab()
    • Creates a network prefab programmatically and registers it with the network manager.
  • Added method: NetworkPrefabs.CloneNetworkPrefab()
    • Clones a network prefab programmatically and registers it with the network manager.
  • Added behaviour for Items module
    • When a scrap item is registered as a shop item, the LethalLib will now automatically create a copy and switch the IsScrap value.
    • When a shop item is registered as a scrap, the LethalLib will now automataically create a copy, assign sell values, set IsScrap to true, and add a scan node.

https://thunderstore.io/c/lethal-company/p/Evaisa/LethalLib/

CC: @frank lotus

#

why is discord formatting it like that lmao

fresh folio
#

once again asking for nuget support 😭

#

if I have to manual update this shit one more time im going feral

#

tbf I can pack it myself

fresh folio
#

I created a pack file but my internet went out so it’ll be uploaded like tomorrow

solar blaze
#

I don't really like these I think they're unnecessary and overreaching. There's edge cases where you'll set up things appropriately then the desired behaviour will break and I guess I'm just not sure what the use case would be. imo you should be responsible for how you structure your item. I also always test scrap / map objects by adding them to the store, there's edge cases where that can break / remove some implemented behaviours. Not really complaining, I can just make sure when I'm testing I temporarily switch the bool and I'll make sure cleaning company still works fine but didn't expect to see that and if I just booted up my PC updated and did some testing without reading and saw scan nodes missing and all this I would have been very confused haha.

#

I guess it's neat that if you're creating generic items you can submit it with isscrap inverted and it will set up some of the cut and dry stuff for you. Is that the use case? Idk maybe it will grow on me

frank lotus
#

Go look at #1192963844323147877

#

for how they happened

lofty nymph
frank lotus
#
  1. correctly scoped nuget API token (Evaisa.LethalLib) -> NUGET_API_TOKEN
  2. thunderstore service account token -> THUNDERSTORE_API_TOKEN
  3. enable actions write perms
#

but that's moot until i've acc done it lol

lofty nymph
#

One problem is that lethallib relies on mmhook for building so you'll need a workflow for generating that

frank lotus
#

hm

#

I want to add mmhook generation to the dehumidifier

#

for now though

#

could mmhook go in the repo?

lofty nymph
#

I'd love a bepinex publicizer type thing for mmhook generation

frank lotus
#

like it doesn't contain any implementations right?

#

hmmmmmmmmmmmmmmmmmmmmmmmmm

lofty nymph
frank lotus
#

Can you link me the hookgen docs

#

that you linked me a couple days back

lofty nymph
#

Lethalthings has a spawn menu that lets you spawn anything, with networking so clients can use it too (although no map objects right now)

lofty nymph
lofty nymph
#

this?

frank lotus
#

yes that's the one, I was looking in the Monomod folder, didn't see the multiple readmes facepalm

fresh folio
#

It just feeds in the relevant info needed to generate the patch

lofty nymph
#

yeah i know

#

i just mean it would be nice to have a bepinex publicizer type thing that automatically generates hook files for specific assemblies on build

fresh folio
#

Ah

lofty nymph
#

msbuild stuff

fresh folio
#

But then how would you use the hook files in development 🤨

#

If you don’t have them till it builds

frank lotus
#

Don't worry about it

lofty nymph
#

hmm true

frank lotus
#

Let me worry about it

lofty nymph
#

lol

frank lotus
#

Prebuild task is the answer you're looking for tho, lol

fresh folio
#

You can’t use a hook if it doesn’t exist yet lol

frank lotus
fresh folio
#

Technically you could suppress the errors but why would you do that

frank lotus
#

hmm

lofty nymph
#

a nuget package with the hook files would probably be better

fresh folio
#

Yeah a monomod nuget packages would be nice

#

But would require upkeep

#

Wah

frank lotus
#

I could just have dehumidifier generate an mmhook package for each game

lofty nymph
#

yeah the problem with stuff like that will always be that it requires someone to maintain it

frank lotus
#

as it already does that stuff automatically

frank lotus
#

it's automated lol

#

all I have to do is tell it the version numbers

lofty nymph
#

yes

#

but it requires you to do that

frank lotus
#

and I wouldn't even have to do that if lethal company was less stupid

lofty nymph
#

what if you stopped doing lethal company modding

#

lol

fresh folio
#

Yeah that’s what I’ve been thinking everytime I’m like wow this game is stupid

frank lotus
fresh folio
#

It’s just like why am I still modding this game when I could modding something more sane

frank lotus
#

which I will merge

fresh folio
lofty nymph
#

use steamcmd to detect updates and automatically push tf

frank lotus
#

Because the version numbering is not consistent

fresh folio
#

Cause zeeks has weird versioning yeah lmao

frank lotus
#

I can, and intend to do that with Dyson sphere company

fresh folio
#

Company

frank lotus
frank lotus
fresh folio
#

You see this is why you make a singleplayer game because then people can’t roast your code as hard or complain as much cause less people are compelled to mod it

#

Free

#

Either that or more successful single player games with active modding scenes have their own level creation tools or whatever to circumvent having to dive into the codebase itself

#

Or you’re Isaac and have the modders that bitch endlessly for good reason

#

Though repentagon came out so that game finally has usable modding tools I think

#

Idk I haven’t touched it… yet

solar blaze
# frank lotus then don't use them >:)

Well that's the thing sometimes you'll want to spawn non scrap items as scrap and if you do so now they'll get fiddled with. Idk I just don't see a use case where this is handy but I see a few edge cases where it will break stuff so it doesn't seem like a good trade. On a more positive note though if it's going this path adding a check for an audiosource and adding one if not is probably a good idea. Maybe even weight < 1. I think it would be nice if this was it's own seperate method for constructing / filling scrap and items.

frank lotus
#

spawning a non scrap item as a scrap item, the game will try and set its scrap value

lofty nymph
#

because things will be missing

#

this just solves those cases

frank lotus
#

the whole point is to let you spawn non-scrap items as part of the spawn random items routine

lofty nymph
#

it doesn't mess with anything that was already set up correctly as a scrap

#

The reason i added this is because i was switching the toy hammer to be a scrap, but wanted to keep a config setting to have it be a shop item

#

before, that would have required me to create 2 separate prefabs

solar blaze
#

Ah ok that's the use case

lofty nymph
#

it is more of a validation step

solar blaze
#

But I mean cleaning company spawns interact trigger objects in the scrap spawning routine and it's fine I just have a dummy grabbable object on the objects.

How exactly is your game dying? Does .clone or createnetprefab add a Physicsprop script or something if the object doesn't have one? That's the only part where I could see things falling apart

lofty nymph
solar blaze
#

Yeah that'll do it

lofty nymph
#

those are the things this solves by adding them if they are missing

solar blaze
#

Alrighty. Well in cleaning companies case I think all that will really happen is isScrap will be flipped and they aren't pickup able so it should be fine.

lofty nymph
#

actually i wonder

#

If IsScrap is false, does that avoid these errors too?

#

because in that case it might not check for the scannode and stuff

solar blaze
#

No isScrap false should still check for scan node and all that

#

isScrap only really tied to whether or not something is sellable and will count towards your quota right

#

Or is it just the latter

#

I think like the key is a great example of an item you'll want to spawn as scrap that's not scrap.

#

But I mean even if you have to flip it in the items .Start it is what it is

violet swan
#

How do i config the offer discounts of my item added with lethalLib? Is it done at random?
Also why does RegisterShopItem have more than one terminalnode?

lofty nymph
#

but for your information

#

it is because the game has 2 buy nodes for each item

lofty nymph
#

@solar blaze idk if you ran into this but little update, lethallib's store item removal thingy is currently breaking the item indexing, so if anyone disables an item, all the other items will buy the wrong thing

#

working on a fix right now

#

not sure how no one ran into this before Thonk

solar blaze
#

I don't think I have good to know tho.

However I think if update price is called repetitively it can break shit.

Could have been something else I did but I quit to menu and reloaded a save a few times then when I tried to buy an item it raised something

#

Cant remember what

lofty nymph
solar blaze
#

Right

#

Mines not live yet

lofty nymph
#

LethalLib 0.11.2

  • (Hopefully) Fixed issue with Terminal, where when a mod was disabling a shop item, all the shop items after it would mess up their orders.
fresh folio
#

@lofty nymph just kinda realized an issue with lethallib

#

so

#

when assigning a rarity to something you can only do it as one set value, regardless of the fact that people might want different rarities on different moons

#

I dont really want to make a jank check what moon we are on and hotswap rarity nor do I want to register content with a single flag over and over

#

I could write my own mod specific fix but
A. id have to patch lethallib stuff which would be jank as all hell
B. this should probably be a standard feature

proper epoch
fresh folio
tough path
#

at some point either lethallib or lethallevelloader or both when they get combined will have a dynamic scrap injection system similar to how LLL does dungeons

fresh folio
#

its not just scrap

#

its everything in the mod

tough path
#

i mean

fresh folio
#

shortcomings of the level flags system

tough path
#

that too then

#

ig

fresh folio
#

maybe Im misreading

proper epoch
#

Not at PC rn but roughly like this

Register(item, 20, Titan | Dine | March)
Register(item, 50, Vow | Assurance)

tough path
fresh folio
#

I shouldn’t hav to run register more than once :(

#

And If I want every single moon to have a different rarity than what

#

Running register for every moon in the game is crazy

proper epoch
#

I don't know how it could possibly be simpler, if you wanna have a unique value for each individual moon you could make it a loop

fresh folio
#

I feel like you’re also missing the part where this weird method is kinda not meshing with my content implementation system

#

As I’m trying to move listing moons for content into editor and also this completely does not work with how I load the items

proper epoch
#

Guess I'm just not understanding your goal or what your starting point of data is but I don't see how the current system is weird at all, if you've got a bunch of items all with different defined values for each individual moon a 3d array would handle it no sweat

#

And I don't know what kind of function you'd be after that can't be handled with the existing register function in a way that's clean

lofty nymph
fresh folio
lofty nymph
fresh folio
#

Thank god

#

I am free of downloading the mod 3 times every day

lofty nymph
#

i forgot who was the person that kept bugging me for a nuget package

fresh folio
#

Me

karmic obsidian
#

hell yeah nuget package

bronze cypress
#

was this fixed?

#

i saw lots of people saying it has new compatibility issues

frank lotus
bronze cypress
#

nice thanks

#

lol everyone swoops in to install right off the bat and there's usually an issue doesnt matter which mod XD

#

glad i woke up late for this one

frank lotus
#

I just had a brainlet moment

#

brain switched off while refactoring

bronze cypress
#

UAHGHHUAHGHHH brain not braining

gleaming zinc
#

Can I use the custom enemy API to reskin them into a custom model I made? If so; Is there someone that can help me do that or just point me in the right direction?

lofty nymph
gleaming zinc
lofty nymph
fresh folio
#

@lofty nymph how did you plan for the dictionary to be fed in?

lofty nymph
#

you can combine level flags ofc for each entry

fresh folio
#

and its currently in you say?

lofty nymph
#

yeah

#

as of 0.12.0

fresh folio
#

Hm

#

Ill try again ig

#

there we go

#

cool

#

freedom

fresh folio
#

@lofty nymph oh lord what did you do to the structure

lofty nymph
#

?

#

lordfirespeed did some refactoring but i don't think any function signatures were changed

lofty nymph
#

Also i didn't add the dictionary yet for anything except scrap

#

LethalLib could really use a fucking rewrite because it is a headache to hack this shit in without breaking backwards compatibility

lofty nymph
karmic obsidian
#

any breaking changes?

lofty nymph
#

Shouldn't be

fresh folio
fresh folio
#

Closest thing I’ve been able to find is in contentmanager but I don’t want to use it

lofty nymph
#

It should be in the exact place you were pointing

#

Modules.Enemies

#

Are the methods private or something Thonk

#

Nope public static

fresh folio
#

Weird I’ll try again when I get home

lofty nymph
#

I am confused

fresh folio
#

I am too

#

I don’t understand why it just wasn’t showing up

#

I am using the nuget package if that would change anything but it shouldn’t

lofty nymph
#

If you can access one part you should be able to access the others

#

If you cant access anything then there is probably a bigger issue

#

I am not home right now

#

But when you have the chance can you check the contents of the nuget package / decompile the dll if it exists at all

fresh folio
lofty nymph
#

I am not using the nuget myself

frank lotus
#

uh

#

let me look

frank lotus
#

...into that later

fresh folio
#

...

frank lotus
#
<PackageReference Include="Evaisa.LethalLib" Version="0.13.0"/>
#

Are you perhaps referencing (and old version of) the DLL and the packge at the same time?

fresh folio
#

No I stopped referencing the dll

#

technically dont need these since I have the nuget gamelibs

frank lotus
#

github link for the whole csproj?

#

and also pls dotnet restore

#

just to double check

fresh folio
#

buh

#

it works in my main class?

frank lotus
fresh folio
#

and they're under the same namespace

#

holy shit im so stupid im sorry 😭

#

I thought I was typing in my method

#

but it was actually the class

#

fuck me

frank lotus
#

:)

#

that's ok

#

don't worry about it

frank lotus
#

rubber duckie method go brrt tho

fresh folio
#

Ive been doing mad class nesting

#

so I was like oh this must be a method

#

clueless

frank lotus
#

haha 😂

flat monolith
#

hello, i've been trying to add a deco item using lethallib, it was working fine with the same prefab as it's scrap version, but i wanted it to be placeable like the rug, and have a starting spawn location, I've tried using the setup below on the unlockable prefab but it doesn't seem to spawn anymore, any help would be appreciated

narrow citrus
#

why can't i buy my own item?

#

it says no object supplied with the action or word was typed incorrectly or does not exist

#

and when i type buy [my item name] it says this action is not compatible with the object

lofty nymph
narrow citrus
lofty nymph
#

also a log file would help

#

however a common issue is that the name overlaps with the name of something else in the game, causing it to be interpreted wrong.
the game doesn't interpret multi word inputs as a single word. essentially when you type buy night vision goggles the game turns that into buy night, and looks for any terminal keywords that start with night

narrow citrus
#

ohh how do i fix that

lofty nymph
#

i am not sure that is the case here

#

can you send your bepinex log?

narrow citrus
#

it says parsed word night could not parse vision could not parse goggles

lofty nymph
#

try uhh

#

typing night-vision-goggles

#

if that works then the spaces are the problem ig

narrow citrus
#

nope

#

it just says this

#

nvm

#

i found the issue

fresh folio
#

@lofty nymph allegedly I cant run custom terminal nodes through the same method that gets fed a dict?

#

its trying to use the base one

lofty nymph
fresh folio
lofty nymph
# fresh folio Keyword should
public static void RegisterEnemy(EnemyType enemy, Dictionary<Levels.LevelTypes, int>? levelRarities = null, Dictionary<string, int>? customLevelRarities = null, TerminalNode infoNode = null, TerminalKeyword infoKeyword = null)
    {
        var spawnType = enemy.isDaytimeEnemy ? SpawnType.Daytime : enemy.isOutsideEnemy ? SpawnType.Outside : SpawnType.Default;

        RegisterEnemy(enemy, spawnType, levelRarities, customLevelRarities, infoNode, infoKeyword);
    }
#

Wait no

#

Thats the wrong one

fresh folio
lofty nymph
#

I am on mobile it is incredibly hard to read source code

#

Lol

lofty nymph
# fresh folio Idk why it’s having a stroke then
public static void RegisterEnemy(EnemyType enemy, SpawnType spawnType, Dictionary<Levels.LevelTypes, int>? levelRarities = null, Dictionary<string, int>? customLevelRarities = null, TerminalNode infoNode = null, TerminalKeyword infoKeyword = null)
#

this is the right overload i think(?

#

the other one doesn't take a spawntype

#

idk which one you need

flat monolith
willow spade
#

try changing y offset

#

for me i went into unity explorer and messed around with the y offset until i got it to work

#

and then use that value back into unity

solar blaze
#

hey map objects get added to levels each time the lobby is opened. You have to restart the game to prevent this

#

To test this create a spawn curve of 0,1 and 1,1 (always spawn one)
open the lobby once and you will see one of that item, close that lobby and reopen it, 2 will spawn and so on

#

This is trying to remove duplicates when they don't exist instead of when they do

lofty nymph
#

lmao

solar blaze
#

haha ik, my latest update has a bunch of map objects where it's integral only one spawns and people were saying a bunch were spawning, I thought they were playing with some difficulty mod that iterates over map objects and adjusts the curves at first lol

lofty nymph
lofty nymph
solar blaze
#

sweet thanks a bunch

willow spade
#

I am trying to update my unlockable price and it still purchases at it's original registered price

#

i would type the name and on the confirmation page it will show the changed price but pay using the registered price

#

anyone know how to fix this?

#

nvm i got it, updating lethallib made it work

lofty nymph
#

i do not recall any changes related to this

willow spade
#

.12.1

#

yeah it was working fine yesterday

#

idk what happened

lofty nymph
willow spade
#

yeah

lofty nymph
#

I have heard some people complaining about prices not updating sometimes in lethal things for example, or things not being removed from the shop

#

but it has been really inconsistent

#

like i haven't been able to reproduce it on my end

#

if it breaks again and you want to do some experimenting i'd appreciate it

#

i truly have no idea what could be going wrong

willow spade
#

weird, my unlockable was working fine yesterday when i built the project and then today i made a few changes that didnt involve it and it just broke

willow spade
timid brook
#

Are there any good examples of mods utilizing the rarities dictionary for scrap? Trying to set it up for myself but still a c# noob and microsofts documentation on dictionaries is a mile long lol

#

Would much rather just learn by example

lofty nymph
proper epoch
frank lotus
#

huh, it is pretty unhelpful

karmic obsidian
#

dictionaries are just maps

#

you got a key, you got a value

#

you can get value by key, you can store value by key

#

you can iterate on all keys

#

you can tryGet or getOrDefault for extra safety for when there isnt a key

fresh folio
solar blaze
#

@lofty nymph idk where you @'d me but I implemented the store config syncing yes, haven't heard any bugs about it yet I'll let you know if I discover anything.

fresh folio
#

Assigning new values to a dictionary is pretty easy

I personally do it in editor but doing it in code is easy to figure out

lofty nymph
lofty nymph
# fresh folio I have my ways :3

oh btw, do you have any idea what could be preventing a custom enemy from opening doors?
it keeps getting stuck on the edge of the door like this

#

EnemyAICollisionDetect is what makes it able to open doors afaik

#

but i have that all set up

#

so my only guess is that it is somehow failing to hit the trigger

timid brook
#

I think Chaos struggled with that too, his solution was to make the AI blow the door off the hinges lol

lofty nymph
#

my solution is making it open doors when it gets near it

#

psychic fish

frank lotus
#

(i think that works)

devout glacier
#

I had the exact same problem and it turns out my issue was just that I didn't tag the component with the colliders on it as "enemy"

#

WTO's enemies all have a "collision container" empty with a capsule collider, rigidbody, and the EnemyAICollisionDetect all on it, that needs to be tagged and layered properly

devout glacier
#

here's exactly how I have my collisions set up

#

the main mesh inherits from the transform

#

this was the problem that was leading me to having them only react to weapons but not doors

wintry dew
#

custom dungeon's door sound and every custom item sounds are played twice sad

#

how do I fix it ?

lofty nymph
#

@tough path was it you or someone else who figured this out

#

I think lethallib had a utility function somewhere for fixing the mixers if it is caused by that Thonk

#

i have to go sleep

tough path
#

I need to do a pass on my audio collection and restoration this week

wintry dew
tough path
#

@wintry dew it needs to be the one vanilla uses

#

so if yours is from the assetrip thats not the right one

wintry dew
#

im confused

#

the door object is a prefab from the original lc asset

tough path
#

As in your spawning it at runtime or it’s from the assetrip

wintry dew
#

ohhhhh

#

wait

tough path
#

Yeee a copy of a vanilla asset != that actual asset. So in LLL I usually automatically replace all the asset references in a moon with the real ones at runtime

idle oasis
tough path
#

@proper epoch @torn badger ^ incase relevant

proper epoch
#

Yeah already figured out the whole enemies that can open doors thing, gonna leverage it for the new doors

fresh folio
#

Sorry

devout creek
#

ye i had to figure it out too for the doors and enemy it seems to be a trigger collider that is interacted with the door also having a nav obstacle on door

so i think enemies need a trigger collider and enemy tag and enemies layer

doors need door lock script and animated object interact script

had to test a bunch to get enemy to work for our doors

#

here is the flowerman i ripped from game to figure out how it works to get doors working

has a nav agent and a capsule collider inside the nav agent radius that has a trigger checked on it

#

here is decompiled script for door lock

timid brook
#

Anyone know why this code would still be using the base method for RegisterScrap instead of the newer overload that takes <Levels.LevelTypes, int> dictionaries as params? I'm using the latest LethalLib as a dependency

#

it seems to be forcing the base method always

#

where this is the one I want

candid willow
#

are your levelRarities and customLevelRarities nullable? if not, make their types nullable, that could be the issue

timid brook
candid willow
solar blaze
#

@stray sluice @humble pasture what do you think about removing RegisterNetworkPrefab from this (or adding a flag).

It seems like it becomes deep and when doing something like

GameObject prefab = NetworkPrefabs.CreateNetworkPrefab(name);
prefab.AddComponent<T>();

The added component won't be reflected in the registered object.

humble pasture
#

idk, we just figured out how to programmatically create network objects; for the actual implementation in lethal lib you'd have to ask @lofty nymph

solar blaze
#

oh I thought it was your pr and you credited yourself for some reason lol mb

solar blaze
#

hmmm ok

lofty nymph
#

Prefabs are references

#

so until spawned, it gets updated on the fly

#

afaik

#

maybe i am mistaken

solar blaze
humble pasture
#

you sort of are @lofty nymph

#

yes prefabs are just references, but once you register it, the gameobject you registered has no impact on the network prefab registered in the network manager

#

to modify it from there, you have to get the reference from the network manager

#

at which point to can modify(ish) it on the fly (until it gets spawned)