#archived-code-advanced

1 messages Β· Page 100 of 1

regal lava
#

combined mesh idea was probably the easiest solution with unity to generate a new mesh without touching code

#

static batching is just some optimization for culling after you have your mesh data, and chunked it accordingly.

#

beyond static batching you also have gpu instancing from the shader, but you can't have both enabled

deep jasper
#

so well, each grass is anyways an individual gameobject

#

and each is marked static for batching

#

shouldn't this be moved to GPU anyways just to have more performance?

regal lava
#

one thing though is static batching is resolved at runtime, so yeah it's a little hard to work with on the editor

deep jasper
#

I mean i generate grass positions at runtime based on current density param

#

just the positions

#

I swear i can let GPU do that in parallel

#

and then also let gpu cull stuff if it's possible

regal lava
#

It's up to profiling to compare if static batching is better than GPU instancing, but from my testing I usually do use static batching for non-moving meshes and GPU instancing otherwise.

deep jasper
#

is grass counted as moving tho

#

i mean it might have wind as part of vertex shader

#

so it kinda displaces itself each frame based on noise

regal lava
#

GPU instancing may be better then, but I need to check again to see if vertex manipulation does break batching

deep jasper
#

Im just extreemly noob at grass coding

#

but my initial idea was to have terrain as cell combination, which is streamed to player at runtime

deep jasper
#

and so each time cell should load, i calculate random grass positions on the terrain and objects placed on it

regal lava
#

Oh nice. In that case could be better for mobile haha

deep jasper
#

so well, some objects might support grass growing on them, and some don't

compact ingot
#

It’s also how TABS & co can play animations on millions of objects

#

(Shader based animations)

deep jasper
#

and then come the grass lod and frustum culling/distant culling problems

#

which idk how to solve properly

#

like sure, each frame calculate distance to each grass pos and change mesh to lower one or even ignore from matrix

#

but fps falls to 20 or 5

regal lava
#

Culling stuff is just something you usually balance with chunks

deep jasper
#

but doesn't unity use frustum culling on individual gameobjects by default

#

like a built-in feature

#

even if they are spawned at runtime

regal lava
#

right, so this is what static batching help resolve. It'll cull indepedent objects, but still draw it all in the least amount of calls as possible

deep jasper
regal lava
#

otherwise individual gameobject renders is one drawcall each

deep jasper
#

this things looks exactly as i want it to be xD

#

and yeah sure it costs πŸ™‚

regal lava
#

https://www.youtube.com/watch?v=jw00MbIJcrk
Guys a memer but he uses some alg to cull in a similar way

While billboard grass is a performant, easy option for visualizing grass, modern games like Breath Of The Wild are able to utilize real geometry to get more interesting and appealing foliage. How can games nowadays afford to do so?

Support me on Patreon!
https://www.patreon.com/acerola_t

Twitter: https://twitter.com/Acerola_t
Twitch: https://w...

β–Ά Play video
#

but dude worked for nividia so he's usually got some good ideas

deep jasper
#

i watched all 3 of his grass videos

regal lava
#

it's all computed in the shader which is ideal, but it's his alg at the end which makes the video

#

but too crazy to me. I think a few more drawcalls and chunks is fine and let frustum culling do the work

deep jasper
#

if fps is higher than 140 on my pc then yeah, a few more draw calls is fine

#

but when it's 20

#

πŸ’€

compact ingot
regal lava
#

all his videos are like that

compact ingot
#

yeah

#

😦

regal lava
#

it's like wow cool waves but really how

compact ingot
#

anyway, solving the "indirect" bit and the "culling" bit in a performant way is so non-trivial that you can just stop attempting it unless thats what you want to specialize in, programming/dev wise

#

bite the bullet and get one of the assets, you're just reinventing the same code anyway if you DIY, this is a solved problem and its somewhat weird that its not a base engine feature

#

also, if you want to DIY, you can also use vfx-graph to render grass πŸ˜‰

deep jasper
#

hehe

#

lez go

regal lava
#

"This asset needs shaders capable of indirect instancing. Such shaders can be hard to obtain, and a full tutorial on how to obtain those is provided in the Github page. However 1 shader suitable for HDRP is provided allowing to display grass with wind deformation."

compact ingot
#

instancing is only half the rent, you also need to shade the vegetation nicely πŸ˜‰

regal lava
#

What does Unity's terrain usually do anyway? Chunk/Frustum too eh?

compact ingot
#

and you need to be quite careful what you do there because of the many instances

regal lava
#

I'd really suggest trying some Mesh builder and generate a SDF of a terrain then build your meshes in chunks

#

probably the easiest mid solution for decent performance + add on some static batching for trees

compact ingot
#

the terrain is already a SDF of sorts

regal lava
#

I've found it alright for generating a ton of grass, I just think the UI/tools a little dated

compact ingot
#

true

#

but adequate to make trashy steam polluting shovelware πŸ˜›

#

you can go very far with the unity terrain if you replace basically everything except the auto LOD πŸ˜„

#

actually the problem with unity terrain is IMO that once you try to go big with it you run into way worse engine limitations than just grass rendering

#

try loading open world chunks smoothly LOL

deep jasper
#

well, if chunks are small, it's not a big deal

compact ingot
#

try building a game with 100+ chunks (takes forever)

compact ingot
deep jasper
#

256x256 with no grass attached

#

grass is procedurally generated

compact ingot
#

well, you'll still get frame drops even with 256 chunks

deep jasper
#

you mean instantiating the terrain gameobject

#

out of terrain data

compact ingot
#

basically what happens between 90% and 100% in the async load blocks the main thread

deep jasper
#

it's also lots of objects which should be spawned ig

compact ingot
#

you can time-slice your start functions and instantiate all gameobjects manually after the load to spread it out

deep jasper
#

i render first cells around the player while he is on loading screen

compact ingot
#

but that is just very inconvenient and complicated and should be part of the engine

deep jasper
#

and then when player goes to another cell, i cut the ones which are not in range and spawn new ones

compact ingot
#

yes, but that alone doesn't get rid of the hiccups

deep jasper
#

i can probably let them spawn one by one

#

but yeah, instantiating a single 256x256 terrain mesh might take time

compact ingot
#

well, in any case, you can do a lot of work around the fundamental engine problem, i just think this should not be neccessary

#

also there is no tool support for it, its just a pain, and slow 😦

deep jasper
#

what if i spawn a flat plane or smth and then give it several seconds to curve using the height map

#

player won't rly notice anyways

compact ingot
#

if you're really dedicated i think you can make a streaming system that incrementally loads data and instantiates and displaces stuff

#

but thats akin to building a custom engine

#

so what's the point?

deep jasper
#

well, doing a moddable game

#

which supports terrain changes

#

each changed terrain gets packed to an asset bundle, and then game overrides references when user starts it

compact ingot
#

sounds like a non-fun problem to have

deep jasper
#

well, i wrote a lot of editor code already

#

the biggest problem rn is image/audio implementation

#

writing an audioclip to a bundle and then loading it for modder to use

#

rn my code allows me to unpack any bundle and drop it's contents to Assets folder

#

so it's like a "dependency", which is written inside the mod description

deep jasper
#

ScriptableObjects were the easiest

#

Model Prefabs too

heady cargo
#

Hi guys, what would be the best way to create a map transition system in which I have a chained list of maps?

Points about the system:

  • It will be possible to move forwards and backwards in the maps.
  • Scenes will be in different files
  • And there may or may not be dynamic loading of the assets in each map, depending on whether the player moves forwards or backwards.
dusty wigeon
warm wasp
#

I might just be being stupid, but can someone explain why the following code isn't working? I'm trying to get a Game Object to move in the direction that it's facing.

rb.velocity = transform.forward.normalized * speed;

I've tried debugging transform.forward, but it is always equal to (0,0,1), regardless of the Game Object's rotation.

sly grove
#

also there is no sense in normalizing transform.forward

#

it is already a unit-length vector

warm wasp
#

oh i'm so dumb i meant to put this in general, my mistake

#

but well i'm here, i've tried debugging rotation as well and the value is changing

#

so the object is in fact rotating

sly grove
#

show your log code and what was printed, etc

warm wasp
#
        rb.velocity = transform.forward.normalized * speed;
        Debug.Log(transform.forward.ToString() + transform.rotation.ToString());

Outputs: (0.00, 0.00, 1.00)(0.00000, 0.00000, -0.18319, 0.98308)

sly grove
#

you're logging a quaternion

warm wasp
#

correct

sly grove
#

Debug.Log(transform.eulerAngles)

#

if anything you're probably rotated on the z axis

#

which is just a roll

#

which will not affect which direction transform.forward is

warm wasp
#

should i do transform.eulerAngles instead of transform.forward in the first line?

sly grove
#

no

#

of course not

warm wasp
#

it outputs: (0.00, 0.00, 1.00)(0.00, 0.00, 183.24)

sly grove
#

yeo

#

like I said

#

your object is still facing directly forward

#

it's just rolled

#

The code is working perfectly

warm wasp
#

oh i see what you mean

#

what can i use so forward isn't based on the z axis but instead x or y?

sly grove
#

the z axis is always forward

#

that's nono negotiable

#

maybe explain what you're trying to actually do

#

is this a 2D game?

warm wasp
#

yes

sly grove
#

If it's a 2D game then "forward" is usually right or up

#

so you want either transform.right or transform.up

#

the red arrow is transform.right

#

the yellow/green arrow is transform.up

#

(when you have an object selected and have the move tool on)

#

forward is the blue arrow

warm wasp
#

alright that works, thank you

sly grove
#

which for 2D games usually just points directly into the screen

warm wasp
#

and sorry about putting it in the wrong channel

urban sandal
#

I have a file which contains optimized vertex data as :

UInt8 [bitsize =  8] = VertArray, NormalArray, BoneWeightArray, trianglesArray ```
I'm looking for a dev who can write a script which can load this optimized mesh in unity by converting the UInt arrays to Vectors2, Vector3, etc
If anyone is intrested in doing this job please text me back, I'm also willing to pay a good amount for this.
thorn flintBOT
hardy jacinth
#

why Unity.properties doesn't generate partial PropertyBags for abstract types? (annotated with [GeneratePropertyBag])

swift osprey
#

Can someone forward me more information about the structs going to the stack instead of the heap as an optimization step? I cant find something tangible regarding Unity.
For more details;
I read from somewhere that initializing Vector3s inside a Update is not as expensive as creating a class, and that Vector3s are like for example floats since they are structs, that they dont generate garbage.

sly grove
#

it's just the difference between value types and reference types in C#

swift osprey
#

Much appreciated, I'll read them through.

steel snow
#

how do you serialize a graph object which contains references to monobehaviours that are always in the scene ?

#

i have nodes which are game objects with a node class but the graph itself uses dictionaries so won't just remember the data

#

if i just store the raw data, the issue then when i deserialize is the nodes are already gameobjects in the scene so how do i get the data back to them

tiny pewter
#

add component (or reference the existing one) then load the data back to the class?

steel snow
#

huh?

#

you might need to be a bit more descriptive

#

the nodes are already in the scene so when the graph deserialises it needs to inform the nodes about their connections so they have connection info

tiny pewter
#

how you serialize the graph? adjacency list or edge list?
build the adjacency list first then you have the connections of each vertex

steel snow
#

   public void OnBeforeSerialize()
    {
        _connections.Clear();

        List<INode> nodes = new();
        List<INode> neighbours = new();

        _graph.GetAllNodes(nodes);
        foreach (var n in nodes)
        {
            neighbours.Clear();

            _graph.GetConnectedNodes(n, neighbours);
            foreach (var neighbour in neighbours)
                _connections.Add(new Connection(n as Node, neighbour as Node));
        }

        Debug.Log("Serialize " + _connections.Count);
    }```

like this
#

then on deserialize im trying to load back in the connections and link them to gameobjects already in the scene

tiny pewter
#

this is edges list

steel snow
#

yes the edges have a reference to the two node game objects

tiny pewter
#

when you deserialize it you get the edges list back, do you have a hashtable or any other mappings that allows you to get the gameobject back from based on node identifier?
this is not how you deserialize but how you get the node gameobject in world back based on some data

#

when you first load the graph you must know how many vertices the graph has then create the gameobjects

steel snow
#

the graph has a dictionary for adjacencies it holds a reference to a monobehaviour

#

the issue is how i link that back to the object in the scene on deserialize

#

private HashSet<T> _nodes;
private Dictionary<T, HashSet<T>> _edges;

this is in my graph object

#

neither can be directly serialized

tiny pewter
#

isnt each vertiex has its own unique identifier?

steel snow
#

since _connections will be an array of Connection (node A, node B) these are references... would that still link the right game object on deserialize

#

well the reference is the identifier and they implement IEquatable

#

public sealed class Node : MonoBehaviour, INode
where
public interface INode : IEquatable<INode>

tiny pewter
#

reference can be identifier since they are address and address is unique.... but also got changed when the application closed and open again
i would separate the data about the vertex and gameobject, since you wont deserialize the whole monobehaviour, and i would assign the unique identifier to gameobject and vertex pair
eg i have a graph
vertex id: neighbor
0:2 3
2:
3:1 2
1:
and i would store an array of
index 0 1 2 3
GameObject A B C D
once i deserialize the graph then i use the vertex id and array index to access the gameobject in the array and load the data back to gameobject
if you need to load other graphs and no enough gameobjects in the array, instantiate more

steel snow
#

the issue is the graph needs to reference INode interface so just storing IDs is not ideal

#

seems like i need to handle the link between game objects and ids in a monobehaviour that manages the graph then

midnight violet
#

Not sure if I remember correctly, but I was using scriptableobjects to store the information, as those are persistent files

steel snow
#

SOs are good but i plan to add to the graph at run time so still need to save but you can't really save to SO at run time right?

midnight violet
#

you can , depending on your data, save it and overwrite the SOs default state at runtime with that serializeddata

steel snow
#

hmm why must this be so confusing

tiny pewter
#

what data you store in the file?
i mean you can include one more field to identify each vertex if not exist

#

then provide the vertex id to gameobject mapping
you cant use reference equal only to identify different vertex otherwise i have no idea how you store the edge

midnight violet
#

I am wondering, if your handling of data and gameobjects is the right way to do. If you edit it on runtime, the nodes should store all info about the gameobjects and update them on runtime. Not mirror their data

steel snow
steel snow
#

the graph object just takes an INode type but because its dictionary and hash sets when i recompile the data is lost

midnight violet
#

So you are not storing anything anywhere yet?

steel snow
#

well im serialising and deserialising on a monobehaviour

#

so it should keep it there

midnight violet
#

You got the code for that?

tiny pewter
#

but you are not (de)serialize the whole monobehviour since you implement your interface

steel snow
#

sure i use the ICallbackReciever with this bit of code:

    [SerializeField]
    private List<Connection> _connections = new();
    [Serializable]
    public struct Connection
    {
        [SerializeReference]
        Node _a, _b;
        [SerializeField]
        string a, b;
        public Node A => _a;
        public Node B => _b;
        public Connection(Node a, Node b)
        {
            _a = a;
            _b = b;
            this.a = a.name;
            this.b = b.name;
        }
        public override string ToString() => $"{a} -> {b}";
    }
    public void OnBeforeSerialize()
    {
        _connections.Clear();

        List<INode> nodes = new();
        List<INode> neighbours = new();

        _graph.GetAllNodes(nodes);
        foreach (var n in nodes)
        {
            neighbours.Clear();

            _graph.GetConnectedNodes(n, neighbours);
            foreach (var neighbour in neighbours)
                _connections.Add(new Connection(n as Node, neighbour as Node));
        }

        Debug.Log("Serialize " + _connections.Count);
    }

    public void OnAfterDeserialize()
    {
        Debug.Log("Deserialize " + _connections.Count);
        foreach (var connection in _connections)
            Debug.Log(connection);
        _graph = new();
        foreach (var connection in _connections)
            if (!_graph.TryConnect(connection.A, connection.B))
                throw new Exception($"Failed add connection {connection}");

        _connections.Clear();
    }
midnight violet
#

Sounds to me like the mono is just resetting as they are recompiled, which makes sense.

#

Yeh, I would take that whole data part away from the mono and use something persistent like an SO with save and load functions or what not.

steel snow
#

right but is my approach wrong here with using Node refernces?

#

would the reference still be valid when re-opening the engine

#

if its not wrong ill have to do a <int,GameObject> setup

#

but that would require a re-write of my graph object at this point

tiny pewter
#

reference is inconsistent across different life time/cycle
btw you can refer to some real world example of how to storing the graph in plain text and think how you would load it to your application

steel snow
#

right but i need to figure out how to find the node in the scene when loading it back in if i cannot use node reference

tiny pewter
steel snow
tiny pewter
#

and i would store an array of
index 0 1 2 3
GameObject A B C D
use vertex id as key and assign a gameobject to each vertex, reuse the gameobjects when loading a new graph

your problem is not about where the graph comes from (yes you can load a graph from internet or ram, file system is just one of the sources) but how to load the graph to your world (hence how to store it)

steel snow
#

so my graph now has to return a node id aswell

tiny pewter
#

yes, you can use string btw, as long as it is unique and you can associate each vertex with its data

steel snow
#

actually i guess maybe something like this:

    [SerializeField]
    List<uint> _ids = new();
    [SerializeField]
    List<GameObject> _nodes = new();
    [SerializeField]
    private List<Connection> _connections = new();
    [Serializable]
    public struct Connection
    {
        [SerializeReference]
        uint _a, _b;
        [SerializeField]
        public uint A => _a;
        public uint B => _b;
        public Connection(uint a, uint b)
        {
            _a = a;
            _b = b;
        }
    }
#

so the serializer only cares about ids not the graph

midnight violet
#

Again, I wonder why you store the gameobjects instead of creating a dataset of nodes. And from that dataset, you create the gameobjects with the relevant data

steel snow
#

because the node gameobjects need to know their connection data when i load the graph in

#

they already exist in the scene

midnight violet
#

No, your node dataset needs to know the ocnnection

tiny pewter
#

separate the data from gameobject and monobehaviour using a struct or class (but your monobehaviour will store it)

midnight violet
#

Imagine a database with two users in a mulitplayer game. Those are stored on the database and created on runtime. If you add a new user, you first create that user on the database and tell all clients to create a gameobject with the name of hte player coming from the bdatabase. You dont throw in a new gameobject, tell the server to copy that gameobject to all clients and figure out something locally. Same goes for your dataset nodes. You have the database storing all connectinos, positions of the objects and what not. And in runtime, your scene will take that data and create the gameobjects out of it.

#

and if you want to add something on runtime, you still can create a new gameobject with ocnnections and pass all that information to the database back.

steel snow
#

but the nodes are already in the scene as static objects so creating them on deserialize doesn't make much sense to me

tiny pewter
#

having example is much better than my answer
so reuse the gameobject

midnight violet
#

You said, youw ant to create more on runtime

steel snow
#

how do i find the specific gameobject for the specific node data in the graph without using GameObject serialize?

steel snow
#

but the rest are already present

tiny pewter
#

you need a object pool

#

when the graph is unloaded then recycle all the vertices back to the pool

midnight violet
steel snow
#

no i dont understand how instantiating them would help because then i can't just add them to a scene during level design id have to add the data to a graph rather than add the node to the scene which is harder to level design by ?

#

or im not understanding what you're trying to say πŸ˜„

midnight violet
#

second πŸ˜„ πŸ˜‰

steel snow
#

thought so lol

#

ive been struggling to get my head around how to think about it lol

midnight violet
#

Let me try to rephrase it. So, lets start from, what is your node graph actually doing in the end? what is its purpose?

steel snow
#

the graph contains a hash set of all nodes (INode) and all the connections. it also checks with the nodes if a connection can be made (INode) contains things like CanConnect(nodeB) etc

#

connections are in a dictionary

midnight violet
#

Thats not the question πŸ˜„

#

What is its purpose, not how does the code structure work

steel snow
#

other than that its just storing that data for which i can get info from

#

for any kind've waypoint setup i need

midnight violet
#

Ahhh, waypoint system, got it

#

And you want to set waypoints in runtime for units lets say, and if you save and reload the game, you want those waypoints to be persistent

tiny pewter
#

short: dont use reference or try to serialize any kind of reference (they are pointers and not persistent), use other stuff to identify each data

steel snow
#

the static stuff

tiny pewter
#

dont talk about graph now, you want to store some data of some npcs so how would you identify each npcs? ofc its name or id
then when you store it you save the npc data with its name or id
when deserialize it you create a gameobject (or get it from pool) and load the data back

#

now replace "npcs" to "vertices"

steel snow
#

but if its a static object already in the scene creating a new gameobject would mean i have now got 2 in the scene one relic with no link and a new one that does

#

maybe i should not make Node : Monobehaviour, INode instead just have Node : INode ?

midnight violet
# steel snow yeah but even the non runtime isn't persistant at the moment

Yeah, I can imagine. They will reset to mono default state everytime unless its a public variable or something. So, thats why, store it apart from any scene related stuff. If you setup a waypoint, the code would do
User Clicks to set waypoint => (pass in the transform values, pass in the unit its related to) The system creates a waypoint visually in the scene and also adds a node to the database => Saves the data. From there reloading, you check for the player file/database, recreate the units from savegame and recreate all nodes depending on that unit.

steel snow
#

do i have to create the graph but not have those gameobjects in the scene than on play it adds them?

#

thats kind've odd

midnight violet
tiny pewter
#

gameobject is just the view of your model

midnight violet
#

You can still write your own level editor and when you create a gameobject and add the monobehaviour RuntimeNode for example to it, it will trigger your nodemanager to add it tot he database and save it.

steel snow
#

imagine this simple scene. right now graph holds a reference to these 3 Node classes and the connections ignore the little blue circle. if i save just raw data great, but now i load the raw data those 3 nodes need that raw data assigned back to them. thats why i was using reference but reference as mentioned wont persist if i close unity

midnight violet
#

As we said in many different ways πŸ˜„ Do not hold the DATA inside your GAMEOBJECT. The gameobject is just a placeholder for your data.

steel snow
#

so should i have something like NodeObj : Mono

and in that have a Node : INode struct lets say which holds the data?

#

i dont understand how to link them

midnight violet
#

you should have a database/json/scriptableopbject or whatever that holds the data for all nodes. You define, what a Node is, what values does it have.Vector3 for position, Node inComing and Node outgoing nodes? Whatever you prefer

steel snow
#

right now how in that image above would the game object of node 0 be linked the data in scriptable object ?

#

when i deserialize

timber flame
#

How to avoid from colliding nav mesh agent with each other? When I reduce their radius to zero (close to zero), they are fluctuated

midnight violet
#

simply said like

public List<WaypointPath> waypointPaths;
public class WaypointPath
{
  public List<Node> nodes;

  public void AddWaypointNode(Node node)
  {
    nodes.Add(node);
    node.incoming = nodes[nodes.Count -1];
    SaveToSomeFileOrwhatNot();
  }
}

public class Node
{
  public Vector3 position;
  public Node incoming;
  public Node outgoing;
}

and then you could just serialise that whole thing to a file. And when you want to create a new node, you just trigger the addwaypointnode from your scene when you create a gameobject with a specific RunTimeNode class. The rest of how you handle input of the user is another story

#

This is written in discord, so please dont take this code 1:1 πŸ˜„

steel snow
#

im not seeing how this would then tie to a pre-existing object in the scene so the object can update its visuals based on the waypoint data

midnight violet
#

jesus πŸ˜„ YOu are really stuck to having that premade scene stuff tied into the database

steel snow
#

well yeah all the data is in one graph

midnight violet
#

the graph is your scene?

tiny pewter
#
public class Node{
  public Vector3 position;
  public Node incoming;
  public Node outgoing;
  public NodeObject nodeObject;
}

public class NodeObject:Monobehaviour{
  public Node nodeData;
}
#

now the node know which gameobject it is assigned to

midnight violet
#

You gotta let go the idea, that you are doing the node creation ion the scene. You just creating visual representations of the nodes in the scene, but the values for them are stored in a dataset

regal olive
#

Eating milo powder taste goodπŸ‘

steel snow
#

ill first seperate node from monobehaviour inheritance

#

maybe that will highlight in my mind how i can then move forward

midnight violet
steel snow
#

okay will do

#

thanks !

midnight violet
#

that should clear your head if you do not get into your current code while trying out. Just to get the idea and then figure out, if it works for you and how you can adapt it to your current code πŸ™‚

steel snow
#

i might have to ping you tomorrow or something if i still get stuck πŸ˜„

midnight violet
jovial oriole
#

Is there a way to write a script that looks at the terrain layer and changes the layer... i.e. grass every where and a dirt road. I want the dirt road to be on a new layer called walkable

untold moth
jovial oriole
#

circled

untold moth
jovial oriole
#

That's what I figured.. I just thought there might be a way to script something that would separate the 2...

untold moth
#

Why do you need the road to be on a separate layer?

jovial oriole
#

i want to make the road walkable

untold moth
jovial oriole
#

I want it to be the only walkable area

#

I put together this but not sure `public class TerrainTextureDetector : MonoBehaviour
{
public Terrain terrain;
private TerrainData terrainData;
private Vector3 terrainPos;

void Start()
{
    // Get the terrain data
    terrainData = terrain.terrainData;
}

void Update()
{
    // Convert player position to terrain coordinate system
    terrainPos = transform.position - terrain.transform.position;
    Vector3 mapPosition = new Vector3
    (
        terrainPos.x / terrainData.size.x,
        0,
        terrainPos.z / terrainData.size.z
    );

    // Get the texture mix at the player's position
    float[,,] alphaMap = terrainData.GetAlphas
    (
        (int)(mapPosition.x * terrainData.alphamapWidth),
        (int)(mapPosition.z * terrainData.alphamapHeight),
        1, 1, 0, terrainData.alphamapLayers
    );

    // AlphaMap to determine the dominant texture?
    // Main texture here?
}

}`

#

but that was something for when i was working on a survival game walking on grass vs dirt to change the sound

untold moth
jovial oriole
#

I was trying that, but navmesh, navmesh surface, is new to me, so I was trying to break it into something I knew... basically I'm trying to create a TD game, I want the walkable area to be the dirt and not grass... in the past I used cubes that I sliced down to 0.1 and created a grid... trying to not do the grid thing

untold moth
jovial oriole
#

enemy start
follows path
when given more than one path determine the path of least distance
determine path with least possible damage based on towers on screen
change course if tower upgraded that changes the math of best course
continue path
follow path to end

midnight violet
#

You could compare your position on your worldgrid to the painted texture on the terrain, if I am not completely wrong? Like the painted texture is the "minimap"

#

Probably this could be accessed and depending on black white or whatever there is in the texture, you know if its walkable or not. not sure this is the best practice of restricting the player

untold moth
midnight violet
#

Maybe navmesh could also be used here instead of trying to figure out a path from textures

jovial oriole
#

that's why I am trying to separate the road from the grass so the enemy can only walk on the path, if i separate the path into a new layer called walkable I can set a start and end waypoint for walkable

#

navmesh maybe the best way to go, but i am not very familiar with it yet

midnight violet
#

I would look into this as comparing textures and stuff might not be the most performant way, when calculating a path that can be dynamic with several values considered like towers and what not

#

you could still try to create the walkable paths with some complex code from a texture and bake a navmesh area out of it, but not sure if thats worth it if you could just handcreate simple borders

jovial oriole
#

which channel should i move this question to then... is there a navmesh channel?

midnight violet
#

from pinned messages, that might be the channel for you

jovial oriole
#

this is a simple example of the terrain, the full version will have many more dirt path options

#

I posted in that channel already and got no response so I changed my thought of how to do it

midnight violet
#

I would go to the ai nav channel, ask there. And get some insights first. Then you might struggle with code and can come back here if needed πŸ™‚

#

ye, depending on the topic, it might be to complex or difficult. So it would be your task to split it up in parts that you could ask for

jovial oriole
#

I mean I can create a grid that does what I want, but its not how I want to do it... I want the dirt path to be walkable and the grass area to not be..

midnight violet
#

You might make a list then why you want it or if its just you stuck in the idea for having it πŸ˜‰

jovial oriole
#

lol

#

yeah but where do i post my list?

#

i can see the whole game in my head.. I could draw the game in about 20 minutes,

midnight violet
#

The list of why you want it? Thats just for me to be sure what the benefits are

jovial oriole
#

you gonna be online for a bit?

midnight violet
#

I am hopping on and off as I got time. No guaranteed opening times on my side πŸ˜‰

tall ferry
#

You can bake navmesh areas based on predefined areas. Maybe just create some editor script which detects the change grass/pathway then have it roughly place these areas on the terrain. Bake the navmesh yourself once and done

#

Nothing else really to do unless you completely separate path and grass. This basically means recreate the path and place it on top

tawdry perch
#

I'm making an RPG with races and classes that implement an interface and used in game. Since they are pretty much entirely defined in code, how can I make my game mod friendly so people could program their own races and classes

midnight violet
stuck plinth
tawdry perch
#

Is it possible to load C# scripts from a directory so they could put new ones in there?

stuck plinth
#

no, they need to be compiled into assemblies

#

unless you want to ship a C# compiler in your game!

sage radish
#

Which is actually more doable than it sounds, since Roslyn, the most popular C# compiler, is itself fully written in C#, and can be included in a Unity project as a .dll + dependencies.

tawdry perch
#

That makes sense. How does something like steam workshop work into something like this? I'm pretty new to modding as a concept

stuck plinth
#

obviously, prebuilt assemblies will be faster to load!

upbeat path
upbeat path
misty glade
#

This seems like a dumb question but I have been digging through API/SDK docs for UGS analytics for the better part of 45 minutes now..

How do I set the ApplicationVersion for analytics events?

#

that guy - clientVersion

#

OK, nevermind, it seems like it's pulling from Application Version - in the project prefs dialog.. which I guess makes sense. πŸ€¦β€β™‚οΈ moar coffee

trail spoke
#

is there a way to use bee building system using the cli without opening unity editor ? I need to build to android but unity editor crash

#

I can't use application. Data path outside mono constrictor ( it needs to be called in awake or start methods although sometimes unity allows for that strangely enough like it complains depends on its mode lol) ,

I've a variable needs to be a static therefore I can't have multiple instances of the same type .. but the challenge here is that I need to determine the folder path based on the platform I cant create two static string but the method which I pass the string-s into is static too now .. how I can overcome this?

sly grove
#

You can also use preprocessor directives

median pasture
#

//shooting
if (Input.GetMouseButtonDown(0)) //left-click
{
Instantiate(projectilePrefab, projectilePoint.transform.position,
Quaternion.identity);
anim.SetTrigger("Shoot");
aud.PlayOneShot(shootsound);
} I dont know why but my projectile is always going left instaed of right please help

half swan
gusty kernel
pulsar citrus
#

So I tried to make a backup of my project however it sent it to the recycling bin. I was able to restore my game and the code, but the code isnt working at all

#

Can anyone offer any help?

tall ferry
pulsar citrus
#

Okay thank you. Even when I make new scripts they dont work

#

I dont know if that narrows it down at all

tall ferry
# pulsar citrus I dont know if that narrows it down at all

"Dont work" is about as vague as it gets. Try specifying, probably in the beginner or general channel, about what doesnt exactly work. Right now based on your description all it sounds like is you create a new script and expect it to do something by itself

pulsar citrus
#

So basically as a test, i made a new script with just a public string variable because i would know if the scripts were working i would be able to edit it

#

And assign it a value

#

But not even that pops up

#

The class name is the same and its a mono behavior

pulsar citrus
#

It said it failed to find entry

#

entry-points i mean

untold moth
# pulsar citrus entry-points i mean

You'll need to share the actual error and details on where you see it. A screenshot would do for starters. Because after all the messages, it's still not clear to me what the issue is.

modern jewel
#

ive been trying to come up with a good architecture for a bullet hell combo manager. Essentially I want to have a system where it's easy to tweak which moves a boss uses in what order so I can mix and match (and potentially reuse moves so they can be used by the player or other enemies). But I'm kinda unsure how to abstract this. My plan was to be able to have something like instruction sets, so a list like
[ShootCircle, Wait(2), ShootNova] that I could inject into an enemy and have it perform those on repeat or with some logic of its own too. My problem is that if I make this too abstract, and have it be a list of Skills, it becomes hard to parametrise all skills. E.g.

//Pseudocode
foreach(instruction in instructionlist){
    instruction.execute();
}

Becomes a bit of a problem if an instruction like ShootCircle wants to be able to use the enemy's damage number.

Does anyone know any reading I can do for a system like this, or is the architecture inherently flawed and trying too hard to loosely couple things

#

I suppose one option is to just pass the enemy (or player) script into the instruction and have the instruction retrieve whatever it needs, although for commands like Wait(2seconds) thatd need to be pre parametrised or something

stuck plinth
modern jewel
#

I'm not too obsessed with this being the approach necessarily, and I don't really wanna over engineer. I was just trying to think of how to have fast iterations on enemy behaviour without defining that behaviour on the enemy itself since that to me sounded like i'd require different scripts each time I wanted an enemy to have a different order of moves.

#

There might be a better way of doing that than to express every single possible action as an abstract instruction, I'm not too familiar with gamedev architectures though so kinda unsure in which direction to look for this

stuck plinth
#

i feel like there's quite a high bar here at which any nicely abstracted system is saving you any time vs just throwing a different script on each enemy type and writing out the order in code and/or dropping in a visual scripting graph to do the same thing

modern jewel
#

Yeah most likely

sage radish
# modern jewel ive been trying to come up with a good architecture for a bullet hell combo mana...

A pattern I've used in the past to solve a similar problem to this is to use [SerializeReference] to serialize a list of instructions/actions. You can serialize whatever parameters you need this way, such as:

[Serializable]
public class WaitInstruction : Instruction
{
    public float Duration = 2;

    public override void Execute()
    {
        // wait {Duration} seconds. Execute method probably needs to be a coroutine or async method.
    }
}

You just need a property drawer to be able to select instruction types in the inspector, like:
https://github.com/mackysoft/Unity-SerializeReferenceExtensions
or https://github.com/vertxxyz/Vertx.SerializeReferenceDropdown

#

You could also serialize a reference to the enemy or player, but in my case, I was already using a dependency injection framework in my project, Zenject, so I could also add injectable dependencies to these serializable classes.

fickle tinsel
#

Thanks for the confirmation. Was just looking into this myself. After reading all the options from BuildOptions I found the WaitForPlayerConnection option. Cheers internet person πŸ§€

lavish dune
#

I'm looking for information on some memory stuff in Unity. Let's assume that we have List<Sprite> and List<AudioClip> in a SO in an assetbundle. When you load that SO, does it load all the sprites into memory immediately? The same with AudioClip. AudioClip has Load/Unload Data functions, so I don't know if it loads the compressed stuff into memory before Load/Unload is called or what. I saw no such thing for Sprite or Texture2D, so I'm not too sure about that. The main problem here is audio though, I definitely would not want the whole thing loaded at once.

#

You don't seem to be able to unload individual loaded assets in AssetBundles, so having a good understanding of how they work seems important

#

The documentation also says that if you unload the assets in the assetbundle you can't use it again till reloading the whole bundle which is a rather... spicy choice

#

If I wanted a databank of dialogue voice clips in an asset bundle, I'm not sure what the expected way to handle that would be in regards to not loading all the audio at once

long ivy
lavish dune
#

so what would be the expected way to handle it?

long ivy
#

option 1) carefully avoid creating a dependency graph like that
option 2) lazy way: Resources.Load
option 3) addressables and use indirect references which won't cause those assets to be loaded automatically (ex: AssetReferenceSprite, AssetReferenceT)

lavish dune
#

wouldn't option 3 wind up making individual bundles?

#

also I don't necessarily have access to Resources

#

so that's off the table

#

so am I like expected to make individual bundles per sound file or something?

long ivy
#

? no, put them all in the group and make sure the group is one bundle

lavish dune
#

let's assume this is localization, and this is the Spanish asset bundle, and it has the audio clips for the spanish track in it, but I wouldn't want to load all of it into memory at once

#

so there's not really a great way to group them into smaller bundles and stuff

#

like I'd want to pull one audio clip out, play it, and when the level changes, unload all the audio that was pulled out

#

addressables seem rather overkill for my use case

#

or should be overkill rather, no idea why I can't just unload one file instead of invalidating the entire bundle

long ivy
#

well you only invalidate it if you use the non-destructive unload. What's wrong with loading as needed + relying on Resources.UnloadUnusedAssets to manage ref counts? that should free memory iirc

lavish dune
#

does Resources.UnloadUnusedAssets affect asset bundles?

#

or am I misinterpreting that?

#

the reason I'm interpreting it that was is because it says After calling UnloadAsync on an AssetBundle, you cannot load any more objects from that bundle and other operations on the bundle will throw InvalidOperationException.

#

which admittedly mentions UnloadAsync in Unload for some reason

#

and lists it twice

#

so the documentation is pretty wierd

#

if you can just call Unload on it and then Load after it without InvalidOperationException, that would be fine

#

I haven't gotten around to testing if that's the case

#

trying to get an understanding of intent before I dive into that

long ivy
#

well if you unload a bundle, you won't be able to load objects from it until you load it again. It's setting that unloadAllLoadedObjects param to false that prevents you from loading it again

lavish dune
#

I don't see a way to unload an asset in the bundle?

#

just the whole bundle?

long ivy
#

loading a bundle != loading all objects into memory btw, maybe that's your mistake. It loads a catalog of data

lavish dune
#

yeah I was asking about that. It's not loaded till I load the asset right?

long ivy
#

right

lavish dune
#

and I can't unload individual assets right?

long ivy
#

and then the asset is reference counted and follows the normal refcount rules

#

not specific ones, no

lavish dune
#

wait, the loaded asset gets unloaded if there's no references?

#

because that would be fine

#

I kinda got the impression that once you load the asset, the bundle itself had a reference internally to it (because of what it does with Unload(true)) so it wouldn't free up when I stopped using it

long ivy
#

well you could test that theory out pretty easily. Why is Resources not an option?

lavish dune
#

because the source of the assetbundle isn't in a guaranteed location

#

some would be available through resources but not all of them

tight dome
#

!collab

thorn flintBOT
lavish dune
#

do assetbundles have a watcher or something for it to easily tell what is or isn't ready to be garbage collected?

#

I don't think it's actually that easy to test

#

btw I found this, which says you can't unload them individually, hmm

long ivy
#

sounds like you're stuck with a bunch of bundles then

lavish dune
#

I do think I can work around it though. How fast is loading the catalog? I've never done it before

#

also yeah I'm making a test scene at the moment

lavish dune
#

wow yeah

#

that ain't anything

#

that's with 1GB of audio in small files too

#

thanks a lot for the help evil

#

I think I got a good idea of what to do now

lavish dune
#

did one more test, thought it was funny enough to post

#

load and unload doesn't seem to care too much about how much is actually loaded

#

the above was with Unload(false), the below with Unload(true)

trail spoke
#

how to resolve this there's little to not info on the internet about this

#

TypeLoadException: VTable setup of type unity.SemanticKernel.Connectors.OnnxRuntimeGenAI.OnnxRuntimeGenAIChatCompletionService failed

trail spoke
#

please help , I'm referencing an external dll which cause this issue

upbeat path
trail spoke
#

but do you have any idea why this error occur ?

#

it works fine outside unity

upbeat path
#

At a guess, incompatible .Net versions

#

or a corupt dll

trail spoke
#
Debug.Log(lol.GetType());````

it returns 
```System.RuntimeType```
TypeLoadException: Could not load type 'unity.SemanticKernel.Connectors.OnnxRuntimeGenAI.OnnxRuntimeGenAIChatCompletionService[]' from assembly ''.
upbeat path
trail spoke
trail spoke
shut saffron
#

Hello does ECS supports prefab animations? Like can I create Prefab in Entity and it will be animated in the same was as GameObject ?

upbeat path
trail spoke
#

is obj[] lol allowed

upbeat path
#

yes but why, you already have a defined type for the array

trail spoke
#

I'm off for the day tomorrow gotta check how to load the assembly dynamically at runtime and see if ot could be referenced

upbeat path
#

Dynamic assembly loading is easy. A dll can be loaded as a byte array and a byte array can be converted into an assembly

trail spoke
upbeat path
#

It does not surprise me if you are trying to use lol for anything

trail spoke
#

_lol

#

used lol professionally

upbeat path
#

it's in your code 'object lol' is really Type lol

trail spoke
#

shouldn't be casting of type (object)?

upbeat path
#

of course not, what do you think MakeArrayType() does?

trail spoke
#

No idea but a method that returns an array of something

upbeat path
#

then wtf are you using it?

#

this is code advanced you are supossed to at least know what you are doing

trail spoke
upbeat path
#
typeof(OnnxRuntimeGenAIChatCompletionService).MakeArrayType();

returns a Type
and that type will be

OnnxRuntimeGenAIChatCompletionService[]
misty glade
#

Anyone ever seen this? I have a user with textures that are oddly broken - no idea how to repro or test this. No error messages, just.. broken textures on two UGUI items that I'm using some shaders on. Screenshots of his texture and the expected textures (which I see in editor and my Google Pixel)

sly grove
misty glade
#

Yeah, logistics aside though.. I'm not quite sure where to go from here to test.. Maybe it's something related to some shader on that device that's not supported?

#

I have this massive .shader file but I don't really know how to debug this.. this is HLSL or whatever?

#

I guess it's a bug with this library's shader.. I suppose I'll dig around his asset page and see if there's any infrastructure for reporting/fixing bugs, this is certainly above my head.. I'll see if anyone in #archived-shaders has some ideas on how to proceed/debug this

steel snow
#

i need some people's advice on how to sync my scriptable object to scene objects. so my SO is a graph, i add to it and in the scene i have a graph manager that spawns in gameobjects for the nodes in the graph etc.

the problem comes with deleting the nodes. if i delete the node gameobject in the hierarchy the "on destroy" is called which calls the graph manager so it purges the graph of said node thats fine, but the issue is when i change scene/close the app the "on destroy" is also triggered, so this causes all the nodes to be removed from the graph, then OnAfterSerialize is called because the scene is closing so all the graph data is now gone (and saved an empty graph!). so how do you keep the gameobject in sync with the graph such that if you delete a node game object it will purge it from the scriptable object data and vice versa

tiny pewter
steel snow
#

if i dont use on destroy how else do you clean up the graph data if i delete the gameobject representation

tiny pewter
#

wait why your graph manager requires gameobject to inform it? if the vertex get removed it should update the graph immediately

steel snow
#

the graph manager is the one that links game objects to vertices from the graph object

#

if i delete the game object it needs to report that so graph manager can remove the vertex

#

same goes if i delete the vertex from editor it needs to destroy the game object

#

the manager is the inbetween link

tiny pewter
#

so your graph manager knows the vertex got removed and it can sync the data in disk, no need to use on destroy

steel snow
#

no, if i delete a node game object it doesn't know unless i report to the graph manager first

#

it just feels a bit flimsy the way its all setup

tiny pewter
#

how you remove the gameobject?

steel snow
#

delete it from hierarchy in editor

tiny pewter
#

you can just use the way in the link to distinguish real removal and application quit
i am not familiar with editor scripting

compact ingot
steel snow
#

kinda wish unity had more messages to distinguish these differences

compact ingot
steel snow
#

could pass an enum in the argument which states the origin of the call then

#

thats what i often do in custom editors already to distinguish certain types of edits or deletes

keen ferry
#

whos got a movement system script in unity 3d they can give me pls??

soft moon
keen ferry
#

oh okay ty

dusty wigeon
clear nova
shut hedge
#

If I have a scriptableobject which has many List<ScriptableObject> fields, and I instantiate that. Are the list members also copied, or will they be set to the same instance?

#

(i.e. is it a deep or shallow copy)

sage radish
shut hedge
#

I think they do deep copies of everything thats serializable, except for things that are derived from UnityEngine.Object?

#

but not sure If I understood correctly

misty glade
weary salmon
#

Hi! Not sure if this is really and advanced concept, but I'd really appreciate some help on a concept I want to try out. I'd like to make a bunch of "rooms" for let's say a 3d game of irrelevant genre. I would like to have it so that the next room a player enters is "procedurally generated" in the sense that a script would have a bunch of prebuilt, pre generated rooms at its disposal and pick one of the rooms and plop it at connecting points so that everything connects nice and tidly. I don't however know how to start, or how to provide this script with this set of pre-generated rooms. Maybe I just haven't done my research but I don't know how to describe this concept aptly enough to find any info online.

Any help is appreciated. Cheers!

upbeat path
weary salmon
#

That was a stupid question. Thanks for the help though

sage radish
past talon
#

Help with ScriptableObjects. How do you use them for multiple objects, RTS units for example. Just for one type of unit, should you make multiple instances of one SO to use unit stats on multiple number of this unit? Why can't you just use local variables in prefabs without SO? Perhaps i don't understand how to use them correctly

turbid tinsel
#

But I guess nothing's stopping you from just storing the default stats in the prefabs, it's just that it might become a bit annoying later on

past talon
turbid tinsel
past talon
#

You need to have individual stats for units

turbid tinsel
#

nonono, you're misunderstanding the purpose of SOs then

#

You should store things that don't change (like base max hp, max energy or base movement speed) in an SO, and store changing things (current hp, current energy, amount of speed upgrades) in local data on the gameobject

past talon
#

Ah

turbid tinsel
#

and just link the SO to the gameobject in a script as a variable, and use the unchangeable values from the SO when you need to, for example, set hp to max, or something

past talon
#

Ok, i get it, appreciate it

dusty wigeon
sage solstice
#

Hello I am developing a game and I generate the level and the player at runtime, the enemies spawn from different places, but I want to make the enemies AI to not get stuck on obstocales between them and the player, but I am having issues with navmesh do to generating the prefabs player and enemies at run time, how can I proceed in this, I have seen different videos but didnt quaite made it work.

hollow quiver
#

So I'm taking the advice I was given to make an ICastable interface for all my spells, I'm just not sure where exactly to implement this all properly, so I think my whole structure needs a bit of a retool to get things flowing right. Currently everything works as expected the way it is, now I'm just trying to break it up so the SpellManager has a bit less to do. Here's the breakdown as simply as I can put it without dumping tons of code here:

my Player class searches for the SpellManager spellManager on awake, and used it for things like checking spellManager.IsConcentrating (player cant move if a spell makes them concentrate on it), or activating spellManager.CastPressed()/.CastHeld()/.CastReleased() when it detects the proper gameInput. The SpellManager currently handles the casting from there

my spells are currently made of a few parts. there's an Abstract Scriptable Object class called SpellData, that holds the absolute basics like a spellName, mpCost, whether it requiresConcentration, etc. that's inherited into the Scriptable Object classes like ProjectileSpellData and BarrierSpellData, which holds spell specifics like its projectileSpeed or barrierDuration, things like that.

The SpellManager class essentially holds a dictionary of SpellData scriptable objects called the spellMap (a whole different topic on how im handling spell switching another time), and a reference to the SpellData currentSpellData. then when it gets a CastPressed() or CastHeld() etc from the player, it checks if (currentSpellData is ProjectileSpellData projectileSpell) or if (currentSpellData is BarrierSpellData barrierSpell), starts a TryToCast() method that checks the players mp and cooldown to see if they can cast it, and does the relevant action like FireProjectile() or CreateBarrier()

My current idea is to make a new class for each spell type, so like ProjectileSpell class and BarrierSpell class that both inherit from an ICastable interface that gives the CastPressed() CastHeld() and CastReleased() methods, then having the spell manager call those, but other than the concept of it I'm kind of confused on how to move everything around

humble leaf
#

@versed wave Please don't crosspost

versed wave
#

what does that mean?

humble leaf
#

Posting your question across multiple channels.pick one.

versed wave
#

oh ok

#

any ideas on how to solve the problem?

hollow quiver
# dusty wigeon Move what around ?

Im sorry, I tried to lay out my issue and intention in that post, so I dont know how to answer other than what I already said.

I have some casting methods in a SpellManager that act differently depending on what kind of SpellData scriptable object its being given for parameters at that moment, by checking if that SpellData inherits into ProjectileSpellData, BarrierSpellData, and others. I'm trying to use an ICastable interface to make the SpellManager's part of it easier and cleaner for future things I want to work on by moving those into their own new classes.

Right now I just make a ProjectileSpellData scriptable object, set its name and any parameters it needs, and I pop that directly into the SpellManager's list. If im going to be switching to classes with their own ICastable implementation, then Im just confused on some of the fine details

dusty wigeon
#

If you want to serialize data, you can do:

public class FireballDefinition : SpellDefinition
{
  public class Fireball : Spell 
  {
    public override void Cast(CastContext context);
  }
 
  [SerializeField] private float damage;

  public void Spell Cast(CastContext context)
  {
    FireBall spell = new Fireball();
    spell.Cast(context);
    return spell;
  }
}
#

ICastable is not necessary as long as you can only cast spell.

#

If you ever find yourself in need to cast something else (maybe interaction ?), then, only then, you should create an interface. At the moment, I believe it is better to work with a type.

#

Obviously, it varies from people to people, but from experience a lot of people dislike dealing with interface that are not useful if they are not the one that created it.

#

Hence, I suggest that you incorporate interface only when needed.

regal lava
#

I agree with ICastable can just be the object itself if you only have the Cast method exposed publicly. What I like to do is have interfaces like ICaster on the entity which casts abilities and also include other objects which may modify those abilities, but may not directly be included on the ability object itself.

#

So, if an entity is an ICaster we would know it has mana, it can cast abilities, it has stat related to casting those abilities, and it may have some other utility classes that may modify those casting abilities further.

stoic otter
#

is it possible to check in the fmod api if the event is valid?

deep jasper
#

Can I use Compute shader to define a buffer for DrawMeshInstancedIndirect grass each frame(for frustum culling, LOD and render distance)?

sage radish
gusty matrix
#

Has anybody worked with behaviour trees before? I know there are many different libraries available, but in general, how can I have two leaf/action nodes running in parallel? I want to chase my character and play an animation. The ChaseCharacter-Action has status Running while chasing, how can I also play an animation (probably also Running or returning True)? Any idea?

mint sleet
#

Hello folks, I'm gonna hang myself at dawn because of this ongoing bug. Take a look into the code and save a soul!

   private async Task<string> CheckAuthorizationForTheContent(string[] folders, string fileName)
        {
            string accessURL = /* DataManager.Instance.GetAccessURL();*/
                "https://webapp-240504440.azurewebsites.net/Storage/GetDownloadLink?token=eyJhbGciOiJkaXIiLCJlbmMiOiJBMjU2R0NNIiwiaXNzIjoiaHR0cHM6Ly9kZXYtcHg1Z2M3NGt5bmxrMTVhMy51cy5hdXRoMC5jb20vIn0..010qduiKQfLipG2R.g3C3KemJbM3j8CGMvyvbugKNgRkLswCpPOQSGF9Lkm32cFBAEAkV4-MFsQCkAwHoieZ1zhvl-r0ymxqnbiRdROc-3FfhABfsogMNnFqYcrp3eQcJrfmavxadsfadsfasdfasdfuc2bkVCSoK7-2NNlhQ9zS6Ug89xv9-U-VsmJ7UJRoHj6nbsarMqh8bQB0uyn9G5q8FWjdtMMdv0TQp7yergJnhav7WGMcXC2Vm7vFlZHJneAXQRkRazi4D3FfqhL6AOLs68rygg2Kt2C8HaQ8Nb1WKBktPsjRvCA5JJt9BGZXOjUughWG2eD96Zb325OYOSDkamlfe9cUfzKwfnHKAYLOb4UDG42ZORiLkkBMN7kFPG3rgbGdQhaGn9tJp8FI.i5tYUDFtCqHlD_KTDzvBLQ&blobName=98765bb52c99b2067895e7c3_TheOne%2FStandaloneWindows64%2F00e5d021-0f3a-4ea2-ae20-6db84de3d09b_ramenroyale_08a897ae57b2fb969aa6fe0e178d6b70&bucketName=mealar_production";
            UtilityClass.ParseURL(accessURL, out string baseUrl, out string token, out string blopName, out string bucketName);
            string url = UtilityClass.URL_SCHEMA;
            url = string.Format(url, baseUrl, token, MoveThroughParamsDirectory(folders, fileName), bucketName);

            using (UnityWebRequest www = UnityWebRequest.Get(url))
            {
                await www.SendWebRequest();

                if (www.result == UnityWebRequest.Result.ConnectionError)
                {
                    return null;
                }

                firstTime = false;
                string responseText = www.downloadHandler.text;
                return responseText;
            }
        }```
#

This goddamn code freezes unity after the second request.

#

I'm going crazy!!! There is absolutely none clue, none problem appear!

#

Am I missing something here? Thanks

scenic forge
mint sleet
icy smelt
#

Does Unity releases the memory used by NativeArray to system memory, or the memory will remain available for the process as the Mono managed memory does?

tiny pewter
#

Remain for the process

random dust
#

Perhaps implement a timeout? Still weird that a second request would freeze the application though

mint sleet
#

I did it. timeout gets never hit

random dust
#

So it's before the await?

mint sleet
#

sorry sorry. just I'm confused. yes I put timer and timer never works. the whole app freezes and I have to use task manager to get rid of the corpse of unity

random dust
#

I think it's a good idea to figure out what line specifically freezes though

#

If it's the await itself in this code or before it even

mint sleet
#

await line %100

random dust
#

See if that freezes

mint sleet
#

when I remove await and use it syncron then it works but since it has never catch the promise the returnung value becomes null

#

I'll try it out! thx

random dust
#

The code seems totally valid so perhaps this is some issue with the current client you use

#

There's no reason for it to lock up

stuck plinth
mint sleet
#

yes it's unity 2023 and unity's own.

#

is there a known issue or what?

#

@stuck plinth

stuck plinth
#

not that i know of, just wondering if it was a 3rd party library since a few of those existed before it was officially supported to await those

mint sleet
#

I see.

stuck plinth
# mint sleet I see.

if the unity main thread freezes it's often still possible to pause it in the debugger if the problem is an infinite loop in C# code somewhere, it's probably worth trying that

#

if you're lucky you can even sometimes attach the debugger after it's frozen haha

mint sleet
#

no when it comes to await, the unity freezes and debugger just does nothing

#

not sure there is nothing like might cause to infinite loop

thin mesa
#

make sure to break all so you can actually inspect what is happening on the main thread

mint sleet
#

I'll give it a try asap. Thanks folks. I'll get you updated and get more help in the channel if I'm going to crazy

fickle mountain
#

I have a dynamic weather system in URP. How do I interpolate smoothly between the different Reflection Probe?
It seems to just not be an existing feature anywhere, bar rebuilding a new cubemap yourself every frame, which is hella slow.

regal lava
#

How would that work? Isn't reflection probes just baked images much like baking light maps? Also try #archived-urp

waxen cedar
#

Anyone here a mobile game developer

merry cedar
#

Hey, so I am working on a custom logger. This logs out when I get a log from a script.

I am having issues figuring out how to get unity to select the correct log location, when double clicking in the console, instead of where the custom logger is.

If any knows of a solution I can use I have been scratching my head on this one. Thx.

upbeat path
merry cedar
upbeat path
merry cedar
misty glade
#

Does anyone have some tips for using git lfs successfully with unity? I'm constantly getting shit breaking when unity tries to do something to files at the same time as git lfs during "rehydration" of the pointer files...

#

and it's.. giving me heartburn because I can't tell easily if unity is going to break something accidentally

abstract folio
misty glade
#

i do

#

TBH i'm not even sure why those file in use conflicts are happening.. I just got git lfs online today so I was assuming it was that

abstract folio
#

hmmm.. antivirus perhaps? nah.. that would be an odd coincidence... for it to start right after that

misty glade
#

no antivirus, i live on the edge πŸ΄β€β˜ οΈ

#

but actually - maybe my backup software is trying to do shit in there.. i'll check that

#

yep.

#

πŸ€¦β€β™‚οΈ

#

thx sir. :p

abstract folio
#

hehe, that was ALL you bud πŸ™‚

misty glade
#

nah, I needed someone to think outside the unity box.. antivirus led me to the right answer

#

what a wild 24 hours though.. i had to .. sort of urgently integrate firebase, and they have 2 very large files in the package and it just horribly broke my branch, and fixing it was a nightmare

#

this is such a frustrating gotcha with this particular package (if you're using github)

abstract folio
misty glade
#

if they can be resolved from the packages.json or whatever - but the firebase package isn't in the unity registry so you have to install it as a "custom package" and it has to ride along in the repo if you want your CI/CD pipeline to be able to compile it

abstract folio
#

ah! so the code goes in the asset folder directly? I see

misty glade
#

bits and pieces go everywhere tbh

#

and these guys... these are the naughty ones

quaint dew
#

Aight, ran into an issue where both the GetAction() and the GetTempAction() returns null. I might have overlooked something really simple, but haven't been able to find the issue, but here's the code:

https://hatebin.com/qhialwdtky

The tester.cs

    InputManager.GetInstance().OnLoad += InputManager_OnLoad;

private void InputManager_OnLoad(object sender, InputManager.OnLoadEventArgs e)
{
    inputItem = e.instance.GetTempAction("SpawnItem", "<KeyBoard>/space");
}

private void Update()
{
    if (inputItem.GetTriggered()) //Line 38
    {
firstConveyor.TrySetWorldItem(new WorldItem(item, new Vector2Int(1, 3)));
    }
}
misty glade
#

post Tester.cs

misty glade
#

it's hard to tell what your intent is.. have you stepped through it with the debugger?

abstract folio
#
    {
        inputItem = e.instance.GetTempAction("SpawnItem", "<KeyBoard>/space");
    }```  The, ``e.instance``, seems odd to me.   is ``e`` NOT the instance itself?  Is this a unity class? ( can't find docs for it)
quaint dew
abstract folio
#

reading...

misty glade
#

k - couple things, just from a layout/organization perspective..

You're subscribing to an event of onload from a singleton but not unsubbing - best pattern here would be to do this in enable/disable.

You're getting an action from the instance - but why? why not just let the input manager manage the input and then have things around your game listen for those events?

#

yes, visual studio debugger - if you don't know how to use it .. well, you should, especially for questions in this channel πŸ™‚ someone in gen/beginner can help w/ that

#

i'd restructure your input manager to fire events and then let.. whatever needs to listen to them subscribe to those.. pseudocode:

quaint dew
misty glade
#
public class InputManager
{
  public static event Action InputEvent<string>; // string action
}

public class Tester
{
  private void OnEnable() => InputManager.InputEvent += OnInputEvent;
  private void OnDisable() => InputManager.InputEvent -= OnInputEvent;
  private void OnInputEvent(string action)
  {
    if (action == "jump") DoABarrelRoll();
  }

}
abstract folio
misty glade
#

you don't need to be passing around references to the instance.. that's kinda the whole point of a singleton.. that it just exists at the "global" level

abstract folio
#
    {
        inputItem = InputManager.GetInstance().GetTempAction("SpawnItem", "<KeyBoard>/space");
    }```  <- sanity check , access singleton directly
misty glade
#

it's also just a lot simpler to read and understand.. what you have currently is kind of a mess of chasing around pointers to an instance and.. unsurprisingly, it's hard to figure out what's broken or where your NRE is coming from since the mental workload of this is high (and not necessary)

#

your tester (and I imagine the rest of your game) also has/have a lot of entanglement with the input manager.. like.. needing to know when it's loaded, listening for a certain action in update, etc.. your "consumers" of input should generally be able to do so with a minimum of fuss - just one line to listen to an input event and one line to stop listening (OnEnable/OnDisable above)

#

since you also have race conditions of whether or not the Tester is Started before the InputManager fires OnLoad - in which case your Tester.InputManager_OnLoad() method will never get called, or will get called randomly sometimes and not other times

#

(which is probably your issue here, btw)

#

InputManager.OnLoad fires - but Tester doesn't exist yet.. then Tester gets started and subscribes to input manager's OnLoad but it never "hears" it because it didn't exist when input manager fired it

#

so inputItem on line 38 is null

#

here's a couple screenshots that might help - this is my idiomatic use of singletons and rendering components that need to listen to events

quaint dew
# misty glade ```cs public class InputManager { public static event Action InputEvent<string...

I'll look more into doing it the way you described, but how'd that work with unitys new inputsystem? Wouldn't that require for the "consumer" add in one OnInputEvent function per action they want to listen to? if you did it like that with the string action thingie, wouldnt that make me need to loop over all the actions inside the InputManager each frame and send a event to it? Like I dont see how I could do that since the inputAction.ReadValue<T>() needs to return the value of the action, not just if it happened, due its used in movement where a vector2 is returned, but maybe im just not that used to working with singletons and cant see the path

misty glade
#

put an update loop in your input manager to listen for all inputs

#

and just emit an event with whatever the action/binding is, or whatever you care about

#

I haven't used it extensively since I make mobile games, but .. that's how I'd do it.. your input manager would just listen to all inputs and then emit the string action that you care about

#

and also, yes, essentially one "consumer" for whatever it needs to listen to but that's just one way to do it, depends on the game

#

like if you're a platformer game and you want your player to respond to a bunch of actions like "run right" or "jump" then your player object would just listen to those actions and respond accordingly.. that might not be a great architecture, but it's just one way of doing it

#

for a platformer, another architecture might be to couple input manager and something like "player manager" more closely, so the player manager listens to the input manager for all the inputs, but then emits its own events for rendering components.. like "takes damage" or "starts slide" or "dies" or something

#

then you could have something like a particle effect renderer that flies around near your player and changes emission rate or color or even turns itself on/off by just listening to PlayerManager.HealthChanged events

#

then your player manager doesn't need to know anything about the way the world is rendered.. it's just emits the events based on what happens in gameplay

#

dunno if that makes sense

quaint dew
# misty glade dunno if that makes sense

that makes alot of sense actually, the part i cant really get is how id emit the Data easily without the OnLoad that Gets all the acitons

OnLoad is called once at randomly (when the gameobject for it loads), not when the actuall object is created and setup correctly, so gathering the Inputs later inside the update loop would work just fine with InputManager.GetInstance().GetTempAction("yada", "yada");

I didn't have this problem before I added that the InputItems get stored inside an dictionary, so that I don't create multiple items for one binding

why i added a OnLoad is because before i had the problem that the InputManager class didn't load before the others, but now i might have ran into the exact opposite problem..

Is something like

public void OnInputEvent<T>(string name, T _value)

be possible? Would the "consumer" be able to only subscribe for only float inputs? (The actions themselfes does not store which type they are so i'd still need to send ALL of the Actions and values into it, and then if the name would match i could move on.)

quaint dew
#

Found the issue..... It's so simple,

inputActions = new Dictionary<string, InputItem>();
tempInputActions = new Dictionary<string, InputItem>();

forgot to initialize the Dictionaries...

merry notch
#

how can I tell the compiler to chill out and just trust me on this one

#

like first of all AIController<T> should be able to cast to T considering T is constrained to a type that it already is

#

secondly im checking if its of type T

#

and third just like let me do it anyway then throw a runtime error if it doesn't work

#

(because it will work)

#

I think i got it?

upbeat path
#
T obj = this as T;
merry notch
#
                if(m is T) {
                    currentState.stay((T)m);
                }```
#

oh ok

#

weird

#

ty!

#

whats the difference between (T) and as T

#

that makes that work

upbeat path
#

because as T tries to cast and will return null if it fails

merry notch
#

oh ok

#

tysm

small latch
#

Don't forget you can also do:

if (m is T cast) {
  currentState.stay(cast);
}
upbeat path
#

of, silly me, it cannoy fail

small latch
#

It's the same thing as (T)m yeah

upbeat path
#

scope limited so could be useful

sage solstice
#

Hello I am developing a game and I generate the level and the player at runtime, the enemies spawn from different places, but I want to make the enemies AI not get stuck on obstacles between them and the player, but I am having issues with navmesh due to generating the prefabs player and enemies at run time, how can I proceed in this, I have seen different videos but didnt quite make it work.

untold moth
scenic forge
scenic forge
#

And depends on if currentState/currentState.stay is Unity objects or not, you can use optional chaining and clean up all the null checks.

sage solstice
# untold moth Regenerate the navmesh at runtime.

public class PrefabScript : MonoBehaviour
{
private NavMeshSurface nav;

// Start is called before the first frame update
void Start()
{
    nav = GetComponent<NavMeshSurface>();
    nav.BuildNavMesh();
}

}

I already do

sage solstice
#

even though the prefabs have navmeshsurface and I build the navmesh on Start

#

its my first time working with it and I cant seem to figure this out

untold moth
sage solstice
#

yes 100%, they are generated on runtime and the entire level are those objects, so no objects no level

upbeat path
#

which are you using btw, GitHub NavMeshComponents or com.unity.ai.navigation?

sage solstice
#

com.unity.ai.navigation

upbeat path
# sage solstice

So you are collecting all objects from difference layers using their meshes. I notice your floor has no mesh so it wont be included

merry notch
sage solstice
upbeat path
#

I see no mesh here

scenic forge
sage solstice
#

it has a mesh its just on top

#

had to scroll up

upbeat path
# sage solstice

if you clear the NavMeshData and run your script, does it come back?

upbeat path
#

are you sure your script is running?

#

coz I dont see prefabscript on the inspector either

sage solstice
#

yes it is running

#

I printed inside it and its printing, and on my screenshot is the generated nav which is that shape I dont know why

upbeat path
#

must be your mesh, change the collection to collider

sage solstice
#

its assigning the navmeshdata btw

upbeat path
#

looks like you are generating lots of prefabs.
what I would do is have an empty gameobect with the Navmeshsurface on it. Instantiate the floor prefabs as children of that and then build the navmesh when all done

sage solstice
#

okay I'll try it thanks

upbeat path
#

change the collection to children

#

and remove the surface from the prefab

sage solstice
#

@upbeat path I did, however I dont see any navmesh

sage solstice
fickle tinsel
#

Any advice on developer experience for handling secrets while developing a game server in the Unity editor?

I’m using third party services (AWS gamelift, twilio) and want to populate secret values in my Unity editor while iterating the game server code. In production, the game server obtains these secrets from either command line arguments or environment variables.

While developing in the Unity editor a monobehaviour have serializable props that can be set. This stinks because someone can accidentally version control secret values. Any advice on how to make this better?

upbeat path
upbeat path
fickle tinsel
upbeat path
#

save them there, they are in your registry and cannot escape

sage solstice
upbeat path
sage solstice
fickle tinsel
upbeat path
#

right so you did not change it to run AFTER you instantiate the floor prefabs. It also needs to be on the empty gameobject

upbeat path
upbeat path
fickle tinsel
sage solstice
upbeat path
#

PlayerPrefs are for runtime EditorPrefs are for in the editor

upbeat path
fickle tinsel
sage solstice
upbeat path
upbeat path
fickle tinsel
sage solstice
upbeat path
#

IN A SCRIPT WHICH YOU CAN THROW AWAY AFTER IT HAS RUN

fickle tinsel
#

Whatever dude.

upbeat path
#

I had already said that, twice

stuck plinth
upbeat path
#

no, the point is that it cannot be exposed

#

you do not want to be serializing the values in Unity

sage radish
fickle tinsel
# sage radish Is there anything wrong with using environment variables for this? The only anno...

Thanks for considering my question. Nothing wrong with the solution and something we've considered. The developer experience (devx) is just a little awkward and time consuming.

  1. New envvar needs to be set
  2. Close unity editor, if open
  3. Set new envvars (source into current shell session if need be)
  4. Craft command line args to open unity editor, prepending ENVVARs before unity editor (time consuming)
  5. Unity editor now knows what the latest ENVVAR values are for what my game server uses.

It is time consuming enough to break someone out of their flow, given how long it takes unity to close and then reopen.

#

Most designers would rather stay out of the command line, if you know what I mean πŸ˜…

upbeat path
#

you know you could just keep a text or json file in persistentdataPath, that will keep it well away from Git

fickle tinsel
# upbeat path you know you could just keep a text or json file in persistentdataPath, that wil...

A variation of this is something I'm entertaining. Solution: write a script that looks for .env in the project (AssetDB) to set the envvars. It monitors the file for changes and resets the envvars.

  1. Add .env to .gitignore
  2. Add file, set secrets (or share the file)
  3. When anything changes (aws gamelift fleetid is the thing changing the most), just edit that file
  4. Monitoring editor script sets the envvar for the unity editor session (stored in app's memory, not in anything serialized)
upbeat path
#

until someone blits their git ignore then you are screwed

sage radish
fickle tinsel
upbeat path
#

I would value security over experience any day

fickle tinsel
upbeat path
#

I mean if you are going to go the gitignore route, why not just hard code the values into a sript in the project and ignore that

upbeat path
fickle tinsel
# upbeat path I mean if you are going to go the gitignore route, why not just hard code the va...

Code scares designers more than config files like .env, if that makes any sense. I like @sage radish 's solution a bit more.

If you like the experience of serialized fields, but dislike the possibility of it getting tracked by VC, you can create a custom editor that uses PlayerPrefs/EditorPrefs/temp file to save and load the secrets instead of serializing it in the project.

Staying in unity editor is a better devx

fickle tinsel
upbeat path
sage solstice
upbeat path
sage solstice
upbeat path
fickle tinsel
# upbeat path That's not a bad solution, best of both worlds, can't think of a downside offhan...

Agree. Just so I have it all spelled out explicitly -- Solution:

  1. Create/Update new editor tool (editor window probably) to allow game devs/designers to set secret values (from gamelift/twilio). Since these secret values are not stored in a serializable field, no risk of accidental secret leaking.
  2. Upon secret value entry completed the editor tool will write the value an envvar so as to not have to write handling code. Option to persist in editorprefs to avoid re-entering secret values on unity start up.
  3. On unity editor player run the scripts will read from envvar in appropriate Awake/Start MB methods.

@sage radish anything else to add?

upbeat path
# sage solstice thank you!
    public void MakeWalkways()
    {
        for (int x = 0; x < 5; x++)
            for (int y = 0; y < 5; y++)
                for (int z = 0; z < 5; z++)
                {
                    if (Data.shape[x, y, z] == 0) continue;

                    Vector3 pos = new Vector3(x - 2f, y - 2.5f, z - 2f);
                    GameObject go = Instantiate(quad, pos, quad.transform.rotation, walkways);
                }
        surface.BuildNavMesh();
        agent = Instantiate(npc, npc.transform.position, Quaternion.identity);
        //agent.SetDestination(Vector3.zero);
    }
#

The Surface is on the Walkways game object
The colliders are on the Plane (2) gameobjects

sage radish
fickle tinsel
# sage radish Do you ever see a scenario where a designer won't check the "persist" checkbox? ...

Do you ever see a scenario where a designer won't check the "persist" checkbox?
I think a designer would expect to enter in secret values once and then be able to use the same secret values until they enter new ones, even when closing and reopening the unity editor.
I hadn't considered making it optional.
I just meant the MVP of the editor tool doesn't need to have the feature of persisting between unity editor restarts. Though it's actually very important to have that feature.
Do you see that as a security measure?
Need to read more about editor prefs to know for sure. I would may be concerned if by setting editor prefs, all unity projects could read the values. In that case we may consider other persistence mechanisms (like writing to a gitignored file).

upbeat path
#

Yeah, editor prefs can be read by ALL projects. PlayerPrefs only by the one project

#

Another thought, as you are using AWS already could you not use a S3 bucket as a password manager and that way the devs don't have to do anything

sage solstice
upbeat path
sage solstice
upbeat path
#

because it will always leave an edge the width of the radius of the agent

sage solstice
#

So what can I do? Upscale everything?

upbeat path
#

I'm not sure what you are trying to achieve

sage solstice
#

I want the small size cube to have a navmesh

upbeat path
#

ok, for very small meshes, look at my surface, see how I changed the Tile size and the Region area. Im my mesh the walkable area is only 0.2 units wide

sage solstice
#

I got it

upbeat path
#

perfect

sage solstice
#

thanks for everything

upbeat path
#

np, glad we got there

#

you might want to change the agent step and jump height if you dont want him walking on top of the walls

elder pagoda
#
    void OnDestroy() {
        if (loadout != null) loadout.OnSetHitEffectsChanged -= OnSetHitEffectsChanged;
        if (controller != null) controller.cust.OnPrimaryLoadoutIndexChanged -= UpdateUsage;
        if (controller != null) controller.cust.OnSecondaryLoadoutIndexChanged -= UpdateUsage;
        addEffectButton.onValueChanged.RemoveAllListeners();
        buttPrim.onClick.RemoveAllListeners();
        buttSecnd.onClick.RemoveAllListeners();        
    }

guys I've been doing clean up like this with everything, is this redundant? do I get memory leak if I dont?

sly grove
#

this is good and correct

elder pagoda
#

and very tedious cz_very_sad thankyou tho

bleak citrus
#

It would be nice to have some way to automate that

scenic forge
#

My reactivity system does that, and it's quite trivial to do any kind of "automatically clean up all the listeners"

#

This goes back to that reactivity system is essentially just a thin abstraction on top of the basic event handler, except every event subscription goes through Signal.Subscribe so you essentially have a central place to hook into event subscriptions.

#

The implementation is extremely simple: you have a global variable as the current context, where it's just a list of unsubscribe actions:

abstract class MyMonoBehavior : MonoBehavior
{
  private List<Action> _unsubscribes = new();

  protected abstract void Setup();

  private void Start()
  {
    GlobalContext.Unsubscribes = _unsubscribes;
    Setup();
    GlobalContext.Unsubscribes = null;
  }
}

Now in Signal.Subscribe, you simple check the global context and add unsubscribe to it:

GlobalContext.Unsubscribes?.Add(() => ...);

Now you can just call all the unsubscribes in OnDestroy:

private void OnDestroy()
{
  foreach (var unsubscribe in unsubscribes)
  {
    unsubscribe();
  }
}

(The actual implementation is slightly more complex but not by much, the basic idea is the same)

#

Boom, you now have a MB that automatically unsubscribe all the listeners when it gets destroyed:

class Foo : MyMonoBehavior
{
  protected override void Setup()
  {
    Player.Hp.Subscribe(value => Debug.Log($"Player Hp changed to {value}"));
    Player.Level.Subscribe(...);
    // ...
  }
}

You can subscribe to as many things as you want in Setup without having to worry about forgetting to unsubscribe a listener and causing it to keep triggering after destroyed and causing memory leaks, no need to manually keep you subscriptions and unsubscriptions always in sync during code changes and refactoring, everything is automatically cleaned up and unsubscribed for you.

#

A reactivity system solves so many state management problems that I feel like it's really under utilized, but I do get the reasons why that is, because it's not how most people write code. Most people write procedural code where you explicitly give step by step instructions to the computer by saying "when destroy, unsubscribe this," and if you forget you get a memory leak on your hand that is potentially difficult to even detect.

timber flame
#

I have a problem with nav mesh builder.

At the beginning of my game, I create some buildings and then build/update nav mesh. It is OK most of the time but rarely, it cannot bake it and apply changes.
The buildings have nav mesh modifier and box collider. I use nav mesh plus package


  foreach (var structureLocation in _initialStructureLocations)
            {
                _structureSpawner.Spawn
                (
                    structureLocation.Definition,
                    structureLocation.Location.position,
                    isConstructed: true
                );
            }

            await UniTask.Yield();
            
            _navMeshBuilder.BuildNavMesh();

When spawning new buildings, it is completely OK and update nav mesh

  [Button]
        public void BuildNavMesh()
        {
            _navMeshSurface.BuildNavMesh();
        }

        [Button]
        public void UpdateNavMesh()
        {
            _navMeshSurface.UpdateNavMesh(_navMeshSurface.navMeshData);
        }
hollow quiver
# dusty wigeon No idea what is your issue. Why can't you just do something like: ```cs public a...

So it's been a busy few days, but in the meantime I've managed to redo my SpellManager much better! I took what you said and went with the abstract over the interface, a simple Spell abstract that's passing overridable CastPressed()/CastReleased(), as well as the functions all spells would share like checking mp cost and cooldowns, so they're being handled there and I don't have to worry about it in my actual Spell classes! Thanks for the advice!

charred thunder
# scenic forge A reactivity system solves so many state management problems that I feel like it...

Is the idea of reactivity system some general programming concept? As i search for it, there are only some vue related things comming up.
Do you mind elaborating on it a bit further or send me some other information about this, or some actual implementation, as i'm interested in the the thing you're trying to solve here. I've seen some other implementations for a more specific use case like unity events in an talk about SO for example, that kinda go a similar direction.
But i can't see how your pseudo code here would make any sense, and even if it did, why the indirection over this global thing here?

scenic forge
#

What I've written above is a bit of an extension of the previous write up, it makes more sense once you understand why the layer of Signal abstraction exists over just using events directly (specifically for the use case of automatic clean up, it allows a global point to hook into any event subscription)

tall ferry
scenic forge
tall ferry
scenic forge
#

Yeah I definitely would not recommend ripping out what you already have, let what works continue to work.

#

It's just a different style of programming (reactive vs procedural) that is specifically very good at dealing with state management, so it's worth exploring in a toy project or something.

upbeat path
wooden prairie
#

thx

charred thunder
slow jay
#

I'm creating a music game where the player is moving inside a tunnel and can create twists and turns using WASD. The movement is completely free form and currently it's very basic:

  • If the player presses, for example D, then transform the tunnel to the right by some constant speed.

I'm looking for advice on how to implement better movement in the game. Something that is smoother and more dynamic, it should feel really great when combined with the music. It should feel like the player is moving in sync with the music. e.g maybe at some parts of the song, the movement is really fast, and in others slower.

#

one thing on my mind is bezier curves, and i'll try that next, but let me know if you guys have any tips!

gusty kernel
solar estuary
#

https://gdl.space/imumasaceg.cs

this is some code I copied from some smart dude, its to make a random 2d tilemap, in line 113 I attampted to make a chance to spawn an enemy on every tile, but the pos is off, I thought it was something to do with my grid size (2.5) so I made the pos multiply by 0.4, but now its more of a mess

sly grove
#

not with magic numbers

solar estuary
trim swan
#

hey guys i am trying to make a 2d game but when i implemented the wall jump the player continuously started flipping can you help me solve it

#

here are the code

dense aspen
#

lemme make a thread

trim swan
#

i dont know much about cooding it would be a great help if you guys can help me

trim swan
#

oh oky thanks

dense aspen
#

rhytm game

slender prairie
#

I have a system design question. I'm making a survival game, the most common class is unsurprisingly Item. There will be many different types of items, probably over 50. The way I envision is that any item can be held, and the player can use and held item on any other item (usually just existing in the world). Not all items are compatible with each other, and a lot of the behavior between most items is going to follow a pattern but a lot of it will also be too unique to have a system, so I will need to hard code the results of a lot of interactions. Additionally, it's bilateral interaction, so using Item A on Item B can be different than using Item B on Item A.
I have a couple ideas on how to implement this but I want to know if anyone has a system they've seen or heard of that would work well for this purpose. Thanks!

regal lava
#

I'd make a table of item combinations, and when you are to Combine(Item item) with another item you would look up the combination in the table.

slender prairie
#

I see. Would each combination refer to a helper function to actually execute the interaction?

sly grove
sly grove
#

I imagine they'd be different, right? Since using water on a campfire is probably different from using a campfire on a bucket of water

slender prairie
#

Yes it would be different 😁

Additionally, it's bilateral interaction, so using Item A on Item B can be different than using Item B on Item A.

sly grove
#

Ok then you 'll want to make like a "key" for this interaction which you can use to look it up. Something like:

public struct InteractionKey {
  public Item A;
  public Item B;

  // implement HashCode and Equals for this
}```
Then you can use a Dictionary to look up the specific interaction with this as a key
regal lava
#

If they aren't the same for each combination you can still key value pair

slender prairie
#

Got it, thanks guys!

regal lava
#

assuming you always receive an item back after combination, then you'd probably want a polymorphic Use() method to handle that

#

for any specific interactions for that item

slender prairie
#

The way I planned was to use items only as containers for information (i.e., tool hp, item type) and all interactions would be managed by an overhead manager script on the server.

regal lava
#

item use rpc* -> manager script -> use

slender prairie
#

Oh oh I see

sly grove
#

My cheeky way would be something like:

public delegate void InteractionHandler(Item a, Item b);

public static void WaterCampfireInteraction(Item a, Item b) {
  WaterItem wi = (WaterItem)a;
  CampfireItem campfire = (CampfireItem)b;

  wi.Consume();
  campfire.Extinguish();
}

Dictionary<InteractionKey, InteractionHandler> itemInteractions = new() {
  { new (ItemType.Water, ItemType.Campfire), WaterCampfireInteraction },
  // ... more interactions
}```
slender prairie
#

Yeah, that seems very robust. I like it.

scenic forge
#

Alternatively:

void Combine(Item first, Item second)
{
    switch ((first, second))
    {
        case (WaterItem a, CampfireItem b): Combine(a, b); break;
        case (CampfireItem a, WaterItem b): Combine(a, b); break;
        // ...
    };
}

void Combine(WaterItem a, CampfireItem b) {}
void Combine(CampfireItem a, WaterItem b) {}
// ...
#

You can easily use multicursor in your IDE to create the switch.

#

It still sucks that you have to keep the two parts in sync, but pragmatically speaking that's a fine tradeoff for how low amount of effort it takes.

slender prairie
sly grove
#

Not sure how it works for pattern matching but normal switch statements get compiled down to jump tables which are basically the same as a dict

scenic forge
#

Dictionary will scale linearly, but realistically it won't matter because you won't have thousands and millions of item types.

scenic forge
#

As for the pros, the major one is that you don't have to keep writing var foo = (Foo)a; var bar = (Bar)b; in every single one of those methods.

slender prairie
raw dew
humble leaf
#

Does it work? πŸ€·β€β™‚οΈ

raw dew
#

yeah perfectly

#

just wanna see any other approach

solar estuary
#

hi yal

inland delta
# raw dew https://paste.ofcode.org/JXe6SRLj9tJfTtctNMg5DF is this a good stamina logic, i...

Those duplicated properties like this one and it makes code hard to read and hard to control the execution flow/maintain:

    [SerializeField]
    private bool _isWalking = false;
    public bool isWalking{
        get{ 
            return _isWalking;
        }
        set{ 
            _isWalking = value;
            animator.SetBool("isWalking", value);
        }
    }

You'll need to change "IsWalking" anyways, just the the animator bool in there and keep the variable cleaner

[field: SerializeField] public bool IsWalking { get; private set; }
raw dew
#

ion get you

plush hare
# raw dew ion get you

You would have probably gotten a simplified response if you asked in the beginner channel. This question doesn't really belong here.

hardy jacinth
#

I need some advice related to programming or architectural pattern for a problem I face.
Essentially, I currently use something I would call a "deferred builder", and I have a problem expressing it in C#.
There are two kinds of objects: managed children and Uber object (modeled by a tree rooted at Uber object). Children don't function without the Uber object, so there is a strong coupling between the two.
My use case is basically this: uber object performs some kind of work and composes a final result, while children define what kind of operations are performed on data/context provided by uber object in a composable way. So children in reality expose "some function of input and context".

Now, I would essentially want to represent some kind of "pipeline" as well as it's requirements.
For example assume I have a root object Root and some objects A, B, C that transform data like so (this is a mental model, not real function definitions):

A: (int) -> (int)
B: (int, string ctxValue) -> Result
C: ((int) -> Result, string ctxValue)   ->   (int) -> Result

A is just a simple child that transforms int into int. indempotent.
B is some operation that transforms int into Result, but also depends on some kind of context value that would be supplied by the Root when the actual calculation is performed. It's context sensitive.
C is some higher level operation, that transforms one data pipeline into another, in this case (int) -> Result function would be transformed into another (int) -> Result function.

I am not proficient in functional programming, but as far as my knowledge goes this has something to do with monadic composition?
So now I have this use case:
Root knows how to compose the A,B,C and would construct a pipeline that essentially evaluates (int) -> Result by doing with C(B∘A) (the dot is a notation for function composition i.e. (B∘A)(x) === B(A(x))).

#

And here lies my problem: How can I express that B∘A is a valid composition, even though B depends on an additional context value that is not yet known, but will be known and supplied by Root when the actual calculation takes place?

#

My current approach is defining a base Requirement class and each function would export both a "function" (wrapper object with apply method) and a mutable Requirement data object, that is "filled in" in the Root and the apply function uses it in it's context.

compact ingot
#

Typically you need a dependency resolver that orders the graph so that all nodes have all their dependencies when triggered

#

Not all graphs are serializable (that’s the technical term for it) and therefore exhibit race conditions

#

You need to design your system such that these contentions are prevented, handled or at least easy to find in debugging.

#

Fundamentals of concurrency might also be informative (the CS theory and archetypical problems behind it)

#

The monad is just one way to evaluate the functions partially such that you can inject the missing bits later

#

It does however not fundamentally solve the issue

#

It’s just one way of thinking about it

#

If you have pure functions and monadic structure you skip many of the common pitfalls of stateful concurrency

#

But those are very limiting

#

effectively you would be constructing something similar to a shader graph

hardy jacinth
compact ingot
#

well, if you have a tree/dag with just one branch or any kind of events, you have concurrency

hardy jacinth
compact ingot
#

Also Check out PD, VVVV and max/msp

#

VVVV, with its language VL in particular is a fully visual/node-based representation of C#

scenic forge
#

That seems awfully lot like currying.

hardy jacinth
hardy jacinth
compact ingot
#

Same thing

#

Less fancy though

#

it’s what many β€˜visual artists’ and VJs use

#

it’s particularly interesting because they deal with the whole desire of having such graphs not be a tree

scenic forge
#

If you just curry your parameters:

A: int -> int
B: int -> ctx -> result

Then you can simply compose them into B (A(input)) (ctx).

#

B (A(input)) becomes ctx -> result.

compact ingot
#

and thus the monad rises

#

that functional approach will get terribly ugly when that structure is supposed to do anything to the outside world

scenic forge
#

I'm not sure that has anything to do with monad, but I'm also not familiar enough with functional programming to really talk about it.

#

I'm just commenting on that what they initially talk about is pretty much exactly currying.

hardy jacinth
#

Currying could be helpful, that's true, but it's also true that it can become pretty ugly and hard to work with later on. I can also imagine C# would make it especially difficult, as all curried functions would require their own flavor of generic method due to the lack of type inference that is present in functional languages. I think there would also be yet another problem in the case of the object C: as far as it's concerned, the "context requirements" for the composition of B∘A should bother it, and it should be able to just "propagate" them outside.

scenic forge
#

Eh, I'm not sure how that factors into each other.

#

Currying is merely the concept of changing Func<T0, T1, TR> into Func<T0, Func<T1, TR>>.

#

Currying:

Func<int, int> Add(int x) => y => x + y;

var addThree = Add(3);
var result = addThree(4);

I guess the more OOP way is to write:

class Adder
{
    private int _x;

    public Adder(int x)
    {
        _x = x;
    }

    public int Add(int y)
    {
        return _x + y;
    }
}

var addThree = new Adder(3);
var result = addThree.Add(4);
#

Granted this is a very dumb example, but I'm merely pointing out that currying is not some giant deep black magic that causes you to completely shift your way of thinking and writing code.

#

(In fact the class Adder way is harder to compose in C#, because C# lacks a way to type constructor so there's no way to pass around classes to construct them)

hardy jacinth
#

ah, yeah, no worries, I am familiar with currying from CS background, I just read a bunch of SO or blog post I can't find for some reason again and their exampel looked pretty verbose, and they as well as people in comments were referencing additional libs specifically for currying, so I just included what they wrote

scenic forge
#

Yeah, not that I would actively use currying in C# either because well, C# is pretty rooted in OOP.

#

If you want a more OOP way of achieving the same thing as in your original example without currying, you would probably write something like:

interface IA
{
    int Run(int foo);
}

interface IB
{
    Result Run(int foo, CtxValue bar);
}

// Optionally implement an interface IC
class C
{
    private IA _a;
    private IB _b:

    // constructor...

    public Result Run(int foo, CtxValue bar)
    {
        return IB.Run(IA.Run(foo), bar);
    }
}
#

Now you have a way to compose A+B into C via new C(new A(), new B()).

hardy jacinth
#

Ah, but you can now see a problem: there is now a strong dependency between C and B, because C inherited what is essentially a part of B's only signature! This is somewhat similar to prop drilling. But I was thinking about a similar approach a while ago, only that CtxValue, now called Environment, would be passed or defined in a closure of all of the children, and it's up to the Root to correctly initialize/pass it Environment.

Some cons of that (depending on implementation): runtime checks (but I guess it either way cannot be done solely on the type level as the "tree" can be dynamic so there is no way to know the type for curried/partially applied function in advance), mutability of the environment (unless it's handled by some clever "EnvironmentBuilder" or "Maybe" kind of type), and possibly a bunch of boilerplate in each child.

scenic forge
#

Yeah which is why currying solves it so nicely, if you have to compose a bunch of stuffs and they all want one thing in common to be passed down, you would simply curry that (ctx -> input -> result) to the front/to the end, so that essentially brings the ctx all the way up to the root.

hardy jacinth
#

yeah, good observation

scenic forge
#

And the OOP way of solving this problem is via dependency injection.

hardy jacinth
#

yeah, zenject? or what is it that is recommended for unity? Never used DI in unity project yet (although DI in that case would be an overkill imo)

stuck plinth
#

DI is just a design pattern really, all those frameworks do is cut down the boilerplate

hardy jacinth
#

yeah, but they also work with unity already, and if I had to do it all over again I would have to know all the quirks (and unity has lots...)

#

serialization, prefab stages, initialization, domain reloads etc are just single examples that make hand-written DI a bit more complicated imo (but again, I didn't use it, I just know that these cases were problematic in other similar situations)

stuck plinth
#

the main feature of DI frameworks is instantiating and looking up dependencies, all the extra stuff in zenject is bells and whistles that i (as a long time zenject user) wouldn't touch with a barge pole πŸ˜„

#

so basically, it's a fancy way to call constructors most of the time

#

in fact, these days i'd usually go with vcontainer instead, since it gets rid of most of the extras

bleak citrus
tired fog
#

Important question, how much garbage creates or how slow is the NativeArray<>.GetSubArray(); method?
Is it shit if i run it multiple times?

tiny pewter
sly grove
bleak citrus
#

well, you're still getting that native memory from somewhere...

#

a persistent allocation is pretty much just a malloc, afaik

#

(unlike a temp allocation, which is taken from a scratchpad allocator that's trivially freed after each frame)

#

but it'll be handled entirely separately from C#'s managed world, yeah

bleak citrus
#

🀦

tired fog
bleak citrus
tired fog
sly grove
#

no

tired fog
#

I can concat two nativearrays in unity, which is weird also because the original data gets modified too

stuck plinth
#

are you importing Linq by accident?

#

if you do array1.Concat(array2) with Linq, you're not modifying either array, you're creating an enumeration of them both

bleak citrus
#

yeah -- which will be an IEnumerable<T> for two NativeArray<T>'s

#

not usable in unmanaged code, but you can certainly do that to iterate over several native arrays in C# if you want to

tired fog
#

So I'm confused

#

Can i pass that into a job and does it create garbage?

stuck plinth
#

no, and yes!

#

if you need to concatenate two arrays for a job, you need to make a new array and copy them into it

tired fog
#

Damm, alright

hardy jacinth
#

can I force unity project/C# compiler to emit errors and respect #nullable enable pragma? I would like to ensure strong nullability...

scenic forge
timber flame
#

How to decelerate nav mesh agents when they approach the destination? Should I code myself or it has been implemented?

timber flame
bleak citrus
#

You also need a stopping distance.

dapper cave
timber flame
#

agent.speed=Lerp (0.2,max_speed,remainig/5f)

slender rivet
#

Is there something I'm missing for adding curves to an animation clip from code? I'm trying to edit/add curves to this menu and while I'm able to see it in the animation tab itself, it's not showing up here on the fbx animation tab. I'm using the AnimationUtility.SetEditorCurve(Clip, bind, FootstepCurve); method from a script to do this.

slender rivet
minor ruin
#

is there anyone that knows about splines, and if i can get a rb to snap to them whilst it moves

humble leaf
#

Last I checked, I don't think the built in spline package has rigidbody snapping. However you can check out the Dreamteck asset, which does.

hardy jacinth
inland delta
#

Never really liked zenject, there is just so many useless things that no one really uses

bleak citrus
#

this one's readme doesn't make my computer run out of memory, so that is promising

fringe root
#

Hey! I'm trying to make an attribute system where they can be applied a modifier and they will keep in a list, calculate the total value of the attribute, emit a signal and i also wanted it to be able to remove that modifier after a delay, but i dont want this to be a monobehaviour. Any way i could use an Async Await for achieving this?

#

got it thanks

regal lava
#

events

#

any reason why you want to async it? Why let your player wait for stats to update when they equip their item.

fringe root
#

no no, i want to remove them if they have a time to be active

#

will come in handy for buffs and stuff

#

btw you can use Task.Delay for it

regal lava
#

oh, so you want a constant effect going on

#

I feel like you'd just want to use coroutines to be accurate as possible

fringe root
#

cant because it isnt a mono behaviour

regal lava
#

make a BuffManager singleton

fringe root
#

no

#

ive solved it already

regal lava
#

;)

#

sometimes all you need is a single update loop manager system

jolly token
#

Wasn’t Unity making Awaitable or something

fringe root
#

for me sometimes all i need is less update loops in random places

fringe root
regal lava
#

oh yeah I heard awaitable is pretty accurate

scenic forge
#

Async/await isn't inherently more or less accurate than coroutines. You can make coroutine power async/await and get exactly the same behavior.

jolly token
#

To be fair Task.Delay can be less accurate since it has no knowledge of game time or time scale

scenic forge
#

Sure but that's not the only way to time things with async/await.

jolly token
#

Yeah it’s not Task’s problem πŸ˜„

scenic forge
#

Yep.

#

Although for this case I don't think async/await is necessary, it seems like simply having an end time property for each stat will suffice, since you are very likely to have to do something in update anyways so just check the end time there.

violet depot
#

What should be the best way to separate a string containing 3 variables:

string s = v1 + v2 + v3;

When v1, v2 and v3 is of unknown size and I dont want to separate them by a character.

tall ferry
#

storing stuff in strings and reading it back is a pretty bad idea though (unless related to saving or other stuff). use a class or struct depending on the use

violet depot
#

string -> bytes

bytes -> string

#

And I dont want to restrict any of the variables to a specific length either, so storing the length as say the first byte isnt really viable either.

tall ferry
#

then its more of a #archived-networking issue but really there are networking frameworks already which can just take a custom class, serialize it for you, then send it over the network. You shouldnt be making your own unless you really know what you're doing.
Anyways this #archived-code-advanced message is still an answer to your initial question.

violet depot
#

Alright, thanks.

sage radish
violet depot
#

But I ended up using the first two bytes to specify my first to variables and then the rest for variable 3.