#0.14 Bevy Jam
1 messages · Page 3 of 1
yep we do that for the UI
Ah yeah right
well by "directly" it's actually a command ofc
new idea:
struct SpawnPlayer {
// player data
}
impl Component for SpawnPlayer {
fn register_component_hooks(entity, world, blah) {
let data = world.entity(entity).remove::<SpawnPlayer>();
// Spawn logic
}
}
because it's not an exclusive system
Only thing that AFAIK does not work is spawning something in a hook
wait what spawn player as component???
no child entities tho
oh god
Oh yeah that's common when you want to load a level or something that does not implement Reflect
note that world.commands() exists, so you can queue spawns
My vote is for keeping the code as-is with observers
For one reason mostly
looks pretty based, you mean
Oh hey @hidden pond is back 👋 How you doing?
requesting approve: https://github.com/TheBevyFlock/bevy-template/pull/68
I have a quick question about the splash screen...are actually allowed to distribute the bevy logo, especially given the licenses this is under? I remember the CI template we forked from removed it due to that.
@prisma delta wasn't the logo transfered to Bevy and is now under the same license as code?
allowed, yes, as long as we get permission and specify the copyright in the README
it just means that whoever clones the template has to consider whether they want the non-open-source bevy logo in their assets
Yeah this is the foundation now
Put it in, but list the credits
Our template also has the CC0, so we might need to specify in the README the license does not apply to that at the very least.
@bitter sparrow waiting on your feedback on https://github.com/TheBevyFlock/bevy-template/pull/70
Just want to make sure we don't accidentally violate a license or cause copyright infringement.
I like how Bevy itself highlights it
I think this is a good example to follow
yes it has MIT and Apache as well which also don't match the logo, regardless we have to specify the license for assets
and should probably specify the license even for assets we use that are CC0
Maybe we should have a button in the menu for licenses?
So that users can add the assets they use easily
you mean the credits screen?
It's a bit different than credits imo
credits = "This is the creative team"
licenses = "This is the stuff we yoiked"
At least in my mind
Credits also should look nice, probably. Not too much text, maybe a few social links
while licenses is just a dump
the font can be minuscule there, just get it onto one screen so no one has to learn that bevy has no widget for scrolling
i mean ig so but licenses are common to put in credits section
I've seen both styles. Personal preference I guess?
Made by
...
Assets
...
Many games just have all licenses in their splash screen
@bitter sparrow can we merge the movement PR or should we wait?
👍
How do you attach sound to a character
If you see something wrong or buggy with the implementation, I'd also be happy if you could comment on https://github.com/bevyengine/bevy/pull/14223 as well
it should be based on the physics right?
Do you mean for footsteps?
That should probs depend on the Velocity, yeah
I have not looked much into audio in Bevy, so I can't comment much on that. No idea what best practices there are.
Also maybe ask #audio-dev
review'd
sec
the best practice is to use bevy_kira_audio instead 😩
Idk about that, looks like it won't be upstreamed after all
even so
the best practice may change in 0.15 or 0.16 but as things currently stand
was that meant as a joke orr am i missing the free section
oh
nvm
i did miss the free section
There is also https://opengameart.org/ which also has some audio iirc
@slender belfry yeah physics don't have to go in core, it more makes sense there if you're pulling in a 3rd-party library like avian2d
then you're just setting up their physics plugin
oh all the physics stuff was just added to the PR?
before it was just spawning player/level
Yep
ok
or wait
what do you mean?
I mean to say "yes, this PR includes all the physics stuff"
But I added that hours ago
😄
so the thing about fixed timestep is
the last time i tried it the tooling sucked
it's "technically correct" but it was a buggy pain
i think some of the bugs have been fixed
is it good enough to recommend in general though?
also for a game jam i'd prob not bother trying to get it right personally, fwiw
I'm pretty sure that at least https://github.com/bevyengine/bevy/pull/14223 is working as intended. Lightyear also is doing it like this successfully, so I'd say it's alright now
well lightyear has the time to write any boilerplate / make sure it works, anyways. in theory, idk what they're actually doing
I wouldn't bother setting it up, but if the template already did it the right way, I'd just follow that and get the correct behavior for free
i suppose
I mean, okay, that's a lie. I literally just bothered setting it up 😄
I'm pretty strongly in favor of showing people how to do it the right way if we are semi-official
if fixed timestep is good enough to be considered "the right way" then sure
it used to drop events, i heard that was fixed recently
so all user game logic should go in FixedUpdate, right?
only time-based things i'd say
physics
you need to process inputs in Update cause the resources get refreshed each frame
graphics need to be in Update
interactions can be ticked with physics so thats FixedUpdate
Exactly right
yea interactions like a projectile hitting something and dealing damage
or triggering an effect on collision
mhm
there are probably cases where you don't need to, but anything based on physics, yes
Not necessarily. The parts that detect the collision need to be in FixedUpdate. The code that then does cool stuff in your game based on that collision can be in Update
for something like updating a health bar, that's in Update i assume
but then you'd be framerate dependent
if there are multiple FixedUpdate steps in the same Update frame, the later ones wouldn't see the effects of the earlier ones
oh no i don't mean vfx
i mean cause-effect
Keep in mind FixedUpdate runs before Update
but yeah, if physics get updated in two FixedUpdates and then we have an Update that reads physics then there will be problems
cant have that
You can query the PhysicalTransform in Update for that
But you could also spawn it directly in FixedUpdate
Your choice really
i'd say fixed update is correct here
the point is the next FixedUpdate step will want to see the effects of the previous step
Aaah I see now!
otherwise framerate affects how fast game-affecting effects are triggered
Yes, if you need to access that information, you are totally right!
I was thinking about a purely visual effect here, like a particle spawner
yeah for sure. that can be in update
So that's where the misunderstanding came from 🙂
just noticed, this isn't a linear interpolator
probably won't be noticeable, but wanted to point it out
Yep. I totally deferred to how lightyear does it
lightyear does it that way?
Ping @lavish robin
i'm once again sad we have to bake in our own physics so that the user can tear it all out and depend on avian2d
As a fellow Avian fan, I am also a bit sad.
Never actually used it tbh.
This is very odd, it's assuming you get multiple FixedUpdates per Update, which shouldn't be the common case
me neither but i'm still a fan
more often you get few Updates interrupted by a FixedUpdate
i'll prob switch to it once i update to bevy 0.14
Lag spike
why are we optimizing worst case experience xD
well, let's wait for Periwink to reply
I'm not sure what the actual question is
Two questions
Why is the example using one Update to many FixedUpdate, which I believe isn't the typical way it works?
In the example it's always a frame (Update) with one or two FixedUpdates
but never zero fixed updates
If your update is fast enough, you should get zero fixed updates
exactly
oh btw. one reason not to use commands or observers for spawning things is you can't add components to them after spawning
Hm no specific reason, just because that's something I was observing in my examples (where I set the tick-rate to 64Hz). But in my tests I test both cases (tick rate faster than frame rate and frame rate faster than tick rate): https://github.com/cBournhonesque/lightyear/blob/main/lightyear/src/client/interpolation/visual_interpolation.rs#L552
like StateScoped would be more idiomatic to add after the helper method spawns the thing, imo
that's why we only do that for well defined constructs 😉
hm
regardless
I'd say that's probably good in this case
Okay I don't think I have the second question, I think you may have a bug @slender belfry
Whaddup
The interpolation uses values from last 2 FixedUpdates, not from last Update (transform.translation) and last FixedUpdate
Yeah i don't think you want to interpolate between the last rendered value and the next FixedUpdate value
you always want to interpolate between 2 FixedUpdate
@lavish robin I'd be super grateful if you could take a look at https://github.com/bevyengine/bevy/pull/14223 in general
(contributor successfully baited into a review, rejoice)
Oh right, that makes sense! Thanks.
haha
glad we got this figured out
so PhysicalTransform is to separate it from Transform which is used for interpolation?
So, just so I got this right: I want to keep track of the last PhysicalTransform and interpolate to the current PhysicalTransform, then use that value for the Transform, right?
if so i'd explicitly mention interpolation as the reason for its existence
Yeah that is part of the huge documentation on the top of https://github.com/bevyengine/bevy/pull/14223, which I did not copy-paste into the template
I'll add comment though, makes sense to mention it 🙂
I'll be AFK for a little while, gonna address the comments later
i'll trigger a release cause why not, we're not paying for it
crazy thought. what if the release workflow split the upload to itch.io into two jobs: one that only uploads the web build, and one that uploads all the native builds
that would give a 3x speedup for uploading the web build instead of waiting 10 minutes for windows...
probably not worth splitting into two releases on itch.io though ig
Baloo Bhaijaan 2
yeahh we are already flagged as suspicious
download my game template! https://the-bevy-flock.itch.io/bevy-template
@lavish robin is it correct like this? https://github.com/bevyengine/bevy/pull/14223/commits/02342f88420c7cfe6c4be8486ff413a02c1f8090
no splash?
Why no splash screen 👀
Also @agile dirge
Ah now 🙂
not released yet
oh
i wasn't linking the release, just making a joke about it being suspicious
lol my bad
hehe
release just finished now tho
ok no
the css spinner -> splash screen combo looks awesome
ngl
i cooked
now we need an SFX for the splash screen
so people kno when their game is done loading
birds chirping sfx
embedded asset
bevy needs an official trademarked sound effect
we should interpret the entire bevy repository an audio stream and find something cool in there
Yes I think that works!
Yay! Thanks for the help 🙂
Mind leaving an approve in that case?
I always imagine the SEGA chime but instead they say BEVY
need to get an audio clip of a parrot saying that
i'm adding some comments
Thanks!
I'd love to try it, but I'm not spending money on that
(also shady licensing when the content is AI-generated)
y'all work so fast
copying comment here:
commands.spawnusesCommands::entitiesto return anEntityCommandswhich includes bothEntityandCommands.
commands.addandcommands.triggerboth can't do this, but an extension trait could (like we do for UI widgets). Maybe an extension trait with a generic method likecommands.my_spawn(impl Spawnable) -> EntityCommands, so you could docommands.my_spawn(Player { ... }).with_children()etc. if you want
the fact that other spawning methods return the Entity id right away, but commands.add and commands.trigger don't, mean that IMO we should not be using the latter two
like maybe we could use them internally, but w/e api is provided it should return the Entity
That's a pretty good point
I don't think this is something we should support
we aren't trying to make another layer of spawn API
we are trying to make top-level methods of spawning predefined game entities
like a layer on top of bundles
yes but it's so limited if you don't get the Entity back
the spawned entity should be mostly complete
what if you want to set its parent?
I'd need an example
okay let's say i want to spawn an enemy
i'm using bevy editor pls so i want all my enemies to be under an abstract Enemies parent entity
commands.trigger(SpawnEnemy { ... }) and then.. what?
You set the parent in spawn_enemy
because you defined that all enemies will have Enemy as the parent
again, this isn't a shorthand for Commands::spawn
it's a new API that shared the same "spawn" name
yes i'm just saying this API is strictly worse
disagree
spawning something and then not being able to do anything with the Entity id is bad
what if you want to store it in a resource, or who knows what
there's always something you don't account for
oof
we aren't making an engine
we don't need to support every imaginable option
most games will have clearly defined mechanics
and in 99% cases they won't need the Entity
if you do need it, explore other options
ehhhh
it's not like it's more work to provide it
this is just limiting options for no reason
i really don't think it's 99% cases
maybe like 80%
probably less tbh
it really is, take a platformer
in a real game you want the flexibility
player, enemies, interactibles
you spawn them and let systems do their job
no Entity is being used
if you have player variants, either use an enum to control the variant or have multiple spawn methods
like, this is not meant to be flexible, we encase very specific logic in a convenient wrapper
you can still get the latter while also getting the former tho
how exactly
return Entity
you can't return entity because you don't spawn entity
and in most cases the user will just not touch it
like
okay
here are the possible cases:
- defer spawning (observers/commands) - no
Entityto return at call site - immediately spawn (
Commands::spawn) - returnEntityat call site, but also provide ALL values for ALL components (including asset related data which we specifically try to defer) - hybrid - spawn an incomplete
Entityand return it at call site, add other components later
we can't do that
Commands::spawn is deferred too btw
okay, so once again, how do you return and not mess up the entity component integrity
the entity id is created before the entity is actually spawned
and
and returned? wdym
...
i will fight against any proposition that introduces race conditions
if you spawn entity and fill it later
in a different command
you have a time period where it's incorrect
can't have that
not really, both commands will be applied at the next sync point
like commands.spawn(xyz).insert(abc) is totally fine to do
okay how about something like this:
let entity = commands.spawn_empty();
commands.trigger_with_targets(entity, InsertPlayer { ... });
return commands.entity(entity);
i see how that would work with commands now
i honestly thought the EntityCommands batched the changes into one command .-.
it doesnt
ic
like will it work? idk i can make a pr to try it out after this lands
no, it will work in common case
im looking for edge cases
we don't want to give a solution that leads to obscure issues
cause with commands, if they come from one system they run back-to-back
but if you do a command then observer
there is way more that can happen inbetween
true idk what the ordering between commands and observers is
tbf though... the trigger_with_targets can instead be commands.add(InsertPlayer { entity, ... }), so the ordering will be well-defined
even though the new entity arg makes observers more appealing
Why not the later Sega Shout, but it's bevy instead? "BEVY!!!1" :p
I actually think the right thing is to have a nice bird song or a flight of birds whooshing by
for the record, this is exactly what commands.spawn does internally: https://github.com/bevyengine/bevy/blob/ec1aa48fc6d4f7683e41d7aa9fff252882549cfa/crates/bevy_ecs/src/system/commands/mod.rs#L355
Back now! I'll work through the comments now and leave the spawning stuff for a follow-up. It may be worth asking #ecs-dev for their opinion as well.
For the record, I have no strong feelings, it should just not look too surprising or weird to a beginner.
this would work for example:
// Auto-derives EntityCommand
fn insert_player(entity: Entity, world: &mut World) { ... }
fn my_system(mut commands: Commands) {
commands.spawn_empty().add(insert_player);
}
not suggesting this as the API just PoC
ok ill just make a pr later
I'm trying to figure out whether we can reserve an Entity and request a spawn command with a specific Entity
then observers would work fine
i think there's an upstream docs error
spawn_empty says it adds a command. it does not seem to
it registers the Entity id directly on Entities
unless i'm mistaken
if spawn_empty makes the entity at call site, instead of just reserving an id
then i think we're fine with the observer trick
yeah ofc this is not blocking
Done 
Another round of reviews plz https://github.com/TheBevyFlock/bevy-template/pull/70
I'll double check my test case
why not
o you have a test case ok ill wait
testing give me some time
but i suspect a hook like what Jan did will make this fail miserably
im not super clear on command/observer execution order
FYI hooks cannot insert entities AFAIK
They only get DeferredWorld
it just cannot access entities and mess up archetypes
but if you defer it it's fine
(as name implies lol)
thread 'main' panicked at src\game\spawn\level.rs:32:44:
called `Option::unwrap()` on a `None` value
fn spawn_level(_trigger: Trigger<SpawnLevel>, mut commands: Commands) {
// The only thing we have in our level is a player,
// but add things like walls etc. here.
commands
.spawn_deferred(SpawnPlayer)
.insert(ComponentWithHook);
}
struct ComponentWithHook;
impl Component for ComponentWithHook {
const STORAGE_TYPE: StorageType = StorageType::Table;
fn register_component_hooks(hooks: &mut ComponentHooks) {
hooks.on_add(|world, entity, _component_id| {
world.get::<Transform>(entity).unwrap();
});
}
}
i insert a component that's expecting other components to already exist
spawn deferred is implemented with observers
wait no, i fucked up the impl
holy crap
it works
okay, well then i have a PR ready
i need some bikeshredders
what do we name this
pub(crate) trait SpawnDeferred {
fn spawn_deferred<E: Event>(&mut self, events: E) -> EntityCommands;
}
impl<'a, 'b> SpawnDeferred for Commands<'a, 'b> {
fn spawn_deferred<E: Event>(&mut self, event: E) -> EntityCommands {
let entity = self.spawn_empty().id();
self.trigger_targets(event, entity);
self.entity(entity)
}
}
Oh whoops, I forgot I didn't use the GameSystem enum I prepared. Fixed.
I personally like spawn_deferred already
That is quite cheeky 👀
So what's the secret reason why this is not what trigger_targets already does?
it returns EntityCommands at call site
yeah, Pyrious cooked
I just had to check the edge case but I bugged him long enough to figure out all the code
I'm moving this to util then
hehehe
i want the name to reference the fact that it takes in an Event
trigger_spawn
perfect
In reference to trigger_targets
now that it works um
i noticed we don't need it
we don't have a use for it here
cause we don't need Entity at callsite
Yesn't
wait
You could add the StateScoped to the spawn_level function this way
I set the PR to automerge as soon as @bitter sparrow gives it an approval
gonna go cook something as well now 
👌
I'd prefer to avoid that name as it may come with preconceptions about what it supports
e.g. loading from a file
i cooked too hard guys
impl<'a, T: Spawner<'a>> TriggerSpawn for T {
fn trigger_spawn<E: Event>(&mut self, event: E) -> EntityCommands {
let mut entity = self.spawn_empty();
let id = entity.id();
let mut commands = entity.commands();
commands.trigger_targets(event, id);
entity
}
}
this is required for ChildBuilder to work properly
my rice is ready 🍚
four transform types 🐸 but ok
comments explain it
how does auto-merge work? is it gonna get merged now
had to refresh the page all good
That would be nice. I would have to use TanTan's 'bevy song' myself though. 😛
let intent = intent.normalize_or_zero();
let velocity = intent * SPEED;
player_velocity.single_mut().0 = velocity;
this fine?
merged
and obviously it panics because i didn't try running it
single_mut moment
so either the system only runs in the Playing state, or i switch to get_single_mut (which would result in silently nothing happening if there are 2+ player entities), or i go back to iterating over the query
my preference is for #3 but open to opinions
if it's the same input scheme multiple players make no sense
okay well #2 is possible because get_single_mut returns a Result not an option, so i could check the error :p
i agree but at the same time no reason not to allow it imo
true
// Option 2
if let Some(mut velocity) = player_query.iter_mut().next() { velocity.0 = velocity }
// Option 3
for mut velocity in &mut player_query { velocity.0 = velocity }
uh ignore the velocity name shadowing
hm if there's more than one player entity for some reason, option 2 will silently move a different entity each time
do all then
I'd do if let Ok(foo) = foo.get_single_mut() else { return; }, everything else is kinda misleading imo
in terms of the resulting behavior, i think moving everything makes the most sense
In fact, what I actually actually do is this https://github.com/tbillington/bevy_best_practices#getter-macros
But that’s way more controversial haha
I can live with that
i mean that macro would be fine, i'm just more concerned about the behavior than the code
for something like a window entity, you want to get the single window or return from the function otherwise
but for player it's not like the system cannot continue if there's more than 1
this system at least
like if you need the window size to do some calculations on each entity in a query, then if there are 2 windows.. there's no sensible way to continue
merged
Fair enough, you’re right
@agile dirge do we have to support triggering the spawn events without an entity?
it seems like that's the main ugliness in the api?
mmm
what if EntityCommands::trigger existed
wouldn't that be nice?
let mut e = self.spawn_empty();
e.trigger(event);
e
😍
I'd like that
PR on Bevy main plz
will do if no one in #ecs-dev complains
commands.spawn(bundle).trigger(event) mmm
also add trigger capability to BuildChildren or a way to retrieve Commands
That’s one juicy API
true
@agile dirge is it alright for you if I do another refactor pass? I’d like to add name to everything, reflect, etc.
Asking because you might get a merge conflict then
Ehh sure
i think if we merge mini's pr before the refactor pr it's fine
Aight, I’ll wait then
well you can make the refactor pr now if you want
ig it depends on what you're planning to do
Also, thoughts on #derive order? I personally do Debug, Clone, Copy, PartialEq, Eq, Hash, Default, Component/Resource/Event
But that’s completely arbitrary
so what i do for derive order is the "most important" derive first, aka Event or Component etc
No preference
and then after that kinda arbitrary but i do the traits required for the first trait first
and put PartialEq by Eq, and Clone by Copy
anything beyond that is fair game afaic
How ready is your PR? I did not look into it too much yet because I thought you were still on it
Sounds good
Hi @hoary flower 👋
I’d love a format option to sort alphabetically, or on whatever ruleset actually
Its ready for review, i did what i could and im not happy with the api and complexity this brings
seen my review comments?
Only the first two you added earlier
added another one based on some discord comments
Hrrm, looking at it, it looks like the kind of code I'd expect to see in a third-party crate, not a Jam template
I think someone who is not deep into Bevy looking at that will get quite spooked
i feel like that's unavoidable though. i could say the same about the physics stuff
bevy is just lacking some basic features upstream
That one is industry standard though. It will look like that in any engine.
This here is more of an experiment
But I don't want to block the PR if both of you think it's a good idea
i think it's a good idea, and will be replaced by bsn
everyone always ends up looking for a solution to this problem one way or another
Id rather not merge this for the template
Disagree; you can easy work with only observers. Yes, they are less powerful than the proposed alternative because you don't get EntityBuilder, but that does not mean that everyone will look for a solution.
i just really think the api is not bad at all after applying my suggestions
Its still very bad and one suggestion makes it worse
Exactly, For me, the issue is less the API and more "Can I expect someone other than us to understand what is going on?"
Like, if this was my own project I'd have no issues using this, it's neat
?
how else would this look?
in the alternative api
commands.spawn(bundle).with_children(children) right
The problem is the observer system
@bitter sparrow could you show me your suggestion for how the spawn_level and spawn_player systems would look like?
I'm ready to change my mind if it looks intuitive enough
fn spawn_level(trigger: Trigger<SpawnLevel>, mut commands: Commands) {
commands
.entity(trigger.entity())
.insert(Name::new("Level"))
.with_children(|children| {
children.spawn_trigger(SpawnPlayer);
});
}
fn spawn_player(trigger: Trigger<SpawnPlayer>, mut commands: Commands) {
commands
.entity(trigger.entity())
.insert((
Name::new("Player"),
Player,
SpriteBundle {
texture: assert_server.load("ducky.png"),
transform: Transform::from_scale(Vec3::splat(0.5)),
..default()
},
Velocity::default(),
PhysicalTransform::default(),
));
}
basically commands.spawn is replaced with commands.entity(trigger.entity()).insert
.entity is calling spawn in the background, I suppose?
nope, it's spawned before the observer runs with .spawn_empty()
That is a bit whacky 😅
Entity() returns the targeted entity of the event
Oh right, it's not a custom extension function
yea
yes but you're not supposed to trigger the spawn events manually
I missed that in my review 🥹
you're supposed to use the commands.spawn_trigger
but yeah a user could mis-use it like that and it wouldn't be an error, that is true
actually it would be an error i think
you can't insert on Entity::PLACEHOLDER right?
well a panic not an error i mean
Mis-use is a bit of an overstatement, a user is just triggering an observer the way Bevy has taught them.
Yeah
ig so but i feel like an observer expecting there to be an entity is a valid use case in general?
just bevy doesn't have a way to require that statically rn
unless it does and i missed it
even the bevy docs for observer have an example that would panic
if triggered without a target entity
What happened to the suggestion of using Commands instead of observers?
im still down :p
it would be an EntityCommand
You can make a PR if you want, I wouldn't block on that even though I ❤️ observers
okay
If @agile dirge is fine with that as well
Im not gonna stop him from making a pe
Pr*
But if it ends up looking janky dont hold it against me if i refuse it
if you want to remove the spawn stuff and keep the ui refactoring part i'll approve
from your pr
or i can redo it in mine
Ye, ill do that when im at pc, away rn
ok
same 👍
Thoughts on whether I should add Serialize and Deserialize to everything?
I'd do it personally just to be on the safe side
But I know many users won't care
no thoughts head empty in this case
btw all the lifetimes can be removed from the ui/widgets.rs stuff
i will do that
the power of '_
aaaaaaa
Aaah yes, ergonomics 
derive deref and derefmut = ?
i havent seen that before
oh
to deref to Transform, right
suggestion for a better name than prefab here?
im going with prefab in the meantime
hmmmmm may have an idea
will request an open mind for this api when i make the pr
i think it will be good
Solving 4 issues in there 
sure 😄
I added this because IME it's quite a subtle footgun for a lot of beginners
sure
so better made sure that people can have a second camera without wondering where their UI went 🙂
IsPrimaryCamera maybe?
or as a separate component
for like following the player
or is that out of scope :p
It's from Bevy
Marker used to identify default cameras, they will have priority over the PrimaryWindow camera.
right
It's imo the ugliest named component in all of Bevy 😄
Hmm
because that's how you'd name them if they were fields on a struct
Didn't think about it that way
although ig that'd be moreso equivalent to IsDefaultUiCamera(bool)
I'll let it roll around in my head. Thanks for the perspective.
I also did not add any derives to triggers because serializing or reflecting them would be bonkers.
Edit: nvm added all the derives as well
btw the fact that EntityCommands != EntityWorldMut is annoying me rn 😄
may want another trait to abstract it
it's Commands, ChildBuilder, World, and WorldChildBuilder
call spawn, and get either EntityCommands or EntityWorldMut
we're currently only supporting the former 2, but for a custom EntityCommand, you need to support the latter 2 as well
because they take world
Hi @pseudo marten 👋
For a game jam submission: does physics really need to run in FixedUpdate? I think the template would be significantly more approachable just setting the Transform in an Update system based on the velocity.
Hey, I see you have been very busy here xD
i had this concern as well
#1258521739395203174 message
There's a ton of questions each time about why things are jittery. Just showing how to do this by default will save quite a few people a headache, I believe.
I mean, people can still yeet the entire thing if they want
It's not interconnected with anything
Is it still that jittery if one takes the frame time in account? I never really experienced any jitter with that
Yeah, your camera will make huge jumps on lag spikes if it's following the player
Also tunneling
Historically, quite a few people roll their own 2D logic instead of using a physics engine, so they will run into that
(Although maybe this changed and now everyone will use Avian, as they should)
Hmm ok, maybe I never used enough physics xD
I see you discussed it a lot already. Just took a quick look and wondered about the size of the template. It has significantly more code/files than I expected.
It's split into rather neat small files :>
Yeah
that is true. the files are mostly like 50 LoC max
Hey, if others feel the same way, I'm fine with removing it and just pointing to the relevant Bevy example for people who care about that stuff 🙂
It was also important to us to show people how they can effectively structure their game code, because that's another question that comes up time and again
So that also contributes to being happy with a lot of small files
I feel the same way:
https://github.com/TheBevyFlock/bevy-template/pull/79
thanks for the input!
(not putting my foot down on any issues / treat me like any other contributor as this is "outside of the bevy repo")
Looking at the code, the changes seem pretty reasonable imo
The deflicker drop is a bit more controversial; I think @prisma delta mentioned this specifically as the kind of boilerplate a template should include (correct me if I'm wrong)
3 / 5 specifically bugged me as well, and I agree with the additional commentary in 5.
I haven't looked closely at the code, because at some point this thing seemed to become quite complex and I stopped following closely. So I am inclined to agree that an effort to simplify things is a good thing.
But this PR does not do that, so that's fine
If the deflicker fix weren't so janky I would be more okay with it
It is supremely jank 
boot state needed for loading window config anyways ^\_(``/)_/^
Yeah I'm mostly just annoyed that it's so janky in the first place lol
this template won't include a window config most likely. but still, it's only as janky as that would be
I'm completely fine removing it as well
But also I think I'm just generally not well aligned with this effort and don't want to rain on any parades so I am trying to keep my opinions muted 🙂
the difficulty in keeping the template simple is that we're not using 3rd-party crates
so no input management, no physics, no UI abstractions, no asset loading abstractions
etc
yeah, there's quite a bit of boilerplate simply needed for doing an actual game and not just an example 😅
I'd like to hear them. You can phrase it as "feel free to completely ignore me", but I'd still like to hear your input
👀 this message gonna be long
Don't worry about us, we all have our opinions too 😄
Well, mainly I am not sure that the timing is right for this effort -- as pyrious mentioned, it would be a bit crazy to try to build a game in Bevy without a single third party ecosystem crate. I also think we definitely shouldn't be picking winners among the ecosystem crates. Especially e.g. among the physics crates.
So with that background, my thoughts are that this template seems a bit too ambitious, and I'd personally rather
- Link users to https://bevyengine.org/assets/#templates in the jam description
- And add any new exciting templates that pop up between now and the jam there.
Very much just my opinion. I do think that a template that goes a bit beyond what we're willing to do with bevy_github_ci_template but still does not use third party crates could potentially be valuable / something I might use myself, but I think we've gone way way way deep into some opinionated patterns.
And because this is "semi-official" I definitely don't want to make a fuss.
timing not being right is understandable. my take is being opinionated now, and later on removing the opinionated stuff in favor of w/e gets upstreamed, is a reasonable compromise
But also I think we should do
Link users to https://bevyengine.org/assets/#templates in the jam description
this anyway. (as well)
reasonable. i think we were planning to link to other templates in the README but that would probably be better (or link from both places)
I definitely see where you're coming from. I'm personally very happy about having had a place to discuss these opinionated patterns, as I was kind of missing a discussion about best practices in general.
In my experience, for a template to be useful, it will be big enough that it has to incorporate opinionated stuff. The templates so far just involve the opinions of a single person, but this one is coming together from the shared experience of multiple people actively trying to find out together how to best structure stuff. I think that's a pretty cool opportunity 🙂 (at least for me, I'm learning a lot here)
Yeah, definitely
I want people to be very quickly directed to the ecosystem
Yeah, me as well. I actually generally like what y'all are doing under these constraints 🙂
Like "hey, these other templates are cool, these third-party crates are pretty much must have, these are neat"
Is anyone vetoing @rigid geyser's PR? Otherwise I'll merge it. And cry a bit because of the merge conflict's I'll get.
Also, I don't think it's physically possible for me to treat you as just any other contributor, try as I might 😅
i might be but i dont have time to review it rn
I'll wait for you then 🙂
I don't have anything against it, it doesn't bring much controversy
most of those topics came up and we just decided to roll with the one we did
oh another thing. .disable.add_after may be strange, but bevy is meant to be modular. so being able to swap out plugins for your own versions of them shouldn't be considered strange
So, while everyone is in this chat, general vibe check: how do y'all outside the working group feel about two things:
- The deflicker workaround
- Having fixed timestamp stuff in the template
if you could do .swap::<WindowPlugin>(window::plugin) it might look less strange
I'd like to hear @prisma delta's opinion on the second one as well
Mind if I give my opinion on those two since I haven't already?
Please do!
Honestly, looking at the discussions I'm starting to reconsider whether this project was necessary
I don't regret it, I'll be taking a lot of this for myself
but looking back, without 3rd party crates there is barely anything to show
we are either:
- implementing something that should be in core
- implementing something that should be in 3rd part lib
I think having that laid out is pretty valuable imo
yes, the knowledge is definitely helpful overall
- I don't think it's needed for this template, since it's way less valuable on web.
- Without an official example, yes. With one, probably not
I am very much enjoying y'all figure out things that should be in core :p
well, someone still has to add it 😩
@bitter sparrow did you add issues for triggers and other commands?
Yeah, I created a ton of PRs over the last days because of stuff that came up 😄
idk wym by issues for triggers. i have a WIP pr to replace spawn triggers with EntityCommand if you're referring to that?
this
btw regarding pub(crate) being noisy, i agree on that. i accept that it may be "more correct", and i don't fully understand what the benefit to it is, but yeah
ah yeah have not done that yet
Personally. I'm fine with the deflicker being in the template, as its a bit jank. However it also doesn't work on all platforms. If it is jank and likely to come up and isn't necessarily easy to find, then I would support it being in the template.
As for things in FixedUpdate, I'm fine keeping stuff in there. Makes things easier to showcase and it's the "right way". Although I won't have an issue if it's removed.
pub in binary crates breaks dead code detection
Since cargo says "oh this could be read elsewhere!"
Which is dumb, because it's a binary
ok that makes sense
i could probably live with maybe having some uncaught dead code in my binary personally
I was mostly pushing for the pub(crate) stuff, but yeah, I'm completely fine with changing it to pub is that's the general vibe 🙂
Yeah, I think I'm slightly on the side of catching my dead code, but I am fine with changing it back. I think just generally we should remember we're just jammin' and havin fun here. 🙂 Enterprise-grade code isn't really the norm.
Also bevy is a WIP itself, so there's a lot that is needed to be done regardless. This has also helped point out and revealed weak points or areas that wouldn't have been brought up otherwize
"simplify the bevy-template" can be the metric for improving bevy :)
I mean hell my PR would've never been made if not for this.
https://github.com/rust-lang/rust/issues/127497 I filed an issue on Rust about this: nothing seemed to match
bevy-template revealing issues in rust 
Okay, so general vibes are the following, correct me if I'm wrong:
- Use
pubinstead ofpub(crate) - Remove deflicker, it's just too jank
- Remove fixed timestep and link the example
Did I miss anything else that people brought up?
idk if removing deflicker was the consensus?
im in and out of paying attention rn though
I think people mostly agree that it's fine in theory, but the specific fix is just too ugly
okay. i won't complain about that. will re-add WindowState if we need window config
very easy anyways
I'm neutral on deflicker and pro fixed timestep myself. But I'm fine if they end up removed. Especially since we are doing this for a specific game jam. Some of these things should be upstreamed, but.
Fully agreed. If we find we need anything back, we should not feel constrained by this PR having removed it.
I have the same opinion on both, but I think that's the minority vibe here (again, correct me if I'm reading the room wrong)
imo remove fixed timestep before the jam
after the jam maybe re-add
99% of jammers will not want to think about fixed timestep
eeeh
I'd rather have a consistent vision
I'll add issues for these and implement them as soon as cart's PR is done. Ping me when you're ready @bitter sparrow
probably won't be able to review it today
Aight, I'll wait then.
Because I don't want to have a ton of merge conflicts everywhere 😅
Fair enough. FWIW I generally view this template as being a kind of good "start here" convenience template. A way for inexperienced and newer people to bevy to hit the ground running for the game jam, without necessarily needing to understand what templates exist or what they want.
At least that's how I've been treating it.
repost here cause relevant
https://github.com/bevyengine/bevy/issues/14231
hm
i managed to get my spawn api to compile
// Impls EntityCommand automatically
fn level(mut entity: EntityWorldMut) {
entity
.insert(Name::new("Level"))
.with_children(|children| {
children.spawn_with(player);
});
}
fn enter_playing(mut commands: Commands) {
commands.spawn_with(level).insert(StateScoped(Screen::Playing));
}
the implementation is 100 lines of code and compatible with Commands, ChildBuilder, World, and WorldChildBuilder
have you used a shared trait and GATs for return type?
yes
great, that's more code we can copy for the issue i posted
heh
should i make a PR or not bother
idk where we're at with that rn, just wanted to get this working
I'd say it's either a light 3rd party crate
or possibly an engine feature depending on the API
i should read the example
engine feature in 0.15 for sure
3rd party crate maybe, but then we can't use it in bevy template 😄
unless it's duplicated
did you use a macro for various sized tuples?
what can level take as arguments besides entity world mut
you can split it into Entity and &mut World if you want
gah 💀
but it's only between those two options
the api is just as bad on that side sadly
you can also make it a struct with EntityCommand impl instead of a function ofc
if you want the command to include some data
if a system could be an EntityCommand.. that would be nice
the ideal interface I imagine for load is something like
or like a system taking Entity as its first arg
fn load(entity: EntityCommands, my_assets: Res<MyAssets>, other_stuff: Res<OtherStuff>) { ... }
which we maybe could do with observer piping
aaaaa observers
i think give observers like 1-2 more releases before they're a go-to option tbh
nvm ig you're suggesting adding an upstream feature for observers actually
it can be on top of observers
for commands
you can make a IntoSystem like trait
that takes EntityCommands as first argument
can't use EntityMutWorld with other args
yep. you can pull resources out of it though
yeah, but it's a nasty interface
pub(crate) fn player(mut entity: EntityWorldMut) {
let asset_server = entity.world().resource::<AssetServer>();
entity.insert((
Name::new("Player"),
Player,
SpriteBundle {
texture: asset_server.load("ducky.png"),
transform: Transform::from_scale(Vec3::splat(0.5)),
..Default::default()
},
Velocity::default(),
PhysicalTransform::default(),
StateScoped(Screen::Playing),
));
}
I'm ok making tests with it, but that's not end-user fit
i agree it's not great. but it does work
well yeah, both work
probably will use observer one in my projects
need to get the ecs patches in though
have you checked the issue?
what do you think about the traits? remove some add some?
adding spawn_with is pretty free btw. that part is like 3 lines of code
the 97 lines is impling a bunch of common traits for all the different types
yeah i skimmed the code and got the general idea
i had to consider this exact thing for the issue so i can understand it more than less
or even don't add it, and then a user can add this themselves with 1 extension trait
yeah, cause it's spawn empty + add
yep
instead of spawn empty + insert
it's the generalized version of spawn empty + insert
mhm
kinda canonical tbh
it's the command brother of spawn trigger lol
I'll sit down and crank few of those out tomorrow
Could you take a look at https://github.com/bevyengine/bevy/issues/14205
?
I experimented a little but no internal impl worked for me
maybe you'll have an idea since you are fresh off commands
actually, we can probably use the spawn_empty trick
now that i think about it
get Entity early and pass it down for insertion
added a comment for spawn_with to your ecs issue
reading
it's the same issue as with deferred spawning
just for spawning observers specifically
hmmm
you can do commands.entity(xyz).observe?
i thought it was just app.observe
actually i kinda remember that
love that there are 4 instances of fn observe and it's not a common trait as well
but this is actually, much worse XD
cause if you have EntityCommands and you run .observe this spawns a new entity
now you need to setup how to make both commands available
api fresh out of the oven
the App version doesn't count tbh
cause all App methods return &mut App... I guess?
||maybe they shouldn't||
so the solution is actually very simple
described in the observer issue
wrapper that holds both, the original builder and the new builder
derefs by default to original builder
allows for .with(|builder| { ... }) to run stuff on observer builder
oh
EntityCommands::observe returns the EntityCommands of the target entity.. not the observer
yes hahaha
🐸
the design is very human
im gonna guess all of those were developed independently as needed
there's no way this would "just work" surely
feels like there'd be some edge case
surface level though sure
i mean it's probably fine
you could also have .target() and .observer() to select one explicitly
commands.entity(entity).observe(reaction).observer().insert(xyz)
i would default to the original builder though
probably reasonable
i mean there's a use case for .with still
if you want to do something quickly to the observer, then get back to your target entity command chain
if we can return a proper EntityCommands I'm all down for it, with can be just an extra
but if we decide with is the feature we can take some shortcuts i think?
oh god, yeah it's be have to be something like that
i forgot command has to be in both
well the nice thing about it is
every method this type implements
will immediately resolve it down into an actual EntityCommands
yes but..
that's only for EntityCommands
what if your og builder is App
or World
would { C, E, E } be the GAT?
well not fine but it might be possible
i dont see the need to abstract Entity?
short for Command, Entity, Entity
ok but E is the concrete type or a generic?
concrete
ok then fine yea lol
no generics there
but something like { T, Entity } is generic enough
er
w/e the GAT is depends on the context
oh
T would be the type we're implementing observe on
wait so you're doing like
WithEntity<T> = { T, Entity }
EntityCommands = WithEntity<Commands>
our new type for .observe = WithEntity<WithEntity<Commands>>
and then implement .og_builder() .observer_builder() which can reassemble the WithEntity<T>
do you want to deref to T?
that could be an issue if T impls some methods that you don't want to be calling instead of the WithEntity variant
no, that would be WithEntity<EntityCommands>
oh i know
T: GetCommands
is enough
is EntityBuilder not a WithEntity<Commands>?
layout-wise yes, idea-wise no
EntityBuilder vs EntityCommands?
i misspelled the name, i meant commands 🤡
ahh ok
this will be a bit clearer when we get some of the simpler traits in
the observer one is the hardest
what's your target milestone for this?
or at least some of it
it's a breaking change i assume
as much as i can force Francois to merge for 0.14.1
that is not controversial
insert/remove is pretty controversial
isn't that not possible because it's a breaking change?
you have to have the trait imported in order to use the method
prelude
users don't have to use the prelude
a change xD
some libraries prob don't
well, they don't have to you're right, but that's the intended use case
Alice seems to have agreed on that
not gonna bother her more though, she's taking time off
is 0.14.1 meant to be before the jam or later?
before jam
hmmm
okay. tbh i could put my pr through and we can just delete util/spawn when 0.14.1 lands
in theory
regarding @rigid geyser's PR. i'd prefer if the changes were split into several PRs
some of the changes are uncontroversial.. some are more controversial
and i don't want to have to resolve all of the controversial stuff while the greater PR is looming the entire time, freezing other potential work and its uncontroversial parts
i'm in favor of simplifying, but not necessarily the way the PR does it
you gotta fight him about it, I'd be happy if it just still worked 😅
I'm not sure how high on cart's todo list the template is
ok. i think a practical plan would be to start by taking the uncontroversial changes from cart's PR and reimplementing them as separate PRs, and merging those through
then discuss the controversial bits
and just use cart's PR as a reference instead of actually trying to merge it wholesale
I'm for removing pub(crate) and flattening down the core/util/game
the PR isn't big, it just touches a lot of files and moves things around, so reimplementing should be easy
the rest i have no strong opinion on
i'm for removing pub(crate) and renaming GamePlugin -> AppPlugin
k
as for the flattening... maybe a partial flattening
like only flattening core would be fine ig
flattening util only looks reasonable rn because we only have ui utils atm
we may not have more in the template
so it could be flattened temporarily with the expectation that util may be re-added later
yeah
are we keeping pub(super) fn plugin or does that become pub fn plugin as well?
👍
for sure. prs set to automerge on approve because uncontroversial
also there is jan's refactor pr: https://github.com/TheBevyFlock/bevy-template/pull/78/
okay, fair enough
or, since cart's coflicting now
if Jan rebases onto main I'm fine merging it earlier
alice said remove deflicker
so i'll make a pr for that
for flattening util
thoughts on keeping the top-level folder named util?
and just pouring util/ui/* out into util/
it's either that or ui_utils or w/e which seems like an unnecessary quantification
cart also took a lot of the core for flattening
yeah i will flatten core in a separate PR imo
ok
@agile dirge resolved comment
okay sleep fr this time