#archived-dots
1 messages ยท Page 165 of 1
The width restriction that github imposes is... not great
Yeah you could copy/paste it edit elsewhere pasteback, but again, friction
perfect. frictionless workflow achieved.
That'll work for us, doesn't really help contributors though haha
meh who are we kidding. There won' be any contributors ๐คทโโ๏ธ
lol, right? at least its reasonably easy for us to throw stuff on there.
So problem solved I guess hahah
The idea is mainly us updates it. We seem to be the most active DOTS community, and we need it to be friction free for us
Also, it's a point of discussion, especially for common questions. BUT, someone with more experience might know a better way and they can refine it
If we keep at it, it'll become a great resource in a few months
It's already an incredible resource comparatively. Hahhaha.
I'm good at structure and documentation, so took that on. I'm literally 3 days into my first made from hand running ECS system, so I'm not the best person to add content yet
Don't worry Benjamin. I've been programming for 3 months total. I got this.
Oh, haha
I might have some stuff laying around, would have to clean it up tho lol
If even.
BUT! The good news is, if I understand the content you put up there, everyone will. ๐
I've been a developer for... 12+ years now. Unity for 5-6 years. Professional Unity for 2.
But, ECS is a mess, and I really did struggle just because of the doc
unity's docs are less than ideal.
it's more on this is HOW you use stuff. rather than is WHAT this stuff DO and DON'T do.
can someone probe unity into hiring the doc managers from microsoft? their docs are ๐
I've been using Photoshop since I was 12 and I could literally make every asset needed for a video game with my hands tied behind my back (including mad pro audio) EXCEPT for programming. Until now. Soon I will be the perfect indie game dev. Muwahaha.
I can't draw for sh*t
that's why I stay in programming
XD
I do have art sense and music sense, but yep, my current skills humbles me.
I'm only alright at animation but I would make up for that by using mocap and slowing down found footage.
There's always ways... or change the style of your game to fit your weaknesses. Can't animate worth shit? Make the animations super stylized.
the only thing i can do is sing. but no one wants to hear a guy singing acapella while they play their game right?
I do
Yeah when my bro and I were young he got into programming and I got into the content creation side of things, haha. I regret not getting into the programming side of things as well.
I've been using Photoshop since I was 12 and I could literally make every asset needed for a video game with my hands tied behind my back (including mad pro audio) EXCEPT for programming. Until now. Soon I will be the perfect indie game dev. Muwahaha.
@tardy spoke As someone with visual/media experience, it really is empowering. But, my advice is once you get good at both, choose your projects carefully. When you can build nearly anything, the options seem overwhelming
Haha yep, I'm familiar with scope/feature creep. I was actually writing a book on that topic (of having multiple skill sets, not feature creep, haha) as I found throughout my life if you have a wide variety of skills you're never really at a loss for work or anything because you can take advantage of so many opportunities and you provide a lot of value to small companies with the ability to wear lots of hats.
Yah, I actually don't have much trouble with work. I partner with just a few people who come to me as "special teams" to build wacky stuff or solve a problem someone can't in-house
Haha that's pretty cool
I sell specialized microphone clips that I manufacture
๐คทโโ๏ธ
Really? DM me a URL?
you know what's fun? I cant even make a fresh project anymore!
Neat. Also, maybe add a vibration dampening version somewhere, if you're making short runs with a 3D printer
probably internal feature. streamlines bug reports when theres only one category
@violet cosmos yeah, I have entire lists of potential products. Been working at a startup so it's been getting neglected, but I'll probably get back to it with some new products soon.
Waiting on the Formlabs Fuse 1 to be released, haha. I'm either going SLS for manufacturing or I have an injection moulder that I can make moulds for with a 5 axis CNC, but that has significant time investments every time you change your design
I have a form 3 for prototyping things for the SLS when it's released, but I tell you that resin is wild. It's so messy. Gets EVERYWHERE.
I don't think people mind 3D printed, as long as you have a good product with good customer service
I'd outsource the 3D printing to someone nearby, and you handle the design, order, fulfillment, and customer service
With SLS / SLA you can make it look injection moulded with some post processing (tumble, etc). With FDM I have mine modded so they print in a very weird way anyway and people don't associate it with 3D printing.
have you thought of having a different business instead of the one you currently have, where you do things totally differently?
@violet cosmos I might, but that actually kills the margins pretty severely for anything except FDM, and also I have my family doing all the manufacturing lol
@tight blade Yah, I'm hoping to transition from being a technology mercinary building things for clients, to making games for customers
@tight blade yeah i'm always doing stuff. My buddy who's a mortgage broker (I also happen to have my license for ... funsies) just made a startup we sold a couple days ago. The startup facilitated two billion dollars of Canadian mortgages per month. My ownership wasn't that high, but it was definitely worth the 1.5 year time investment.
My issue is being weighed down by owning shit. I want to try to not own anything and just travel around with a laptop. Really the only people who only need one tool for their craft are programmers, and imo the most fun type of programming is game programming, and I have the other skills anyway.
oh sorry, that was a joke about alex selling outsource manufactured products instead of manufacturing them himself. It was just a huge conceptual leap
I'd outsource the 3D printing to someone nearby, and you handle the design, order, fulfillment, and customer service
that bit
Lol, that kiiiills your margins
right yeah, since you already have the capital investment in the manufacturing equipment
Also this one audio plugin that me and a friend of mine made on a whim actually outsells the entirety of the store's physical products. It took one week to make, total. If anyone is good at math and wants to make audio plugins, there's SOOOOO much money to be made there.
https://wilkinsonaudio.com/collections/audio-plugins/products/debleeder
I used to sell speakers and stuff too, but got tired of making them. I built a big CNC machine to make them and then... never made them, haha. I might later when I have more time.
I wanted to create a company that 3D prints speakers with an SLS but you'd need a big machine. I was going to fill them ball bearings which is excellent for speaker imaging... I also wanted to patent a technology that creates acoustic diffusion (hemholtz resonators) that is computer generated to EQ a speaker without the need for any inductors / capacitors or DSP. Since the point of that speaker was it uses only one driver for full range. And one passive resonator.
TOO MANY IDEAS!
Wooo, that's a neat form
I bet there's a ton of excellent things you can do with 3D printed structures and sound forming that isn't possible with existing manufacturing
There definitely is
THAT would be fun for awhile
Let's keep it channel related, please.
Set that up, get the right sound nerds and simulation nerds under one roof, then let it run itself
You could simulate it in DOTS ๐
Yeah, I'm done on that tangent anyway, no worries! Back to DOTS. ๐
Honestly, same. Just got off client calls and back to making my ability system in ECS
I've still got that one wrench in my development of VR not compiling with Entities 0.13, haha. My stuff is all pretty alpha so I'm just going to continue building on desktop and hope that that one fixes itself. Not really sure what to do with that in the meantime, haha.
Entities 0.9 -> 0.13 is a pretty big leap and Entities 0.9 seems to have issues with some of my systems despite it does run on VR build (Oculus Quest).
@tardy spoke I might... buy a clip from you
Haha, great!
Is the main reason to not use strings for lookup in a hashmap performance related, or typo related? I could use ints but then the code isn't very declarative in terms of what it's doing, IE you have store this data in 1 instead of store this data in "playerLocation", which is easier to logically follow.
If I recall correctly to avoid typos in redux you called functions which then outputted strings internally to the rest of the system to avoid the typo issue and so you could follow what was happening, but that solution always seemed a bit odd to me. I could do that because then you at least have the context of the name of the method when you call it, which could be "setPlayerLocation".
Getting the hash of a string is a iteration over all the chars
Alexwilkinson is the DOTS' master.
Yeah, it's definitely more "work" for the system to do, but my NativeContainer will likely only be holding maybe 20 pieces of disparate data
You can check out Animator.StringToHash if you wanna keep strings for authoring and performance during runtime
So... is it worth the layer of abstraction JUST to avoid the typo issue because that probably won't be a lot of cycles anyway
@north bay Yeah, that seems like an interesting solution. Could see that being a good compromise. Seems like there's no free lunch here, really.
I would buy the typo argument more in a team situation
I actually get the type argument, i tried js out a week ago for the first time. I normally do not use strings for any type of lookup. But it used it all the time, maybe just the lack of knowledge in the environment, but i had like 2/3 bugs because i used id instead of Id
Hmm. Yeah but maybe you avoided other bugs because of the context the strings provided while creating the logic, haha ๐
Maybe lol
I guess since I have so few variables to set I could just use ints and write in comments what each one is above the NativeContainer holding the "state". Wouldn't be a big deal.
I wonder if an enum might better suit your needs?
or use a constant that is named the way you want and get autocomplete from your ide
or an enum
But those are hard coded ๐ฆ
Hmm... yeah enum actually seems like a gooder. Avoids the typos.
a string is hard coded as well ๐
and autocomplete... and descriptive name... haha
Well I believe there is no way to do an object with lookup that doesn't involve some hard coding somewhere
lol
also added benefit is you change it in one place instead of each and every place you used the same string
Yeah, this enum thing looks like a winner. I'm not really sure what this actually "is" though, or what the JS equivalent would be. Looks like an object with only keys and no values... haha. Seems to act like that too.
It's PERFECT!
By default, the associated constant values of enum members are of type int
Oh, that's super cool. So it literally just translates the keys into a corresponding int for execution.
๐ awesomeness.
Even cooler is โflagsโ - multiple stored in one int
Now you're just getting crazy.
i think flag enums arent supported in bursted jobs
they are, you just have to test for the flags manually rather than use .HasFlag
it would presumably be very easy for them to support this, I should probably make it a post on the forums - been expecting it to just happen naturally but it has been two years already..
small aside, this from the forums yesterday: In the next coming months we will be able to ship a preview of the first phase of the incremental build pipeline as part of dots. It will give big wins compared to what we have now and will work well for mid-sized projects. This will be an opt-in checkbox in the build config assets. First preview will be focused on DOTS, but we will also bring this functionality to GameObject based projects later on.
So, in GameObjectConversionSystem, do I have access to reference types?
As in... How do I access the GameObject that started that convert process?
public gameObject in the constructors and drag it on might work lol
When you figure out a good way we should toss it on the wiki because I actually don't know
@violet cosmos turns out in some test code I did exactly that. Just made a public reference to the gameObject
@tardy spoke I'm referring to within the GameObjectConversionSystem
ah, yeah, no idea then
So, possibly very likely similar to within a System as well. But the GameObjectConversionSystem runs in a separate "conversion world"
Prime wiki material ๐
I'm experimenting with initializing IComponentData with runtime data, in a declarative way
I have a few ideas though, it can be implemented in a number of ways, but obviously have a preference to use reference types, because it's a broader scope of runtime data
What does your conversion system look like? Do you do something like Entities.ForEach(MyMonoBehaviour mmb) mmb.Convert()? You can obviously do mmb.Convert(mmb.gameObject) so I think I'm likely not quite understanding your situation
I actually want to loop over all entities in the conversion world in this case... Looking at how Entities.WithAll() works.
Then I want to get each IComponent for each Entity and check stuff
oh maybe I misunderstood what you meant by reference types
Sorry, I have a few threads going... Yes, ultimately I'd love to use reference types in the GameObjectConversionSystem (this is a special type)
This is a system in the convert stage, in the Conversion World. it's not on the MonoBehavior, or in a Job declared on the main thread
yea... ok.. you may run into some issues with using the correct entity manager (entityManager vs dstEntityManager) and if you want to access entities/components that are being converted you may need to run your conversion script in the GameObjectAfterConversionGroup
Happy to provide more detail or take a look at pseudo code
Is there a way to mark this NativeContainer explicitly read only?
perhaps like this? Entities.WithReadOnly(state).ForEach(...)
@amber flicker Well, as my first attempt at this... Have any idea how I would select all entities?
Since it's in the Conversion World, I'm not so concerned about performance, they only exist there until conversion is done
EntityQuery entityManager.UniversalQuery can be used for all entities but I probably wouldn't use it for anything except a stand-in
wait that syntax is likely a bit wrong, lemme check
MultiListEnumerator<Entity> GetEntities(Component component); ?
Ahh, shit. Maybe GameObjectConversionSystem only runs in the editor
https://docs.unity3d.com/Packages/com.unity.entities@0.7/manual/ecs_systems.html
"GameObjectConversionSystem -- converts GameObject-based, in-Editor representations of your game to efficient, entity-based, runtime representations. Game conversion systems run in the Unity Editor."
@mint iron Thanks for the shout out ๐ Sorry for the late reaction, busy day
Always up for a dots+networking chat hehe
Ahh, shit. Maybe GameObjectConversionSystem only runs in the editor
@violet cosmos WithConvertToEntityit runs on runtime too, I'm thinking that bullet point is referring to subscenes
Weird, where is the "replace" method on a NativeHashMap ? lol
https://forum.unity.com/threads/nativehashmap-tryreplacevalue.629512/ they say it's in there now :\
Do I have to explicitly .Remove() and then .TryAdd()? Is that intentional?
@coarse turtle OK, I'll keep perusing this path
... now, how to figure out how to process all entities and all components of that entity
What kinds of processing?
My idea looks like this
In part of GameObjectAfterConversionGroup....
foreach Entity
foreach Component in Entity
if Component is IInitialize
((IInitialize)Component).Initialize(Entity, EntityManager)
Then, in Initialize, the Component can retrieve other Components for the data it needs
Then, for any IComponent, I can just add IInitialize, and do the specific initialization code in the struct. It doesn't have boxing issues, and solves a lot of other problems
But, I'm doing this as a proof of concept. I would honestly rather be able to reach out to reference data, such as the GameObject, or Singletons, etc and be able to freely get the data I need later
This is for runtime instantiation of data in the Hybrid workflow, bypassing so much mess and keeping it isolated and generalized
My instinct would be to do an Entities.ForEach(Entity e, ComponentTypeImInitializing myComponent, OtherComponentTypeItNeeds otherComponent) and do the initializations one system per dependency
Yes, one per dependency... And that quickly turns into a bunch of boilerplate
I could also make a MonoBehaviour with Convert, or have a InitializeMeType tag, or write a custom initialize factory, or have an "Initialized = false" on the struct.
All of those have downsides, of extra classes, boilerplate, or having to be processed each frame for something that's needed once
My use case is motion vectors: I need the first run's previous position value to be set, rather than 0,0,0. I could put an if check, or do any of the above... But that's not what we do in the real world, is it? Usually we'd set that value as part of the constructor, but that concept doesn't exist in ECS
Hence... Some Initialization as a framework, that I can maintain, grok, search for, and implement generically on just the components that need it, in a sane and isolated way
Wheres the data coming from that you're replacing 0,0,0 with?
I think tag components are next to free btw since they're on the archetype level, its not like a per-entity bool check per update
In this case, it'll be Translation. I haven't gotten into dependencies yet, I'm still on proof of concept
tag components: Need to have a system for each IComponent type, in some fashion or another. It needs to check each frame if there's any InitializeTag components. It needs to be setup to run before, and remember it's a system per. It then needs to remove the InitializeTag component which causes a chunk move
Yeah I would do Entities.ForEach(Position p, MotionVector mv){mv.previous = p}, I dont htink you'd even need to mess with a tag component since it runs in the conversion world only once by default (?)
Why does MotionVector only run once per? Where does it get the first?
It then needs an if, each time... If MotionVector.IsInitialized
each time, each entity, each frame
That's pointless
There's some data that needs to exist, but doesn't change for the lifetime of the Component too. Another use case
"origin" for example, so we can have an Origin component and DistanceFromOrigin component
Why don't I set these at runtime? I'm using the Hybrid/Prefab workflow, and then that opens up writing a whole set of Editors, Managers, Serialization, instantiation factories....
When really I just need to set a stupid value once, before it's put into the general pool of systems ๐
If you're doing hybrid workflow, I think GameObjectConversionSystem is only going to run the once time during conversion of that scene
Maybe Im wrong of course
I'm still unsure of GameObjectConversionSystem is per Prefab that's instantiated, or if it's editor only. We don't have much docs on that (surprise!) so I need to get this basic test working to try out
Back to... How do I get a list of all Entity in the World hehe
@violet cosmos apologies Iโm only half paying attention but if youโre after something similar to a default constructor how about a method on your ICDs called e.g. Default that returns a struct with your preferred initial values set?
ICD's?
IComponentDataโs
What is "preferred data" when it's often runtime values? If I have arrows, how do I set the preferred data for it's first position?
The Origin example is perfect. Where was the object instantiated?
That wouldnโt work for a default constructor either? Just set it using a system that runs on creation of the entity?
That's what I'm looking into... a generalized GameObjectConversionSystem. But need to figure out how to loop over each (and every) entity in the Creation World
if you want to do it at runtime, I wouldn't do it as part of conversion. If it was me and I had my usual 'SetMotionVectorSystem' I would create an additional 'SetInitialMotionOriginSystem' that used [UpdateBefore(SetMotionVectorSystem)] that required the presence of e.g. a SetOriginTag. In the SetInitial.. system's Update I would set the origin and then use an entity query method to delete the origin tag.. e.g. entityManager.CreateEntityQuery(typeof(SetOriginTag)).RemoveComponent<SetOriginTag>(); (though the query should be cached in oncreate
Again, now I need to make a new System and IComponent for each and every Component that needs to be initialized with runtime data?
That's three files
MyComponent, MyComponentInit, MyComponentInitSystem, and very likely MyComponentSystem. Four
To get a float. From a thing. And set it.
imo if you have a lot of common data, perhaps the ICD should actually have a common name. Use another tag to disambiguate. FloatOrigin and 'SetFloatOriginSystem' for example?
What's "common data" about one Entity/Object's initialization origin?
a float or a float3 for example?
I see what you're saying, but then we're back to what I said before: #archived-dots message
Every component that uses it, every frame, every time... needs to check
huh? I think there's some confusion here
you mean if there was an initialise system it would need to check all the entities every frame?
NativeArray<Entity> GetAllEntities(Allocator allocator = Allocator.Temp); - yessss
if you have a lambda such as Entities.WithAll<InitializeTag>().ForEach(...) it will never run once you remove the InitializeTag from the entities.. so it won't be constantly running
it doesn't have to check if the tag exists on every entity
that's the beauty of archetypes
I covered that above too...
Then it needs to run that query each frame. I still need separate systems for each InitializeTag for each IComponentData (because there's no general interface), and also each Entity that it touches, then needs to have that component removed, which causes a chunk move, so I need to manage that on the main thread
All that, to set a float.
once, in an object's lifetime
Then it needs to run that query each frame is a strange thing to say if you understand how the archetypes work. The removing of the tags is also a single change to one element of an array, no matter how many entities you have. I think by all means try exploring the route you were talking about. I wouldn't approach in that way. My suspicion is after spending some more time with ecs you might not either but at least you'll be learning stuff in the meantime. You can totally use interfaces with ICDs and it works quite well.
I think I understand how archetypes work. So in this case, for each archetype that could be intializable, for a moment there is a new chunk allocated (if there wasn't any before) because the entity has the existing archtype, but a small one or four that have InitializeMe tag components. Then I need to look for those (again, a search). Then, once it's done I need to remove those, and because it's removed it's now a different achetype and needs to be moved to a different chunk. because of that, I need to run this job on the main thread, because it's a structural change
Did I get it correct?
This is kind of a weird thing, but I have yet to find anyone in this ECS world who's like "Oh, yah... Shit, we DID forget to add convenient constructors!" Like that's not useful
Like, imagine C# without a constuctor, or using { Value = value; }, and you have to pass it through a new MyConstructor.cs that is 25 lines of boilerplate
Each and every time
Just because there's ways to hack around something doesn't make those ways correct
there's an array entry for every archetype (each archetype being combination of ICDs let's say for now). Let's say you have 10 chunks full of entities, 4 of those are TagA & TagB (Archetype1), 6 are just TagB (Archetype2). Let's say TagA is our initializeTag. 4 chunks will point to the element in the archetype array that has the description TagA&TagB (A1). Therefore if you know you want to remove TagA from all entities that are of that archetype A1, it's super easy for ECS to go in and modify of A1 to just be TagB - in fact, I think of it as freeing up A1 and assigning A2 to those aforementioned 4 chunks. That's why the entityQuery... methods are so cool - they're practically free. This can cause some chunk shuffling of course but it's pretty well optimised in my every day experience of it.
And because it's chunk shuffling it needs to be run on the main thread, and again doesn't get around that I need to add new systems for each and every type and combination
I give up ๐
OK, let me put it to you this way.... You know how you can use entityManager.AddComponentData(entity, new MyComponent { Value = position.z });
Now, lets imagine even though you set Value = position.z, ECS just threw that away and whatever was the default value for Value in the MyComponent struct was used. Wouldn't you be pissed?
Yes, but you have options to set that Value! Like tags!
err.. 1) it doesn't? and 2) Not really - it's inefficient to add one at a time like that (though arguably could be faster)
No, it's a hypothetical
you'd be confused, why can't I set data when I initialized MyComponent?
But you can! Just make this class in a new file, that's 25 lines long and 98% the same as every other one that's doing this initialization, and use that. For each component. AND! Even better, you get to update this class too when you make initialization changes to MyComponent. Don't worry, it's cool, right?
hehe, sorry for being a jerk but...
This is how I feel when people are like "You don't need runtime initializes because..."
It's ok.. I have no idea what you're talking about ๐
maybe i'm misunderstanding what your core problem is, but if your issue is with initialization, why is SystemStateComponentData not a good fit here? it'd be managed by the same system, give you an indication when something needs to be / is already initialized...
Remember: Hybrid ECS workflow, authoring in editor
Perhaps someone else here will be able to follow and I'm just tired
i think there was a SetValue method
@opaque ledge if there is I don't seem to have it
This is 2 years old but maybe still true?
I think editor authoring -> ECS world populated components is supposed to be pretty straightforeward and automatic for simple things
I'll just do it that way for now. Weird. No replace/set value.
I mean [GenerateAuthoringComponent] does a lot
For something simple like using the translation.position -> first value of a motion vector, it seems like it shouldn't be so hard
@manic aurora Do you have a good example of working with ISystemStateComponentData? The examples I'm seeing, there seems to be some magic going on and I don't understand where. It might be useful....
did you look at the official docs? https://docs.unity3d.com/Packages/com.unity.entities@0.9/manual/system_state_components.html
But I think that's again, creating new systems for each IComponentData
Are you wanting like a way to drag the transform component into a field on the generated author component? And that causes unity to automatically populate from that value?
@toxic mural No, I want to be able to freely initialize IComponentData types that use GenerateAuthoringComponent without a lot of boilerplate, extra classes, writing factories and frameworks, and in a declarative, sane way that is also associated with the IComponentData type
You know, like how we initialize things in pretty much everything else
Lets compare this, which is using the IConvertGameObjectToEntity, which is a separate class to add and maintain.... That needs to get used and doesn't let me correlate IComponentData that is authored or not....
using Unity.Entities;
using UnityEngine;
//This monobehaviour exists soley to initialize the Component
public class PlacementBallisticMotionInit : MonoBehaviour, IConvertGameObjectToEntity
{
public Vector3 InitialImpulse;
public bool UsePhysicsGravity = true;
public float Gravity = -9.8f;
void IConvertGameObjectToEntity.Convert(Entity entity, EntityManager dstManager, GameObjectConversionSystem conversionSystem)
{
dstManager.AddComponentData<PlacementBallisticMotion>(entity,
new PlacementBallisticMotion
{
LastPosition = transform.position,
Impulse = InitialImpulse,
Gravity = Gravity
}
);
}
}
All that boilerplate is now required....
vs....
using Unity.Entities;
using Unity.Mathematics;
using Unity.Transforms;
[GenerateAuthoringComponent]
public struct PlacementBallisticMotion : IComponentData, IInitialize
{
public float3 LastPosition;
public float3 Impulse;
public float Gravity;
public void Initialize(Entity entity, EntityManager manager)
{
LastPosition = manager.GetComponentData<Translation>(entity).Value;
}
}```
Which is more sane? The declarative right in the IComponentData, or spread across two files, and 25 lines of mostly boilerplate?
That's hot
Because I need to separate off into the MonoBehaviour, each and every update to PlacementBallisticMotion needs to then be updated as well, for example if say... I added a new property
Or if I removed one
Yeah I get your point
I think it can be done without any initialization if you design your System right, if you 'in' the LocalToWorld and use that as your last position
So, at this point I'm still stuck on... How do i query all entities, so I can experiment with GameObjectConversionSystem. GameObjectConversionSystem.GetEntities seems to take a specific object reference, not a Type
I already do that, then I need an initialization flag. That I need to check each time that system runs by the component, and it also just takes up space and very likely could be a separate ForEach job if it needs to load in N ComponentData to initialize, and again... every time, every frame needs to be checked
I dont think you would need an initialization tag for that
I don't know how you're doing your ballistics motion system though
gameObject.Translation automatically gets ported over into LocalToWorld during conversion
That "LastPosition" is the crux. It's creating what is essentially a small motion vector using the previous position
Yes, but at it's first state... When the system first runs, what is LastPosition?
The best example is Orgin
Lets say I instantiate something, and it has an Origin component, which never changes the value. Then, you have a DistanceFromOrigin component. But, how do you set that Origin once, and only once
er to be clear, this is a runtime initilization by just slapping a zero value PlacementBallisticMotion on an Entity at some point?
No, it's expecting to be positioned correctly
lets not dissect that example and stick with Origin and DistanceFromOrigin
You can't break it down more simply
Origin.Value is a float3 and never changes. DistanceFromOrigin is pretty obvious what it does.
In the case of origin I would just use LocalToWorld.position or whatever the specific is
When?
I guess that would only work the first frame until you started modifying the position
[GenerateAuthoringComponent]
public struct Origin : IComponentData {
public float3 Value;
}
You never instantiate it in code, it's just part of the Prefab. Once you get into setting it with code, then you have a bunch of other crap to worry about
Is there an opinionated C# formatter for Visual Studio, kinda like how JS has Prettier? There's a formatter, but it doesn't remove blank lines, etc
I'm saying, if the example is strictly this simple, then LocalToWorld serves the same purpose and is calculated for you automatically during conversion, based on the gameObject translation
Then you can't just say "hey, go make self-functioning copies of these prefabs!" you have to say, "Ok, which prefabs get Origin? Now I need to set Origin, and set it good
@violet cosmos 2nd one is way worse (from your previous examples)
@toxic mural Show me a system where DistanceToOrigin will always get the correct value on the first frame, please
you shouldn't have methods inside your components
I use CodeMaid for additional formatting and rules in VS
@zinc plinth It's not evil. It doesn't cause unboxing issues, except in this case only when it's first created to call Initialize. It doesn't cause any additional memory overhead.
On the plus side, it keeps the initialization logic with the same file, like a constructor. It's sane, and with some markup like [RequiresComponentData(typeof(Translate))] could be easily secured. It can also be validated, and tested via unit tests
How are you populating Origin.Value?
There is no origin value
this is ecs, your logic is supposed to be in systems, your data in components
if you're putting logic (this is logic) in components you're misusing it
Or there is no origin component I mean
@toxic mural You're missing the point of hte exercise then. Origin.Value is set once, when the Entity is created to it's world position. DistanceFromOrigin is how far it is away, and DistanceToOriginSystem takes an Entity's Origin, and DistanceFromOrigin to calculate that per frame
So, again... When is Origin.Value set in this case, if Origin is (added to the entity) by GenerateAuthoringComponent
yeah I'll admit mine was a bad interpretation lol
This is my point, there's no nice way to do that. My IInitialize isn't the best, but it's worlds better than tags, flags, separate systems or a littany of IConvertGameObjectToEntity MonoBehaviors
Now, still trying to figure out how to get all the entities in the Conversion World
I guess I could just assume that every entity in this case has Translate, because it's generated from authoring
I mean if you're writing the code inside IInitialize(), it doesn't seem that much worse to make it a system that does the logic and maintains the ecs conventions
I agree its a bummer that it results in another file and another system, but the alternative would be something in-editor that we probably wouldn't be able to see from intellisense
yeah system state component data works here if you want initialization code to ONLY run when there is an uninitialized component(s), but it doesn't get you out of maintaining different initialization logic
GenerateAuthoringComponent structs follow the same rules as MonoBehaviour, separate file with the same name, FYI
Also, you missed the question of the challenge: Where is Origin.pos set, the first time, and only once?
on the prefab
No, it's instantiated at runtime, each of these can be in different positions
That's the challenge here... The Prefab defines component sets, among other things, to be converted into entities. The prefabs are instantiated at runtime
But, there's no clean way to initialize runtime values
What if you put (in the Origin MonoBehaviour Awake()), this.value = GetComponent<Transform.Position>() ? So as soon as the prefab wakes up in the world, its values are set, then when it goes through Conversion, the value is already there
Oh wait GenerateAuthorComponent has no Aware()
Origin isn't a MonoBehaviour, it's a IComponentData with GenerateAuthoringComponent
Too bad we can't inherit from the generated component
yeah, ok, what i guess i didn't realize is that there's like...no meaningful way to interact with the generated authoring component at runtime*
Yeah they don't even put files on disk I believe, lol. It just gets injected into some assembly
@violet cosmos I'm throwing my lot in with you, we "should" be able to perform logic on an ICD before conversion, without having to go whole hog and do it all ourselves like with IConvertGameObject
Something like this would be nice
Still, even then that's too much for most use cases, IMHO
I mean it misses the point that there is still the authoring script in addition to the ICD script, but its less bad than a full Iconvertgameobject with assigning each field and setting AddComponentData
That's still lots of separate files
For something that we've accustomed ourselves should be easy
I have an idea for markup too that's specific to structs that implement IComponentData and have the GenerateAuthoringComponent attribute, but right now just prototyping
I really should be working on my game though
Ha, right.. why make a game when you can make a tool that will make it easier to make a game, if one gets to that point..
I know that all too well.. its worse too when you think "well if modders want to do anything, I should make it super easy for them"
Well, I actually want this really badly too
i made it work with reflection for laughs, if you really hate yourself you can create cached delegates to ameliorate the performance cost of the reflected set calls, then rig up some system on top of it that makes it apply generically
really though i'd go make your case in the api usability thread on the forums, this seems like a pretty basic use case, and i agree it's scuffed
I'm building out a lot of Hybrid ECS stuff in the future, and not being able to initialize is going to either add 100+ different boilerplate MonoBehaviours in my project, or a mess of systems
@manic aurora I did. Everyone is like : "Why? Just use MonoBehaviour/Tags/Systems/etc etc" or "why are you using the editor?"
Those are acceptable solutions for tinker toys. They're not acceptable solutions for large scale projects
mmm yes let me just tell my artists they need to create their prefabs as code so i can initialize them easier
i need to sit and think about this for a minute, but what's wrong with this suggestion exactly?
You can author a prefab, and convert it once, and then instantiate the entity multiple times instead.
Something like this would be nice
It would make it easier for them to do this stuff if the editor was updated to support serializing interfaces and generics :{ ill keep dreaming ๐
@manic aurora Runtime data, like position, current time, some ref data, etc etc. These are things we use all the time
I mean its another .cs file for sure
Maybe they could make the generated author component have some 'partial' functions we could fulfill
I don't mind the markup idea either, but that seems like it limits it to 1:1 rather than allowing complex data to be set on initialization
by 1:1 you mean only working on the one ICD necessareily, and not any others that might be added?
Damn, I'm stuck on some basic BS blocker.... I can't pass a variable that's Type into the T of DstEntityManager.GetComponentData<T>
Seriously, I'm inches from this working
Until you try and use generics in a build ๐
NativeArray<ComponentType> componentTypes = DstEntityManager.GetComponentTypes(entity, Allocator.Temp);
foreach (ComponentType type in componentTypes) {
Type cType = type.GetManagedType();
var component = DstEntityManager.GetComponentData<typeof(cType)>(entity);
}
I can't use cType here. Thoughts?
There are some forum posts about using reflection to create generics on entity manager from a Type I believe
that stuff is beyond me though
This usually works in C#land
ICD's referencing managed components do not fare well in subscenes, by the way... hahah.
oh yeah? what happens
bummer
@mint iron wasn't generic collection serialization added in 2020.1 ?
Well, they get stripped if you unload and reload the scene, I should say
I can verify the component seems to have been stripped right off the entity after the subscene is loaded. Not in the debugger at all
I load them based on proximity though so if you never unload it initially it may be there
mmm would be the first i've heard of it. You can get plugins that let you just have an interface for a serialized member and Editor will filter all possibilities to those that implement it when you drag elements to it or search for matches, its freakin amazing. But, 3rd party.
Hm, I think this is the issue: public T GetComponentData<T>(Entity entity) where T : struct, IComponentData;
Theres a thread about using the 'dynamic' keyword to pass in something to a generic funciton without specifying its type, but I dunno if its safe. Also I guess it wouldn't work if you don't have an instance of T that you're passing in, like GetComponentData vs SetComponentData
I have lots of ways to get the Type, that's not the issue. And in general, this kind of thing works
OK, so now I have two different ways of getting the component types from an Entity, but still stuck on GetComponentData<T>
Hm, have something working, but I need to get around that T issue. The concept works though, in general
I think this bypasses all the threading protections in ECS though hehe
Has anyone used RegisterGenericComponentType?
So, I'm stuck....
I either need to figure out how to cram Type componentType into GetComponentData<T>
Or, I need to register an interface as something that can be queried, using RegisterGenericComponentType
The latter is preferred, but...
I think this person is attempting it with reflection
I'm not exactly sure how to apply that to this...
depends how far down the rabbit hole you want to go
I'm massively close, if I could sort one of the two ways out
I'm starting my sweet blob asset quest system now. I am excite. That'll be a cool one to put on the wiki.
Im not a fan of RegisterGenericComponentType because it was really buggy when i tried using it with BlobAsset
The cleanliness of it is outstanding though...
.ForEach((Entity entity, IInitialize init) =>
{
init.Initialize(entity, DstEntityManager);
}
);
its also barely generic if you have to hardcode it
huh, is that an interface passed into ForEach?
didn't know you could do that!
You can't, not without registering it
oh interesting
But, aside... Here's the thing that is hackily working right now
.ForEach((Entity entity) =>
{
NativeArray<ComponentType> componentTypes = DstEntityManager.GetComponentTypes(entity, Allocator.Temp);
foreach (ComponentType type in componentTypes)
{
Type cType = type.GetManagedType();
Type[] cInterfaces = cType.GetInterfaces(); //You would think a simple is check would work, but nope
foreach (Type intCheck in cInterfaces)
{
if (intCheck.Equals(typeof(IInitialize)))
{
if (type.Equals(typeof(PlacementBallisticMotion)))
{
PlacementBallisticMotion pbm = DstEntityManager.GetComponentData<PlacementBallisticMotion>(entity);
((IInitialize)pbm).Initialize(entity, DstEntityManager);
}
}
}
}
componentTypes.Dispose();
});```
It's a bit verbose, but that's because it's in flux
The trick is: GetComponentData<T> with cType
I'm obviously working around it with that if, but that's not what I want
seems like this would be slow
Right now, yes. Comparitively. But, I could optimize it... But I'm not going down optimization until I can get the core working
But remember, it's only run once, when entities go through conversion from Prefab to World
so you have abunch of IComponentData with Initialize() methods on them?
Planning on it, yes
the RegisterGenericComponentType looks way cooler, is that working?
No
ArgumentException: Unknown Type:`Unity.Entities.IInitialize` All ComponentType must be known at compile time. For generic components, each concrete type must be registered with [RegisterGenericComponentType].
The thing is, this is somewhat tenable to keep experimenting. i need to determine how SubScene entities flow through this, instantiation, and figure out why the first entity is never passing through the system, but reports it did later
I also need to unpack and think through this process a bit more, there's a lot to learn here
I see another point of pointless boilerplate to contend with in the Hybrid mode... Having to add conversionSystem.AddHybridComponent() to everything that doesn't exist in ECS world but Scene world, when that could have just been marked up
I think I really need to get better at Attributes
Isn't ECS open source? Or, am I mistaken?
Yessss...... Thank you Unity for including the tools to crack open that function, as indirect and crappy as it may be.
protected override void OnCreate()
{
base.OnCreate();
DebugEntityManager = new EntityManagerDebug(DstEntityManager);
}
protected override void OnUpdate()
{
Entities
.ForEach((Entity entity) =>
{
NativeArray<ComponentType> componentTypes = DstEntityManager.GetComponentTypes(entity, Allocator.Temp);
foreach (ComponentType type in componentTypes)
{
Type cType = type.GetManagedType();
Type[] cInterfaces = cType.GetInterfaces(); //You would think a simple is check would work, but nope
foreach (Type intCheck in cInterfaces)
{
if (intCheck.Equals(typeof(IInitialize)))
{
object initBoxed = DebugEntityManager.GetComponentBoxed(entity, type);
((IInitialize)initBoxed).Initialize(entity, DstEntityManager);
}
}
}
componentTypes.Dispose();
});
Great, so that buggily works, I need to sort out the timings in the Conversion World and SubScene and stuff, but hey... Now I have something to mostly initializes ICD's without going through tags/monobehaviours and other jank
When I get this workflow sorted out, I think I'll package the tools up on GitHub, and it might be far far different than this
Day 3 of ECS complete. Going to play some VR
Lets imagine a hypothetical bullet hell game, where your unique feature is that there's dozens of different types of enemies that have different bullets and attacks. Some enemy bullets move in straight lines, some zigzag around, others seek towards the player, or maybe explode within a radius of the player, etc etc etc, or even better with ECS in mind, a combination of these things.
@violet cosmos you're InnerScript in the forums right?
My implementation of this, incomplete but I have the idea solidified, is make a bunch of Scriptable Objects pertaining to each behavior.
Convert that into blobassets.
and use those blobassets as a look up table in my i.e. bulletSpawnSystem,
Hey, ๐ is anyone using Dots with Addressables?
I just added the unity.localization package which depends on Addressables and suddenly I'm geting a metric f**kton of MissingMethodException: Default constructor not found for type Unity. - like errors when running builds on Android ๐ค
Missing default ctor on Unity.Physics.Systems.BuildPhysicsWorld
Missing default ctor on Unity.Physics.Systems.EndFramePhysicsSystem
Missing default ctor on Unity.Rendering.UpdatePresentationSystemGroup
et al
(If it matters, I'm on 2019.4.7f1 with addressables 1.7.5, entities 0.11.1-preview.4)
I"m also seeing a Unity : Unable to find _burst_generated in the android adb logcat logs ๐ง
yeah I haven't tried it with addressables yet
Pretty sure I remember reading about @storm ravine using addressables for his dots game
Sidenote: The reason I'm suspecting Addressables to be the culprit is because the first occurence was
MissingMethodException: Default constructor not found for type UnityEngine.ResourceManagement.AsyncOperations.ProviderOperation which lead me to a forum post addressing this issue, which appears to be fixes after calling AddressableAssetSettings.BuildPlayerContent(). Unfortunately above errors didn't go away :/
have you recently updated it ? maybe you should consider deleting Library folder
I tried nuking it already without luck
Burst code should have been in there too, right?
(I went with rm -rf ./Temp ./obj ./Assets/StreamingAssets ./Library)
yeah
i am using localization and addressables with my DOTS project as well, i dont have any problems
Currently trying a build on my master branch, prior to any changes around that :/
i am using localization and addressables with my DOTS project as well, i dont have any problems
@opaque ledge I smell hope ๐
Localization 0.7, Addressables 1.12, Entities 0.13
tho you are in 2019
maybe try to create the same project in 2020.1 ?
Maybe I should update Addressables to 1.12. Unsure why Localization 0.7.1. resolved an old one ๐คท
maybe try to create the same project in 2020.1 ?
@opaque ledge good idea. I'll have to switch for any Entities upgrade anyway.
Is it 2020.1 "stable"-ish? (on the Unity scale that is, haha)
fair ๐
but its not LTS either
thats the one of the thing with preview packages, especially Entities, you always have to upgrade your unity version, otherwise its chaos, you will never know if a problem arises because you are using old version
yeah, I was hoping I could avoid it, but we'll see
I really need to get a proper workstation with a 32+ core ThreadRipper... these full recompiles are killing me at โ20 mins each.
a 6-core isn't cutting it anymore these days...
my pc is 9 years old, whenever i change a code i wait Unity to recompile for 40 seconds-2mins, not entirely exciting waiting for it ๐
I can't even imagine the mayhem for a actually big project. "Good morning Nicolas, this is your first day at work. We turned on your computer 3 days ago and it's still importing assets, ..."
1 month later. HR calls for nicolas.
"Hello nicolas we need to talk about your performance, so far, you're pc has yet to import all your assets"
Ok, master branch (no addressables) still builds. So at least no random shit got fubar here โ๏ธ
This is where you expensive a new machine with a nice nvme drive for faster asset importing ๐
Updating to Addressables 1.13.1 didn't seem to cut it ๐ข
This is the whole package-json diff:
It also updated scriptablebuildpipeline as a dependency. Maybe that's the problem ๐ค
Oh jesus christ.... I got it to work...
So when you have a IPreprocessBuildWithReport where you do
AddressableAssetSettings.CleanPlayerContent();
AddressableAssetSettings.BuildPlayerContent();
will fuck up your build without failing the build pipeline ๐
@opaque ledge how do you call BuildPlayerContent() or do you just do it manually through the UI?
yeah thru UI
i never did fancy stuff with Addressables mind you, only InitAssetAsync, LoadAssetAsync and AssetReference, and thats it ๐
I've never rly used DOTS before but I had an idea to make an update loop inside it for each object to eliminate the overhead of unity's update loop. However I cant get it to work nor am I sure it should even be working with hybrid ECS. please let me know if what I'm trying is gibberish or if it makes sense in some way and can be done. I jotted down the idea, but I wanna know if this is somehow a possibility.```cs
public class UpdateableSystem : ComponentSystem
{
private struct Group
{
public UnityEvent Update;
}
protected override void OnUpdate()
{
Entities.ForEach((ref UnityEvent update) =>
{
update.Invoke();
});
}
}
again, this might be completely wrong. or impossible. But I wanna check if it is and if so how I can make this work ๐ค
The thing is ComponentSystem class is OLD, doesnt do any multithreading, it always runs on main thread, its main purpose is to debug and confuse new people.
you cannot run any reference type(like classes) stuff inside jobs
oh, new system is called "SystemBase"
the tutorial and info I found was from last year, so thats alrdy helpful knowledge
so you mean to say I cannot pass in a function, I need to pass in the data for a function thats in the OnUpdate right?
or at least, I cant pass in a UnityEvent (because its a class)
the Entities.ForEach() internally queries for ICD's
so that system wont run since there's no entity with an ICD UnityEvent attached.
im having a rough time finding what ICD stands for, care to unabbreviate it?
IComponentData, sorry sorry. too used to call it like tht
its alright, just been doing this for an hour and that hadnt clicked for me haha
allow me to explain why I want this system tho:
I have a scene that consists of a large amount of objects that dont interact with each other but can be changed from external MB's (f.e. player).
I have currently a system that delegates the update functions from unity into a list and calls them in a for loop in a single manager for the update.
What I was thinking, is that by using DOTS I could make these update loops, since they are individual per object run in, run on ECS for multithreading.
These update loops consist mainly of tile events that will do something with the player when he stands on them.
@deft stump
additionally, there are 2 overlapping scenes that ned to update. but only the ones that are currently on the renderlayer thats active need to be updated
switching between these 2 render layers, switches the running update loop
So you want to mix in Classic Unity's update and Unity ECS? that's my high level overview of what you're asking
yes, I am trying to get the update unity provides to work in ECS so that it can run via DOTS instead of generating a list of update calls as it does with the monobehaviour approach
since the MB update to my knowledge, generates a list with all the methods that need to be updated and loops over them every frame
If I can get that to use some worker threads in DOTS, I can probably get some serious performance gains. but this is quite theoretical for me
yeah... you can't mix ECS with Monobehaviour and or vice versa.
but there is another approach if you're still gungho on the monobehaviour approach
you can use the job system to make your computations run in a worker thread. and you burst compile that job too.
I assume you are referring to this? https://www.grizzly-machine.com/entries/maximizing-the-benefit-of-c-jobs-using-unitys-new-playerloop-api
I am not saying I have to do it with MB. but since I have little experience with DOTS I didnt think it was a good idea to go full on into it and just leave MB's behind
@deft stump or do you think I should move all my coding to DOTS regardless of experience and start learning it instead of clinging to MB's to make a game?
I was under the impression DOTS was to be used as a subsystem in unity, not a shotgun approach for a full game
That's on you man.
in a github wiki that we're maintaining we made the following checklist
But, we really recommend you only come into DOTS if:
1.) You have a pressing technical blocker and you feel the DOTS stack could solve it
2.) OR - You're willing to wade through the poor or non-existent documentation and out of date examples
3.) OR - You have lots of time on your hands and are willing to get your hands dirty learning the future of Unity
4.) OR - You're crazy enough to release a game with highly experimental preview technology. You mad lad / lass, you.
what I gather from that is that its a little too early to rly get into it?
yes.
however, the job system, along with its complimentary burst compiler is good if you want performance from your mb's
in that case I might need to opt for that instead of ECS for now.
it does sound like it would work for the problem I am facing, without complicating things to an environment I have 0 experience with
Just a side note (this may be obvious already) but re multi-threading you canโt do (almost) anything related to MBs on any thread except main. So trying to get a MBs update to run on another thread would not work for example.
@amber flicker that makes my entire idea obsolete doesnt it?
If I understood your intention correctly, yes.
well, fuck
Itโs partly why thereโs all this fuss around entities and structs
And the job system
the best thing I can do then, is stick with the custom for loop on a custom update function on a single manager calling the MB Update I suppose
I canโt answer that. Only general advice I can give is to work through more examples that use Jobs. That will help you understand both theirs and MBs limitations.
sounds reasonable. I know how they work, but am unfamiliar with what the limitations are. I should look into that. Thx for the advice
Np. Itโs pretty tough atm. Good luck.
I do remember this threading stuff popping up in WPF a while back in some software I was writing.
something about not being able to write to the console IIRC
Pretty sure I remember reading about @storm ravine using addressables for his dots game
@spark glade yes we using addressables for all assets, configs, prefabs etc.
@dense cliff I recommend trying to look at it as an isolated system... If you can make it very isolated from the MonoBehaviour items in your game, then you're going to have an easier time
If it's something tightly integrated with a number of MonoBehaviours and GameObject instances, you're going to have a difficult time
That article you linked is an ideal example of best case ECS. There's a number of homogeneous things (the airplanes) and they can run relatively independently
Also, benchmark ๐
@violet cosmos makes sense, they all do the same thing. but are independant in doing so. my objects need to interact, which complicates the entire thing.
I did find a different way of managing it: I add all the objects into the scene, put them on different render layers and manage the updates in one MB Update call from a list that i populate with data from the different render layers
Yah, it can be tricky. I'd say stick with what you have, and if you want to learn DOTS/ECS, when you see a truly isolated system, try it then
๐
I was kinda trying to force it from the perspective of "its more efficient" which was not the right mindset
With DOTS, one benefit of deferring it is that it's very likely to get an update in a few months, and things will change and hopefully improve another baby step
OK, so correct me if I'm wrong. Isn't ECS open source?
Where do I find the source repository, for it?
source repository is internal, so the source is not open sourced for contributions, but you can find the source code and manipulate/view it in your Library -> PackageCache directory
I think unity auto resolves it if you manipulate it
well, if you want to modify it, just move it out of package cache
^
move it into packages folder and unity will not change it
or somewhere else and put file ref to manifest for the package
I've watched a bunch of talks where the Unity team was like "It's open source and we look forward to working on this in tandem with the community", but... apparently that's not true if there's not a GitHub, issue tracker and way to commit code
open source can mean a ton of things to people
technically the right wording would be that it ships with full source code
Yah, I'll move 0.13 to someplace. Thanks. I need to get into the meat of how Unity has implemented some of the authoring component side of things, and extend it
I was just kind of hoping there was a GitHub and it was maintained like how .netcore is
it has been requested many times
not happening
there are some upm packages on github from unity
like the mathematics, input system, PP, SRPs, ml agents etc but some teams just don't do it for whatever reasons (we'll never hear why)
I'm guessing only reason mathematics is on github is because they didn't think it as big of a deal as Entities
That's really kind of dumb. If MS can do it with something as core and over-arching as .net / .netcore, Unity could do it
Microsoft benefits greatly from people having source access and contributions.
especially DOTS stuff is kinda kept behind the curtains all the time until they ship something new
well, people don't REALLY submit that much to those mentioned git repos Unity has atm
And if you think there's a lot of people using Unity, imagine the MS dev ratio to .netcore user ratio in that ecosystem
Ahh, it's in a subfolder.... npm/packages.unity.com/packages.unity.com. Because if you say it twice it's more real ๐
Oh, no it's not
wtf, where is it?
Weโd open source all of Unity today if we thought we could get away with it and still be in business tomorrow,
I think this is their reasoning why they can't open source it. But this more of an excuse than anything really
For things that are shipped into the packages with full source code, like ECS. Yes, it's just an excuse
But, it sure is hidden
Hm, so really... I can't find it
Library -> PackageCache -> com.unity.entities@some_version
@violet cosmos literally what was said here few comments back, it's in your project folder/library/packagecache
well.. I'm late ๐
Yes, if only that were true. It's seriously not. There's a folder there, but it's just a .cache.json file
there is a cache folder for the downloads too
they've moved it x times now so can't remember the current path out of my head, but it's in the users appdata somewhere
but seriously, it is in the projects library folder
I just searched my whole AppData folder, there's only one named com.unity.entities, and it's empty
that just has the manifest.json
it downloads it to users cache if it's not there already
and then copies it from there to library's packagecache
if you can't find it, you are just looking in the wrong place
Weird, I was under the assumption that most packages were all just referenced from the cache, so it wasn't pointlessly duplicated around
But, that was an assumption I guess
library is basically project specific cache
it has all generated stuff too
I just looked at 2020.2 cache folder.. basically there's two folders here:
C:\Users\ <insert username>\AppData\Local\Unity\cache\npm\packages.unity.com
C:\Users\ <insert username>\AppData\Local\Unity\cache\packages\packages.unity.com
entities package should go to the npm one
open source can mean a ton of things to people
@dull copper it especially means a lot of things to people who want to capitalize or profit from the expectations implied by open source without having to commit to any set of standards or principles
thats when its very flexible
"yeah, you could use a decompiler on our assembly code. we're really passionate about the open source movement."
"yes, you can use alpha versions of our product and submit bug reports. we're super enthusiastic about the way the open source source movement can change the world"
IMO anyone who says their product is open source when its only source available should be condemned to write in powershell only for the rest of their lives.
as it is, technically, a programming language.
imagine coding in C# without intellisense
Question on the native stream thingy public NativeStream(int foreachCount, Allocator allocator) What actually goes into the foreachCount
havent used nativestream yet. I'd be curious to know the answer too
I'm looking for a NativeQueue kind of thing that I can have multiple jobs write into
I tried NativeQueue.AsParallel but that seems to only be for parallel scheduled jobs (so 1 job)
Not quite ECS related, but is it possible to store a NativeContainer in a struct that is used in another NativeContainer which is used in a job?
no
Native Collections are not blittable, so you cant nest them or use them inside struct ICDs
Yeah, right, forgot they're non blittable
I'm kinda sad that we even have such a restriction, too much hand-holding at times
What about storing in a blobAsset
I guess you're intending to write to it though so that probably won't help, haha. Likely the same situation.
I'm just experimenting a bit with a render pipeline for lulz
I wanted to jobify some code for light processing, setup their matricies and such while the main thread is busy with something else
Just experimentation, nothing else
And now that I'm thinking thoroughly into it this seems like a big pain
Awesome. How is the scriptable render pipeline stuff? Is it a bit rough around the edges in terms of documentation, etc, or is it pretty good?
I'll probably want to make a render pipeline down the road that is just a simple vertex colour shader. I looked at some tutorials and it seemed a bit... tricky, haha.
The SRP api is not particularly well documented because of how small it actually is. Studying how URP and HDRP work under the hood is the best way to learn how to write an SRP IMO
Yeah, was going to take a look at URP for sure
Even it is far more complex than I need though
I might be able to strip it down, might be the easiest approach
@fringe sinew If you haven't seen these tutorials yet you may dig.
I already saw them, not too interested in em
I think I'm already quite experienced with the SRP api
But, yeah, what I thought to do was to jobify my code regarding lights setup (like, parameters for rendering, matricies, etc.), but it seems like a pain.
All my necessary stuff must be in native containers
We use this in our tech to "allow" components with strings, lists, maps
Can you share some info?
You use a private field on the ICB which contains a handle, then use a static class which has a lookup from handle -> non blittable instance
Then use properties on the struct to hide the lookup
Very anti ECS, but it works great if you have no other choice
But wouldn't the job system panic the moment it sees us accessing a static class?
Works fine as long as the job isn't using burst
You cant PASS jobs managed types, but you can still use them inside jobs
Just not recommended, and very unsafe
Don't really care about safety. Just want to do some processing on managed non-unity types, that's all
Sounds interesting, gonna research some more
Thanks
public unsafe struct Component : IComponentData
{
internal ReferenceProvider<string>.ReferenceHandle someFieldHandle;
public string SomeField
{
get => someFieldHandle.Get();
set
{
someFieldHandle.Set(value);
}
}
}
Here is an example in some pseudo csharp
You'd have something like ReferenceHandle.Allocate() which instantiates a new string and returns the ReferenceHandle to store on the component for use
The danger here however, is memory leak
make sure you have some method to dispose the instance
@fringe sinew If you can guarentee safety you can nest unsafe native containers.
Those are in Unity.Collections.LowLevel.Unsafe
Let's hypothetically say that I don't care about safety a tiny bit
Oh, I'll check those out, thanks
Oh, I'm a bit curious, why would I need to private/internal a handle in your proposed system? Is it to bypass the job system's safety? @stiff skiff
I thought that it relied on reflection to catch all intent behind passing non-blittable types to jobs
That bit doesnt matter
The example is a stripped down version from something from our codebase
we keep the handle internal so others dont touch it
its internal instead private so that the code instantiating the component has access to write the handle
So the main way that you hide all of it is still in the property
I just thought that maybe the safety system only scanned through the field marked as public, that's all.
Thanks for the clarification
Note that this can have some nasty issues if you don't access this data safely, so be careful there
Thanks a ton
Is DOTS considered production ready and are there any big draw backs to using it over traditional structures?
not yet production ready
it's definitely not production ready
not officially anyway
there's few actual productions using it but most of them use heavily customized stuff
some of the big drawbacks would be:
- you have to build a lot of custom tech yourself
- you have to keep up with dots development as Unity changes direction with these things every now and then (how badly depends on which dots components you look at)
- dots has quite sketchy editor support atm, Unity is only now starting to build better tooling for DOTS
- over half of the planned DOTS ecosystem isn't usable or available yet (animations, audio, input, ui, ai etc, could probably include netcode too in this list but some seem to use it)
- you need hybrid rendering to use dots for rendering and hybrid renderer is all but robust atm
@bronze cairn
Thank you for the wonderful information gentlemen.
if you want an adventure and like the ECS pattern, it's available though
actual entities package isn't all that bad, it's just most of the surrounding things that are lacking (rest of the engine framework support so you are kinda forced to use hybrid workflows atm)
@bronze cairn we're compiling a wiki of info on it from the people in this Discord. https://github.com/DOTS-Discord/Unity-DOTS-Discord/wiki May be helpful to ya, though it's relatively new.
Let's hypothetically say that I don't care about safety a tiny bit
@fringe sinew I have some other examples of unsafe work on the wiki
and bear in mind that in order to use any unsafe code you'll need to enable it as an option in your player settings. If your IDE freaks out at you, thats why.
You mean, the one that alexwilkinson just posted?
But yeah, I'm familiar with how unsafe features work in C#/Unity
I've just been implementing some stuff using jobs in our current project, nothing quite major. Barely worked with it previously and I just got curious with all the hand-holding that Unity provides and if it's possible to circumvent it.
So, can I use SystemStateComponents to detect whenever an ICD of SomeType was added to the World?
So for example, if I have an Entity and use AddComponent, does SystemStateComponent get a call?
dont suppose anyone has had luck using TeamCity with the new build pipeline?
@violet cosmos if you add the systemstatecomponent sure
@hollow sorrel Do you have an example of that?
it doesnt do that "auto" what you do is you create 2 systems, one for handling component add one for component remove
Entities.WithNone<MySystemState>().WithAll<ComponentIAmInterestedIn >()
.ForEach()
This is for component add, if any entity have the component i am interested in but not the system component that means component just has been added (or enitity created with that component you are interested in)
So you run your logic and add MySystemState to that entity
Entities.WithNone<ComponentIAmInterestedIn>().WithAll<MySystemState>().ForEach()
This is for component removed, if my system state is there but not the component i am interested in that means component has been removed and you do your logic in here and remove MySystemState from the entity
One thing to note that if an entity has any SystemStateComponent and it is destroyed, entity with system state component will continue to live so with this way you can also detect if entity is created or destroyed, in order to let Unity be able to recycle the entity you have to remove the system state component
yea basically that, also more info here https://docs.unity3d.com/Packages/com.unity.entities@0.13/manual/system_state_components.html
basically you query the component without statecomponent to see if it was added, then add the statecomponent
Ahh, I think I understand. So, it's almost like a variant of Shared Component, but more for tracking state than a data that's going to be available to all entities
not really like sharedcomponent
more like regular icomponentdata except it still exists after the entity gets deleted
What's a specific use case for it?
so generally you'd use it for stuff that you want to deallocate when you delete the entity but its data needs extra cleanup
Hmm, I think I understand...
So if some Entity is indirectly tied to some things that need to be disposed, I'd be checking that and when the entity is on end of life, I can dispose of that unneeded stuff and then call the entity to be removed?
yeah
Gotcha, that does seem useful, and now I understand it's purpose when the docs say "No callbacks" is an important element of the ECS design rules.
Would be cool to have a simple example of that in the wiki ๐
for example you could have a mesh id component and a statecomponent that checks when it has been created, then fetches a mesh from disk and puts it in cache, and when it gets removed you can remove it from cache depending if it has no other referencse
the only 'actual' difference is that it exists after entity gets deleted, but i like to think of it as a component that isn't really part of the World data
like if you were to serialize your World the systemstatecomponents wouldn't be (dunno if they currently are or not)
more like something that tracks system data, except on the entity instead of on the system
Yah, I'm very much interested in leveraging it
One thing that I'm highly concerned about is entity lifetimes, managing their lifecycle and behaviour, and keeping a very smooth and boilerplate free workflow with that
I think I figured out how to adapt my current hack into be more.... ECS
What's the best way to tag a system to run in Simulation, but before any other components?
updateingroup(simulation, orderfirst = true)
Cool, thanks!
Well, poo.... Back to the GetComponent<T> issue, where I can't use a Type for T
with updateingroup?
Yah, the issue is I'm using a hack to get the component, but while that hack is returning a reference to the component, when I update values in that component it's not doing it correctl
updateingroup should be a compile time thing tho
what's your code
might need to use typeof()
Oh my friend, if it were only that simple
Unity's doing something under the hood, likely in NativeLandia and it's not quite letting me access or set the values in the way I've formed this right now
In theory it works well, but... it's not
its a struct, you have to do SetComponent after changing
Ahhh, yes that's probably it. I'm used to other systems where I can just change values for ref types, but in this case I can't
But, now I'm stuck on T again in that case
Did you look into that thread about using reflection to generate a generic overload when you only have System.Type ?
Do I have to remove a component before using SetComponentData, or does it just automatically overwrite?
Woot, nailed it
Maybe...
I think SetComponentData requires that the component already exist on the entity
you can do AddComponentData as well
and yeah SetComponentData just overwrites it
same goes with AddComponentData, only difference between set and add is set will give you an error if component is not there, while add will simply add or overwrite if exist
Ok, so here's the gist...
Still meets the goals I set out for, even though it does use temporary Tag component... It's not a separate tag and system per ICD type that needs initialized. Implement the interface, set InitializeComponentDataTag on the authoring prefab... and it's done. Nothing more, no boilerplate
Next up, to have an IComponentReferenceInitialize interface, which lets this system access the GameObject it's associated with
If I add in some [RequireAuthoringComponent(typeof(InitializeComponentDataTag))] then you wouldn't even have to remember to set that on the authoring prefab
(which, would be useful in itself)
Also, posting it here to solicit ideas for improvements
maybe i'm missing something but doesn't iconvertgameobject already do the same as your .Initialize()
That only works at editor time
This works at runtime, from pre-converted prefabs
I went down that route first hehe
So lets say I initialize a prefab that has PlacementBallisticMotion on it, positioned at (10,23.2,56.1), then that position gets set and set only once and correctly on PlacementBallisticMotion.LastPosition, automagically. I can then write a generic prefab placement thing, and don't have to worry about digging into the prefab to see what components are there, which need initialized, how to set their values.... such a mess and point of bugs
Once I get the ByReference version of it, which can work in GameObjectLandia... Then can read data from non ECS authored components as well
Yes, but know that I know what SystemStateComponents do, this works better for this particular use case, imho
i think that + reactive systems would be better solution than this tho because now not only you have boxing you're also making gc allocations with that array
That's a question... How do I declare and use that array correctly? When I tried to position it outside the ForEach loop I was getting lots of warnings
(and/or errors)
the nativearray is fine, i mean the Type[]
Hm. You're right. I could restructure that so it's declared outside the loop, then cleaned up after
you can't really clean it up yourself unless you call gc.collect
does it matter? this will always be super slow doing runtime conversion?
yah, it doesn't matter too much. This only runs once per Entity that has InitializeComponentDataTag
isn't that meant for every time you instantiate your prefab tho
depends on your game i guess but i imagine that's fairly common
Yes, every time the prefab gets instantiated this will run
That's the point of runtime instance specific data
ComponentType.GetManagedType() is a delegated call to TypeManager.GetType(TypeIndex) which is just an int lookup
I think a lot of us are choosing to build our own code-gen solutions - I wonder if that would help with your boilerplate issue while keeping decent dots performance?
Yes, I could build code gen as well, and I thought about that route. But... That means for every ICD that needs initialization, how do I do codegen for specific types?
I thought about going down an Attributes route, but that doesn't allow logic
it's true reactive system is more boilerplate than just implementing a method on the icomponentdata, but that basically means your icomponentdata is in charge of manipulating itself
which is something you wanna avoid imo
there's a reason ecs is split into systems + components
I've been begging for someone to show me a better way that doesn't require 1-3 extra files or boilerplate, or two points of code to maintain
Show me how to get LastPosition = manager.GetComponentData<Translation>(entity).Value, and how to set that specific Component type to be flagged to initialize
Without an extra file per type. Without an extra system per type.
'Show me how to have custom behaviour without writing any code'? Yea, might be tricky.
Initialization is core to any language and system
what about maybe a static method for your prefab instantiation
so instead of calling instantiate(entity) or however you're doing it now, you'd call prefabfactory.instantiatepoop(entitymanager)
then you wouldn't need a new file per prefab
@hollow sorrel Then I need to dig through each prefab, inspect each component type is in a specific list of components that need runtime data, then set that data. So now the logic is way off in another area
That code would look like:
switch (c) {
case typeof(PlacementBallisticMotion):
//Init logic
What if I want to init it outside that Factory?
Then I need to copy and paste that PlacementBallisticMotion init code
i was thinking more like a method per prefab instead of a method per component, but yea if your ratio is a lot of prefabs use that same component that sucks
I'm planning on making lots of small isolated ICD's and layering them together to dictate the ultimate behavior of an "ability"
This isn't just an isolated system that just throws ballistic projectiles around. I have at least 15 types of movement
and you don't need to worry about e.g. ability 1 shouldn't initialize it's values after ability 2 has?
@amber flicker Likely not, each ability is relatively isolated in it's behaviour by design. If I need that, I'll cross that dependency bridge when I get there
if you have e.g. 15 types of movement, I still don't understand why writing 1 ICD and 1 reactive system that they all share? 'InitialPosition : float3' for example
Do they all need InitialPosition?
have you mapped out what the data required actually is or are you designing for an infinite possibility space?
But again, I need to manage the lifecycle of initial position, that it was set once, and only once
i dunno of a better solution then
i feel like ecs is boilerplate prone because the basic rule is being specific = always faster than being generic and with data oriented you try to design your data around the problem, rather than try to apply something to everything/being as generic as possible
even unity didn't figure a 'real' way around this for the basic component systems, their solution is to codegen the boilerplate but the boilerplate still exists in the background
That means InitialPosition needs an InitialPositionInitializeTag, or a IsSet=false flag
OK, here's a hypothetical....
Lets imagine, hypothetically, Unity 2020.3 removes MonoBehaviour Awake() and Start(). We actually don't need them. We could make another MonoBehaviour that goes through and initializes the other one. It would check a flag and then do the setting
That's where we're at now with runtime instantiated prefabs right now in ECS. There's no Awake() or Start()
There's no sense of "Set this once, based on runtime data" and go about your business
Initialization is a core concept
structs have constructors, even though they're value types
there's OnCreate?..
OnCreate.... a system. Not an instance of a prefab
a prefab is a structure, that defines a set of components and values to be assigned to an entity
What's missing is setting runtime values
Awake() and Start()
that's called an entityAchetype, and you set each field manually in systems
you're trying to bend ecs to your way of thinking but that's not going to be good at all
Again, my Origin challenge
Show me a way to set Origin.Position. Once, and only once. Without having to A: Use flags that need to be checked every frame. B: Make a custom InitializeOriginTag component. C: Write a full fledged structure initialization system that has intimate knowledge Origin is a type to be initialized
how should Origin know to be set by position and not by scale?
That's what Origin.Position is!
Where was I created?
what about a componentsystem that iterates that initializetag and performs a method per entity, then subclass that system and override that method
you'd still have one class per type but you could fit those in one file if you wanted, should be a small piece of code
That's a valid use of data, correct? Origin.Position
you use entity queries, adding a component to a query has no cost whatsoever.....
yes, I know that. But, I need to know this one instance of origin isn't initialized yet. Ok, how?
a fucking tag with a entityquerydesc.None
A tag, specific for Origin though, correct?
So that means Origin needs an OriginNotInitializedTag, and also a separate ForEach that looks for Entities that have both Origin and OriginNotInitialized, correct?
@zinc plinth only concrete types in builds and even then they can be quite finickity
you could just use a .WithNone<InitializedTag> and .With<Origin>
haha @hollow sorrel we've been down this road so many times at this point - he wants them auto-generated with intent
doing conversion at runtime
@zinc plinth yea. you have to use [assembly:typeof(blahblah)] for each specific type
hmm
@hollow sorrel Hmm.... You know I could actually live with that, as an option as well
that's a damn entity query with a tag under the hood, basically what was already said
But, it still is another point of code to maintain, and another point to introduce bugs, but at least that could be collapsed into one file.
The issue here though... It'll need to be a ForEach in a ForEach, because I can't remove the NeedsInitialized tag until all of the Component types that need initialization are processed. But it would be "ECS"
Let me prototype that up quick, it's not too far off the auto-init I wrote
you just remove all intialization tags at end of frame (with a super cheap entityQuery call)
I'd want to remove it immediately after it's initialized. Because if that tag is a tag for state, then if the entity lives a frame with that state tag set, then it's incorrect and could be a point of failure
btw i feel like initializing like this is prob way less common than you think
and if you do you don't need to use a seperate system
you'd just put that entityquery in the same system as whatever does stuff to your Origin or whatever
and often you could prob get away with initializing in the same iteration as your regular query
e.g. you don't usually have to "initialize" a position, you just set it in your movecharactersystem, or set it right after instantiating if it's a static thing from wherever you're instantiating
WithNone<Initializedtag>
if the entity lives a frame with that state tag set, then it's incorrect
but you remove it at the end of the frame
not sure how that's a point of failure
As a bit of background, the past couple years I've been working on a dots tween lib - supporting any monobehaviour or ICD. As you can imagine 'initialization' is pretty important as you have to know where to tween 'from'. In my humble opinion you want to have some reactive system that initializes the values. It sounds like you might be on board now. I use code-gen for various reasons. It's totally a valid option but regardless, in my setup all of the properties have systems that check if their default data needs to be set at runtime. I don't think you can be worried about the performance of this but be runtime converting and using reflection to set initial values. You may, for example, only want the values to be initialized after another system has placed them initially.
@amber flicker Yes, I am concerned about dependencies in this case too
But, that is a bridge I'll cross once I get into that
RemoveInitializeTag(); should be e.g. EntityManager.CreateEntityQuery(typeof(InitializeComponentDataTag)).RemoveComponent<InitializeComponentDataTag>(); to be 1000x faster
EntityQuery doesn't have RemoveComponent... I'm looking up how EntityQuery works
yea you need to use entitymanager sorry.. lemme fix your code, 1 sec
ideally you wanna use an entitycommandbuffer to prevent extra sync point
yea plus, in and a whole bunch of things
entity names are an editor-only feature @violet cosmos
@zinc plinth do you mean WithName() ?
@violet cosmos I mean entities having name in general, you won' have that in standalone
I would also choose to remove LastPosition from PlacementBallisticMotion and put it in it's own separate ICD called e.g. PreviousPosition. Makes the system very widely applicable
(also please create your queries in OnCreate instead of recreating them in OnUpdate) ๐
entities.withname is just what it shows up on the profiler as, it's not the actual entity names
yes - I did mention that before but didn't do it above - general good practice - time to do a new version
@zinc plinth Where am I defining an entity name?
hoo didn't know that @hollow sorrel
Yah, I'm just in the habit of using that
you're still right that it's editor-only but i would assume they ifdef that out in non-dev build ๐
@amber flicker Thanks for clarifying, I appreciate it ๐
hehe, yah I just did that too
also GetEntityQuery > EM.CreateEntityQuery
because the later doesn't trigger system optimization in case there's no entity to process
oh? is that true @zinc plinth ? TIL
ye
internal EntityQuery GetEntityQueryInternal(EntityQueryDesc[] desc)
{
var state = CheckedState();
ref var handles = ref state->EntityQueries;
for (var i = 0; i != handles.Length; i++)
{
var query = handles[i];
if (query.CompareQuery(desc))
return query;
}
var newQuery = EntityManager.CreateEntityQuery(desc);
AddReaderWriters(newQuery);
AfterQueryCreated(newQuery);
return newQuery;
}
void AfterQueryCreated(EntityQuery query)
{
var state = CheckedState();
query.SetChangedFilterRequiredVersion(state->m_LastSystemVersion);
#if ENABLE_UNITY_COLLECTIONS_CHECKS
query._GetImpl()->_DisallowDisposing = true;
#endif
state->EntityQueries.Add(query);
}```
I mean unless EM.Create somehow is able to get the context that it's called in a system, but I highly doubt that
checked: it doesn't
hah.. just went to fix up some code and saw I'm already using GetEntityQuery.. yet another thing I probably knew then forgot ๐

Good to know though, I didn't know the difference
OK, even though I have another option that's structured through the interface.... I think I'm convinced on this. The one thing I'm going to do though is keep the interface, but empty... So I can tag ICD's that are initialized
Would also be nice to have a [RequireAuthoringComponent()] attribute instead for the ICD though
Thanks for being patient with me and helping me out guys. Even though I didn't use the init interface... Writing it and making it work, learned a lot
yet another thing I probably knew then forgot
i had the classic "google an ecs thing, first result is a post by myself with the answer" happen to me recently
So I can tag ICD's that are initialized the.. what.. ?
I assume @violet cosmos meant tag entities that are initialized but still yea.. pretty lost with that paragraph.
@zinc plinth So I can know that if I'm looking at a IComponentData definition, I also know it needs A: The InitializeComponentDataTag on the prefab and B: That somewhere there's a system to set it's value
Interfaces are chucked anyways. IComponentData is an empty interface as well
@manic aurora I'm curious now - what was it about?
I'm working on a project that's going to take me a year to complete... In 8 months am I going to remember this struct or other has init?
@violet cosmos two approaches - your other systems will know it's been initialized because it doesn't have that tag (WithNone) or because they all run after your 'InitSystemGroup' or whatever where you explicitly run your init system first
Why did Unity make IComponentData then?
They actually are using it to filter types, simply that. It's an empty interface
I can "tag" my structs and leverage it in the future as well, either with codegen or even a quick grok
i wanted fine grained control of system updates across multiple worlds without manually updating every single one of them, so it was like, how to fiddle with the new playerloop api
it's a pretty out of date post, i should remove the ecs portions which are probably outright misleading now, the player loop stuff still helped
ah! yea - so much trial and error in that - like getting an editor world working outside of subscenes.. kinda simple.. kinda just try things until it works
ended up not using it anyway ๐คทโโ๏ธ - turns out i wanted multiple physics worlds, and stepping those manually in parallel is blaaaazing fast
oooooh nice - doing some trajectory prediction or something?
time rewinding netcode D:
oof ๐ brave
wish we had a dots-wip channel - would be nice to see some people share some things - you posted anything anywhere about it @manic aurora ?
I JUST got back to it. I had a WIP stall out about a year ago when I got to the โrewindโ portion and couldnโt find an efficient way to do it
Over the weekend I proved out the performance of the multiple physics world approach, so just gonna start reimplementing things on latest dots packages
happy to share when Iโve got something concrete, it SHOULD be pretty crazy
nice - plz dm or here when you have something to show
@manic aurora You know of Chronos, correct?
Also, the Unity XR Interaction Toolkit has a way to record controller positions and play them back. I'm not 100% but I think some of that toolkit was ECS, and possibly including that feature
yeah actually DOING the rewind is nearly trivial for my case, so no point looking for 3rd party help with that, it's just about doing it performantly at scale. my year off was basically waiting for dots physics (stateless + fast) to be mature enough to fulfill my use case, hah.
usually if i ask a question i keep my use case a secret, because explaining my netcode needs always results in a ridiculous 2000 word essay
@manic aurora How do you determine what parts go into different physics worlds?
well for my use case each physics world is just whatever existed in that world during that server tick, and i clone worlds as i need to to rewind individual players
Ahh, gotcha. So they're kind of like snapshots of the past?
yeah, exactly, a player's view is always some interpolation of two consecutive historical worlds, so you want to recreate that view on the server with that information
So, before I get too much deeper into this...
I understand that ForEach().ScheduleParallel() schedules just that query to multithreaded. Is there a way to schedule multiple ForEach() queries to run in parallel?
In this case, I'm expecting multiple different types of entity archetypes/systems, but small sets of entities... As in, 5-20 sets of ForEach in systems, that only return 0-10 entities
that should just...happen if the systems in question don't have dependencies on one another and are in the same group and not ordered such that other systems invoke sync points between them
How do you mean, same group?
are you looking in the debugger and seeing them run sequentially?
No, I'm working out conceptually right now
same group like, SimulationSystemGroup, PresentationSystemGroup, etc
So lets say I have
Entities.ForEach(ref Translation t, in SomethingA a).ScheduleParallel();
Entities.ForEach(in Translation t, in SomethingB b, SomethingC c).ScheduleParallel();
Entities.ForEach(ref Rotation r, in LocalToWorld ltw, in SomethingD d).ScheduleParallel();
....
and many many more like that. Each ForEach would be 0-10 entities though (very often zero)
sooo, it sorta depends
if you schedule a job writing to a translation, then immediately schedule a job reading from it, those two things can't be sensibly run in parallel. i forget if the job system is smart enough to figure out to make them sequential, or if it just errors out, but that's an example where you'd lose your parallelism
say these were all read only jobs? you can just schedule a crapton at once and dots will hand em out to worker threads in a sensible way
Is this where all the ecs lords are at?
this is the emotional support group.
I just read up a bit. I could've done that first
Yo wth is up with this? What's with all the magic
I mean, I love the way it works but it's entirely different and there's a lot of stuff going on that is hard to predict will happen
yeah, there's a lot of trial and error involved, but most people here and on the forums are pretty happy to answer any questions if you get stuck. there's so much magic because there used to be zero magic, and it was extremely cumbersome to work with ๐
Does Entities.ForEach create some sort of instructions that will actually run elsewhere? Is that why it needs the .Run()? What's up with the command buffer and also how drunk were you when you came up with BeginInitializationEntityCommandBufferSystem like really
Oh I like the magic, sort of knowing what's happening. But it's going to make it a lot more confusing for newcomers to C# and unity I think ๐ค
I only just started today but I'm looking forward to figuring out saving/loading, stats, leveling/rpg stuff and all that. I'm excited about the future.
I'm sorry. I've spent most of today bottling this up before I remembered there's a channel
So I sort of just opened the flood gates
I'll take it one day at a time... But I'm having fun. It's really an entirely different way of thinking though
Okay so breath... Actual questions.
- Is there some sort of "bird's eye" description of this ecs stuff? But that I mean how does Entities.Something.Run() work exactly
- Is this a system UE also uses?
Entities.ForEach is (a lot of) syntaxic sugar to create jobs from entity queries that you declare within the Entity.ForEach (you can't use true EntityQuery per se in this)
.Run() is synchronous. So you can ForEach().Run() and access the result immediately. Alternatively to Run, you can use Schedule, which will schedule a job that gets processed in another thread asynchronously; you get the result later
Run is main thread execution
for 1. the official docs are getting better https://docs.unity3d.com/Packages/com.unity.entities@0.13/manual/index.html and the discord started a wiki that's getting filled out kinda quickly and has some additional resources https://github.com/DOTS-Discord/Unity-DOTS-Discord/wiki/Best-Practices
imo the samples are the best resource though, stuff you can actually run and play with https://github.com/Unity-Technologies/EntityComponentSystemSamples
I've been following this
Ignoring the thumbnail, it's actually pretty good. But every line of code took me 30 minutes of research
nevermind all the api changes since that video
Also the setup was quite difficult...
Unity really tried hiding it
No longer in preview, no longer listing the repo in preview info
I had to guess the names (and happened to be right)
haha, i found a list of the full package names for all the experimental packages somewhere
i should've saved it
I've seen no changes yet besides EntityA/EntityB
Wasn't this by any chance was it?
i...obviously did not watch this hour long video in the past two minutes, but just skipping through it, i'm noticing he's not using SystemBase
which i would recommend using
Okay well, I'll add that to my research for after I finish this video
At 43 minutes now ๐
i...obviously did not watch this hour long video in the past two minutes
... Amateur.
Once I get this, I'm going to make a summary from my perspective.
See if I get this right. I want to document it in "simpleton" terms
here's the list i was talking about https://forum.unity.com/threads/visibility-changes-for-preview-packages-in-2020-1.910880/
I actually wrote that up on the wiki the other day: https://github.com/DOTS-Discord/Unity-DOTS-Discord/wiki/Installing-DOTS-Package-in-Unity-2020.1
So this channel is kind of like a passionate fan club then
I'm still deciding if I'm going to jump on the boat or run away in fear
I like that. That's commitment
When do you predict this will land? Because it's been in the works for a couple of years now right?
Ultimately, I think Unity will make it a core part of the editor then deprecate MonoBehaviour
Years
yeah, my best guess is "not in 2021, probably not in 2022"; i took a year off, and when i came back they were pulling dots even further from public consumption, as you know
i mean if you're talking full editor support, "not in 2024"
Hm
that said, you'll uh, notice that despite that, we are still here, the forums are pretty active
probably a reason why ๐
I will read all the links you sent earlier tomorrow. I'm starting to get tired and a bit tipsy ๐ But does it include stuff like saving and how to deal with stats (damage, xp and such)?
I'm pretty new to unity (not coding) so I think getting into this now will give me a fair shot of moving from web dev to game dev
for individual feature implementations, i'd poke around the samples; the docs are gonna be a lot more high level, but without them nothing else will make sense
I understand. Thank you
Unity should come with a warning label
Might cause you to hate your current job
I can't stand JavaScript anymore. Or Swift. Or Kotlin.
I just want to do this all day ๐
Honestly, if you're just getting into Unity, I'd go with the MonoBehaviour workflow
^ that is pretty good advice too
ecs is cool and powerful, but gamedev hard, monobehaviour easy
Well when I say "just" I mean < a year
I've done monobehaviours, I get them, but they frustrate me
Btw this is one of the friendlier channels I've visited so far. So hats off to you
dots community is lovely
Anyway, my next game is going to be using ecs. Mark my words ๐
I'm not one to shy away from a challenge. I'll out-friendly all of you, you hear me? :p
Uff, I'm having a bad math day
math. Not even once
In ECS, what's the logical way to break down the behavior "Move to Target"
My first thought is to have a MoveToTarget component, that has a float3 Position, but... I'm not sure how to reference that other Entity/GameObject inside ECS Land
Does MoveToTarget instead have a property Entity Target, that has to be initialized? then I don't need Position but i use EntityManager.GetComponentData<Translation>(moveTo.Target);
If the latter is the case, what's the best way to handle if say... The Target Entity was destroyed?
https://docs.unity3d.com/Packages/com.unity.entities@0.13/manual/ecs_lookup_data.html - I guess that's covered in this example
Is there a way to define my own groups, assign systems to those groups, and slot those new groups into existing System Groups?
so done writing the Visualizing DOTS/ECS part 1 in the wiki
https://github.com/DOTS-Discord/Unity-DOTS-Discord/wiki/Visualizing-DOTS-ECS--Part-1
kinda proud of this

nice! Good job with that, it's very clearly presented
Hello , can i store sha512 at FixedString64?
nice writeup! I always wonder why people say data can't have functions though,
like they can, but that is not the usual pattern to take. Instead, usually static classes are used for utility methods. I don't really see a problem though with putting methods in component data structs that exclusively operate and that one component data
I should also add "have you ever wrote a SQL statement in a cell of a database before? Did it run? Of course not!" ๐
@violet cosmos yeah, I think I would probably do it like that,
if you have an entity manager, you can use Exists to check if a desired entity is still there,
otherwise, you could work with something like ComponentDataFromEntity<Translation> translationGroup;
in a job,
those groups serve as lookup for components for entities that have those. you can also check if an entity has such a component with translationGroup.Exists(entity); and then get the component for an entity with translationGroup[entity].
I think you could also use a concurrent command buffer to query your MoveTo components for destructions if they either reached their target or you find the the target entity was removed or doesn't have a translation component
nice writeup! I always wonder why people say data can't have functions though,
like they can, but that is not the usual pattern to take. Instead, usually static classes are used for utility methods. I don't really see a problem though with putting methods in component data structs that exclusively operate and that one component data
@minor sluice
You can do it for structural functions, not main calculations. If you put your calculation over components, you will lose architecture and ecs pattern.
Guys how many characters can be store at FixedString64?
well how many bytes is 1 character?
not sure how the new entity foreach query is to write this, but with a job struct, you'd just let a system class get the component group by doing
PlayerEnemyCollisionJob triggerJob = new PlayerEnemyCollisionJob
{
GetComponentDataFromEntity<Translation>()
};
and then in the execute method of the job, you can check with Exists on the group if index entity has such a component, and access it with an entity as index above to get the component
@radiant sentinel what do you mean with main calculations?
like I wouldn't put methods in that need to operate on any other data outside of the data that is already internal to the same struct, because then you'd be right of course - losing the architecture because components are mixed with overarching logic again, like it is often the case with monobehaviours
well how many bytes is 1 character?
@deft stump
Utf8 or other
I dont know about FixedString64
I think the doc answered your question
Those who need more than 65,535 contiguous items should allocate from the heap, as storing that many things contiguously in a C# struct is likely to result in much wasted time, as the compiler copies the struct often.
I think the doc answered your question
@deft stump
65000 items, not characters
It is 64byte i think and i can store sha512 because it is 64 byte
How can i store bytes at FixedString64 structure?
ascii characters are 1 bye, utf8 characters are 2 bytes, chinese and japanese(and maybe even more asian languages) characters are 4 bytes
Thank you @deft stump @opaque ledge
Is the burst compiler of any use outside the job system?
Like, can I burst compile anything else?
nope.
Burst doesn't like touching managed objects
Yeah, but you can use jobs without ECS, like you can schedule a bursted job in a Monobehaviour and wait for it to complete etc.
Yeah, but right now I'm not using jobs
I'll just put it onto my monobehaviour and see what happens i guess
Doesn't really do anything but I'm not surprised
You can make a job that runs on main thread and burst it.
Job system doesn't always need to be for multithreading.
Most of my performance intensive stuff happens with compute shaders so not really gonna happen I think
Why?
I can't call compute shaders from jobs can I?
And I'll need to convert all my stuff to use native containers
You can do anything in jobs. You probably can't do with Burst though.
But doesn't hurt to try.
Correct me if I'm wrong but I don't think you can do compute shader stuffs in jobs
And even if you could, the calculation is on GPU side anyways.
Why not? Just do Job.WithCode and run on the main thread.
It's a case of whether the task is better suited for CPU or GPU.
I don't think they were asking whether they can transform their shaders to jobs.
But to burst the code around the shaders.
^
Its already running mostly under 1ms but I was just wondering if anything could be done
Anyways, it depends on what you're doing. You can apply DOD to anything.
Most of my performance intensive stuff happens with compute shaders
yeah
My interpretation is that majority of the frame time is spent waiting for GPU to finish the job, and the bottle neck is not on the CPU side.
Bursting the code of CPU starting the GPU compute shader won't help much if the bottleneck isn't even that.
Yeah, that's true
Right now I work around the GPU bottleneck by waiting a frame before trying to get the data
But it was a general question, so I know I have such an option if I need it
Not an expert by any means but I'd say 1ms is more than good enough.
Then the answer is yes, and Unity recommends you use jobs/burst wherever possible.
If you need performance.
But you'll need to change the approach a bit for that.
