#bevy_new_2d
1 messages ยท Page 2 of 1
Thanks ๐
there doesn't seem to be an easy way to run cargo update from a rhai script
Really? Not even just running a CLI command raw?
At least that can be fixed with bevy new
i didn't do too much digging. i asked chatgpt because i'm not reading the entire rhai book ๐ญ
i didn't find anything by searching the rhai book for related keywords
it seems to be intentionally unsupported for sandboxing purposes, but i don't have a source for that
it may be possible to go through a rhai -> rust interface to get around the limitation. that would be a not-easy way to do it :p
Welp, telling people to run the magic command is not that bad
that's also true
probably worth adding that to the README until a better solution exists at least
Or remove the locked modifier from CI and donโt generate a lockfile
Agreed
But thatโs a bit dangerous imo
yeah --locked is good for stability
Just place it where we say cargo branch --move main or something like that
oh just realized also
the two commands we have there
it's missing a cd <directory> in between
though that's not what it's called in powershell :p
cd is a valid alias
(It will just lint against it in scripts)
ah
"How dare you not use Set-Location???"
But it will also lint against your own functions not starting with a blessed verb like Set, Move, Get, Run, etc.
No "CalculateFoo" allowed
๐
Powershell's linter really has some opinions
reminds me of go's formatter
i worded it to avoid cd anyways
But that does not do cargo update -p your_project
Which means they get a different lockfile
Yeah, for all dependencies
we could suggest cargo update -p your_project but that's a longer command and the user would have to substitute their project name there, so they can't copy/paste
and cargo update accomplishes the same goal of fixing the Cargo.lock file. it just also updates dependencies
Hmm, alright. I'm just worries because I have seen stuff break post cargo update before
like semver-incompatible update?
Using our lockfile at least guarantees that the template works
Yep
I mean, as in someone didnโt follow semver
And cargo update ended up breaking my build or runtime
but in principle you're right
Which is nasty to fix
Oh, right
I assume those should be safe, otherwise itโs a Bevy-wide problem
Then cargo update is fine, youโve convinced me
That means we can remove our lockfile from the generated files
that's true
should we?
i think keeping it for the main branch makes sense (well, it's necessary for CI actually)
I think I prefer the terseness of having the cd in there
But thatโs alright
Agreed, we can just exclude it in the cargo generate settings
yeah
and/or remove it from the branch
at some point i believe we want to merge the cargo-generate branch into main
at which point we'd want to keep it in the template but exclude it from being copied on generate so yeah
We have that issue about only supporting cargo-generate, that has some intersection
i just don't understand how all the other cargo-generate template maintainers write code without rust-analyzer
Actually, reading it again, I think a new user could interpret the wording as "in the this newly generated dir that we are already in after running cargo-generate"
Yeah it seems a bit whack
adjusted wording
Approved
thanks
Since we're on the topic -- with a fresh Cargo.lock, my CI no longer fails here; but later doctest fails in src/audio.rs because there is a
/// use bevy_quickstart::audio::Music
which probably needs to become
/// use your_project::audio::Music
(or maybe use self::Music is a thing?)
Ah, never mind, thanks for fixing it (https://github.com/TheBevyFlock/bevy_quickstart/issues/300) ๐
yep ๐
doctests are compiled as though they're in a separate crate i believe, so self or crate wouldn't work
i haven't tried self though, only crate
I'm currently doing a complete rework of Foxtrot based on bevy_quickstart (#1124043933886976171 message) and thought we could maybe have a section in the template for derivatives
We could list foxtrot and pyri_template there
What do you think?
yeah that sounds good to me. pyri_template isn't ready yet but it can go there when it is
i found an approach for main-branch-only that works: https://github.com/TheBevyFlock/bevy_new/pull/11
(this is a PR to bevy_new as a proof-of-concept)
this means that every templated file will have 2 copies that should be kept in sync, instead of the entire repo having 2 branches that should be kept in sync
it also means that "normal" CI / CD workflows should continue to work, but a ci-generate.yaml workflow would still be good to have to make sure that generated repos have passing CI as well
and that the cargo-generate command works at all
and we shouldn't have too many templated files. mainly the CI/CD workflows and putting the project name in a few places (Cargo.toml, index.html, src/main.rs, doctests)
as for running cargo update -p {{project-name}} and other commands in a post-generate hook, that is actually possible. @stable cloud found that Rhai can do this:
system::command("cargo", ["update", "--project", variable::get("project-name")]);
Wow, thatโs super nice to hear!
i ran cargo generate -ap path/to/local/bevy_quickstart to test and it spent like 20 seconds loading up ~9.5GB of RAM before asking me for project name
weird
oh.. so cargo-generate seems to load the entire template into RAM before doing any templating or committing it to disk
and my local bevy_quickstart has a 9GB target dir ๐คช
which we're not explicitly ignoring because the github source doesn't have that
maybe we want to add an ignore = ["target"] for local cargo-generate testing purposes
actually, this doesn't help. it still loads everything into RAM, it just won't copy the target dir to the new repo
i mean that's still nice but it only solves half the problem
if my target dir is 32 GB that's gg to my system ๐
but like idk. what if hypothetically there is a template with 20 GB of assets? cargo-generate will load it all into RAM and force you to restart your pc?
i would have expected it to clone to disk and work there
made an upstream issue: https://github.com/cargo-generate/cargo-generate/issues/1275
cargo-generate clones hard links as separate files 
so they end up taking more space in the generated repo than the template
target directory has a bunch of hard links in it, which makes the problem worse
anyways that's enough yak shaving. working on a bevy_quickstart PR like this one so we can remove the cargo-generate branch
๐ ฑ๏ธrilliant
Even ๐ ฑ๏ธriallianterer
much appreciated ๐
Related to #288.
Remaining tasks after this:
Delete cargo-generate branch
Delete cargo-generate.yaml workflow
Remove manual clone instructions from README.md
Remove "GitHub template&a...
Ooo nice! I'm definitely excited about that.
This is a followup to #305.
After this, ci-generate.yaml is the only remaining task. That needs a little more time to cook in https://github.com/TheBevyFlock/bevy_new_minimal first.
this thread should probably be renamed to bevy_new_2d as well
bevy_new_2d
nice!
Ah this is where quickstart went! ๐
There is an issue with trunk serve on windows and IPv6. I think the Trunk.toml file needs to be updated but not sure what impact this will have on other platforms
# Use IPv4 first - prevents errors on Windows
addresses = ["127.0.0.1", "::1"]
The error is
ERROR error opening browser error=Custom { kind: Other, error: "Launcher "cmd" "/c" "start" "" "http://::1:8080/" failed with ExitStatus(ExitStatus(1))" }
Created a PR https://github.com/TheBevyFlock/bevy_new_2d/pull/311
I'm sure y'all know this but I think the widgets approach in this template will need a reboot for 0.15 #general message
That's odd, when did Spawn trait land?
I was leading the issue for extracting those traits and I've seen no progress since
ah, the template defines one..
yep its a template thing not a bevy thing
I did not know that! Thanks for the heads-up
trying to update bevy_new_2d to 0.15.0-rc.1, there's a fun breaking change
fn spawn on the struct ChildBuilder was moved to the trait ChildBuild
so now in method resolution, child_builder.spawn doesn't know if we mean ChildBuild::spawn or Spawn::spawn
because they're both trait methods
whereas before, it was unambiguously ChildBuilder::spawn because that was an inherent method
oh, uh I'll stop working on that then ๐
hello, trying to publish WASM on Itch with CD release.yaml, always getting this browser error message after deploy:
Encountered HTTP status 403 when loading asset
when I build wasm target in my local machine is working well
have you followed all steps in: https://github.com/TheBevyFlock/bevy_new_2d/blob/main/docs/workflows.md#cd-releasing ?
(on itch's CDN, missing files are served with HTTP 403 Forbidden instead of HTTP 404 Not Found, so the underlying problem should be "assets are missing")
I think so, indeed my Itch page has the download buttons for Mac, Linux & Windows versions and are working well
on where is the task in release.yaml that is doing the job with Trunk?
@tacit verge do you think that can be related with same problem of app ID? https://github.com/TheBevyFlock/bevy_new_2d/issues/316
add some screenshots that may help
You could download the zip from itch and inspect it / verify it works with a local web server
this seems different
downloading the web zip from itch and checking if there are any obvious issues would be good
also make sure you have AssetMetaCheck::Never: https://github.com/TheBevyFlock/bevy_new_2d/blob/77363f452205512ef8e9a0648b0bce5fbe3abf64/src/lib.rs#L35
ok, I'll try it
I must write these lines too? https://github.com/TheBevyFlock/bevy_new_2d/blob/77363f452205512ef8e9a0648b0bce5fbe3abf64/src/lib.rs#L41
artifact downloaded and working fine from local server
if you don't have AssetMetaCheck::Never, you definitely need that for itch
ok, doing right now
for it to work with the html / css included with the template, yes
otherwise, not necessarily
awesome!! it works!! thank you so much @mortal breach @tacit verge
last question, if my window game size is 800x860px and I've defined in web/index.html this canvas dimensions:
<canvas id="bevy" width="800" height="860">
I must set something else in Itch config page?
yeah i believe this will be controlled by itch ultimately
an example where it's set to 1280x720
Oh so we need to make the repo public and then we'd be able to rebuild?
public repos get infinite free ci
for private repos i'm not 100% how it works personally
it seems the free github plan includes 2000 (private repo) ci minutes per month
thanks for your help, again @tacit verge ๐
bevy 0.15 update PR: https://github.com/TheBevyFlock/bevy_new_2d/pull/318
oh, I keep forgetting I'm not on the "approval means mergeable" list for that repo lol
yeah, you could probably be added but i think i shouldn't do that unilaterally
hm i don't get this CI failure:
/tmp/rustdoctestv64gum/rust_out: error while loading shared libraries: libstd-ca74a2d9c5166d9f.so: cannot open shared object file: No such file or directory
oh hey, I just hit that in an unrelated crate, doing cargo test --doc --all-features
failures:
---- src/lib.rs - (line 200) stdout ----
Test executable failed (exit status: 127).
stderr:
/tmp/rustdoctesthdW3dm/rust_out: error while loading shared libraries: libstd-bd6705db1e77d5f2.so: cannot open shared object file: No such file or directory
wonder if rust nightly is doing something interesting
BTW I just realized that the template is still titled "Bevy Quickstart" on the assets page for Bevy.
right, that should be changed
the description will probably become outdated-ish too
since it's not worked on by the bevy jam working group anymore, and it's meant to be the official 2d template at some point, not specific to bevy jams
I figured, which is mostly why I brought it up here as a heads up because I just happened to notice it while looking over some other things on the asset page.
i merged https://github.com/TheBevyFlock/bevy_new_2d/pull/312 and updated some issues. we should look at the Bevy Jam 6 milestone issues and try to get through everything (fix or relabel to the next milestone) before the upcoming jam in a few weeks
easy pr needs review: https://github.com/TheBevyFlock/bevy_new_2d/pull/335
and another small one: https://github.com/TheBevyFlock/bevy_new_2d/pull/336
another small one: https://github.com/TheBevyFlock/bevy_new_2d/pull/338
and a PR to update to bevy 0.16 rc: https://github.com/TheBevyFlock/bevy_new_2d/pull/339
thanks for the reviews @finite depot :)
you're very welcome, been a while ๐
yep, i know you've been busy
It's funny, I just updated my own "instance" of bevy_new_2d to the 0.16 RC yesterday for my MSc. stuff and here you go updating the template itself the following day
Great timing, now I can change my guesswork to your better update ๐
hehe
i moved some issues to the Bevy Jam 7 milestone (the non-critical / controversial / hard ones)
there are 11 unblocked open issues remaining in the Bevy Jam 6 milestone, with a PR ready for 1 of them
just noticed we're still using a custom OnPress component + observers for button interaction instead of the new bevy_picking stuff, i'll make a PR for that :)
nice to be able to simplify the template a little bit
hopefully we can remove the Widgets and Spawn Commands patterns for bevy jam 7 ๐
Bit out of the loop here; how could we do that?
well we can't currently, the upcoming jam is number 6
i'm hoping we get some good ui/bsn features by bevy 0.18
Aah gotcha
looking for opinions regarding https://github.com/TheBevyFlock/bevy_new_2d/issues/332
the video was a useful resource at the time, and could still be useful now
but it may also cause confusion as many things have changed since then (including the name of the template)
should the video be removed, or should a disclaimer be added?
I'm tending towards remove, as stuff changed quite a lot. What do you think, @trim zealot ?
if y'all feel like the video no longer represents the project feel free to remove it. I was asked by the cli working group to prepare a video for their next release (which would be 0.2) so I'm still producing these kind of videos if y'all think an updated one would be useful for the next jam.
The linked issue re: install not working is fixable by mirroring main to that branch in the repo; GitHub already redirects from the old repo to the new rename. I understand not wanting to maintain backwards compatibility like that but breaking the install instructions was definitely a preventable situation too.
I think an updated one would be supremely cool, if it's not too much trouble ๐
no trouble at all. Give me a heads up when the repo is in a state that's stable and you want shown for the 0.16 game jam and I'll make a video. Assuming this will be relatively soon after the stable release but just lmk and I'm happy to do it.
btw i noticed the bevy_new_2d CI has started clean-compiling and taking 14 minutes instead of 1 minute
i'm not sure what the cause is. i have noticed that clean compiles are always followed by an "empty" cargo cache sweep, and iterative compiles are always followed by pretty big cache sweeps
which could be a red herring
@tranquil breach thoughts on this theory? cargo-sweep checks if a cache-restored file was accessed during a workflow job by comparing its atime to an earlier timestamp, so it's possible that many files are incorrectly deleted because their atime doesn't get updated (see https://unix.stackexchange.com/a/8842 )
btw the change to the release workflow is still not working. i'm gonna iterate on it in a separate repo and come back with a pr that actually fixes it
Very out of the loop for this one, but it looks like bevy_enhanced_input is more likely to be upstreamed?
Damn @foggy relic that was quick, I didn't even ping you ๐
I'm procrastinating release notes!
Iโll definitely have to test this, as Iโve been noticing some things get incorrectly deleted by cargo-sweep too, thanks for calling it to my attention!
release workflow is working again ๐
PR to update the Bevy Assets entry: https://github.com/bevyengine/bevy-assets/pull/510
i noticed that generating a new project with bevy_new_2d brings in the three license files (MIT, Apache, CC0)
whereas bevy_new_minimal ignores those files
wondering which behavior should be preferred
on the one hand, we don't want to add license files to the user's new project that they don't actually want to release their project under
on the other hand, it's easier for the user to delete files than to add them
thanks for fixing it ๐
i'm leaning we shouldn't include the license files by default, unless we add cargo-generate prompts for the user to choose which common license(s) they want
we probably shouldn't include docs/ or README.md either
Fully agreed. Although for users who have just heard about bevy new 2d and may not even know about the repo, a link in a README could be useful. So they know where they can go to learn more about e.g. the workflows.
hm i see what you mean, if you know about the command but not the repo where the documentation is
i can add a README.md.template
Exactly, I see that happening once the Bevy CLI is official
Maybe just
# <the project name>
This project was generated with `bevy new 2d`. Visit its [GitHub repo](https://github.com/TheBevyFlock/bevy_new_2d/) to learn about blablabla
(any clue why the markdown syntax highlighting made the green? ๐)
html tag probably
oooh right!
I know this was rejected before, but I'd like to revisit the idea of using pub(crate) instead of pub. When we have a lib.rs, clippy cannot detect dead code as easily. I just ran into this while adapting the template for a project. In level.rs...
pub fn spawn_level(world: &mut World) {
// The only thing we have in our level is a player,
// but add things like walls etc. here.
SpawnPlayer { max_speed: 400.0 }.apply(world);
}
... I removed the SpawnPlayer because I replaced it with loading some map data from disk. To my surprise, cargo clippy doesn't have anything to say about this. I then changed:
// player.rs
/// A command to spawn the player character.
#[derive(Debug)]
pub struct SpawnPlayer {
/// See [`MovementController::max_speed`].
pub max_speed: f32,
}
to pub(crate) and I get 3 warnings about never used types and methods.
i'd still consider this a clippy issue, but i see your point that it would provide value to users of the template now
@tacit verge do you think you could find some time for a code review? I want to rework Foxtrot into something resembling a 3D version of bevy_new_2d with external libraries on this branch in time for the jam. It's still WIP, but the first person controls are implemented. Still need to add an NPC, dialog, pathfinding, and particles. And docs, of course.
Most code that differs from bevy_new_2d is in the demo dir. In particular, I'd like some input on the player subdirectory. I especially dislike the render layers floating around, but I'm not sure where to nicely tuck them away.
sure, i'll take a look
With the latest Bevy CLI version, we don't need to manually pass --no-default-features for web and release builds anymore.
PR here: https://github.com/TheBevyFlock/bevy_new_2d/pull/357
heck yeah!
i'm going to go ahead and assume that unsafe is a no-go for bevy_new_2d ๐ญ
you need an unsafe impl Bundle for MyType to create your own BundleEffect, e.g. for adding an observer to your entity
so we can't use fn() -> impl Bundle for entities that are buttons or have buttons as descendants
and it would probably be confusing to mix and match entity spawning design patterns
so no fn() -> impl Bundle in bevy_new_2d ๐ฅฒ
Oh heck, thatโs really unfortunate
BTW I went ahead and commented some stuff in #333 -- the Support JetBrains IDEs better issue. I also opened a draft PR to kinda show how this would work.
TL;DR it should be possible to add in some default build configurations like how vscode does.
Oh thatโs good news ๐
Yeah, there are several questions that should probably be answered regarding how it's implemented, but at least it's possible ๐
i'd be happy to get the support in first and work out the rest later fwiw
either way
what are the contents of the default .idea/.gitignore?
also, what's the issue with shell commands? is the output format affected?
# Default ignored files
/shelf/
/workspace.xml
# Editor-based HTTP Client requests
/httpRequests/
# Datasource local storage ignored files
/dataSources/
/dataSources.local.xml
well that's pretty brief so it would be reasonable enough to include, ofc that means if they change it upstream we'd want to change it in the template too which is awkward
Yeah. The issue is some of these files (like workspace.xml) is literally just configuration of your current environment. So tabs opened and stuff.
right, it would probably be pretty annoying for a user to accidentally check that in to the repo
i imagine this .gitignore file doesn't change very often
This is autogenerated whenever you first open a project in RustRover, and doesn't seem to ever be regenerated AFAIK. So it probably shouldn't change much.
seems the maintenance cost would be low and the UX benefit would be high then, so i'm in favor of including the .gitignore
As for the issue with Shell Commands over the default cargo runners and stuff, has to do with some integration. (Such as easily switching what toolchain you're using via editing the configuration. Or being able to quickly change the build profile (dev, release, test, bench)).
Cargo will use the build tab for showing information regarding the build, which provides a slightly nicer UI with regards to build errors. If we use shell commands we can either have it execute in the IDE's Terminal, or not. If we do the former, you can easily click on where errors are, but it opens up a terminal whenever you run a command, which probably isn't a big issue. If you don't put it in the terminal then you don't really get any of that.
FWIW since the goal is to provide decent defaults, I think going with the shell commands is fine enough, and if someone really wants to use the cargo commands, they probably have some ideas of how to use it.
ic
It might be possible to get that working with the shell commands, but I'm not quiet certain.
bevy CLI also supports a --verbose tag to see which commands it runs, so a user could use that to find the proper cargo commands
in VS Code, both "shell" and "cargo" commands have the same structured formatting because it's parsed from the output, so the decision to use bevy run for VS Code tasks was made in that context
Yeah. Looking into it, part of that niciety is because the cargo Configuration by default has a "Before Launch - Build" which runs a build of the project generally before running it. This isn't possible with the Shell scripts though.
i'd probably lean towards cargo commands for jetbrains ides if the UX is better that way
fully unifying under bevy CLI is a nice ideal but it's not that important
The UX is a bit better, but if we go with the options running in the terminal then it should be fine. That would preserve the ability to click on where an error is and the IDE will jump to it.
The only thing that's lost through not using the cargo commands is that build option, which while nice is also manually trigerable. (Build will also automagically take you to where an error is, but again that's also manually triggerable)
The only downside to running it in the terminal, is that to cancel it you have to cancel it in the terminal.
All right so we'd probably need to use some shell stuff anyways, so it might just be better to use the shell commands for now, at least for the web stuff since we'd also need to run wasm bind-gen and the like.
if we wanted to we could have the best of both worlds by making a plugin for RustRover /jk
At the very least, what I have in the PR now will work, and going with it might be the best idea in the short term to get something in there for the Jam.
I'm also not 100% on grouping the build stuff in a folder/group, but if someone doesn't like it they can always change it pretty easily.
There is actually a slight issue with the terminal commands. I can't seem to use the RustRover debugger. So we might want to provide at least one cargo run configuration to allow debugging.I'm not sure how debugging web builds would work though tbqh.
So how does the plugin snippet work?
All right so bad news regardings the snippets:
It is possible to have it in RustRover, the only downside is they are global, so can't be shared per-project.
There's a plugin that, theoretically, would allow this to work but it hasn't been updated to the latest version of the IDEs, and I'm not sure when it will be.
The Plugin is Open Source, I just don't have the knowledge to maintain it, but I could potentially update it.
Without the Plugin the best way to share it is for me to port them to RustRover, then export my settings and only export those Templates. Which can then be downloaded and imported to work.
BTW I've gone ahead and created the live templates for Rust Rover even though it's not the easist thing to share for the time being (that is, it's a zip file)
i think it's fine if there isn't full feature parity in support for the two ides
Fair enough. If you want we can provide information on how to (briefly) setup the snippets (mostly linking to the documentation) and the like or provide my zip file if they want to try and use them. However fwiw I didn't even know RustRover had that feature, and it has several useful templates/snippets built in.
we could put that in the docs/tooling.md ๐
Cool. It's actually fairly simple to setup, and it's mostly 1:1 with the VSCode Snippets
nice
The main difference is Live Templates require you to set the context they work in.
The plugin live template in RustRover is:
use bevy::prelude::*;
pub(super) fn plugin(app: &mut App) {
$END$
}
and is set to only work in rust modules.
The component live template in RustRover is:
#[derive(Component, Reflect, Debug)]
#[reflect(Component)]
struct $NAME$;
And is set to work in modules, statements, and expressions.
i'm merging your PR now
All right. Do you want me to add in a cargo build really quick so we could at least have a native way to debug in RustRover or should I do that seperately?
That's absolutely fair.
So how do you want me to do the section in tooling on the Live Templates?
Iirc there's some writing on recommended plugins for vs code in there, unless that was changed
So it could go in that section
Well I imagine it would be it's own section for Rustrover, no?
Right but same general area since it's about editor tooling whereas the first part is about crates
Ah all right.
i've started taking a look at foxtrot and its code, figured it would be most efficient to provide feedback in PR form. started with an initial style pass but i'll try to get around to some less surface-level review tomorrow
Oh thank you so much! Really appreciate it ๐
I won't push anything onto main until it's done so you don't get any merge conflict
I can do some level design until then
ok, i'll try and update to main real quick to unblock the pr
done, the merge conflict was a deleted comment
good to merge this pr and i can make more later, which most likely won't touch as many files
merged ๐
Maybe I should add module level comments now so that reviewing is easier
So I've gotten a way to fix debugging with dynamic linking on RustRover, downside is that it's not generalizable. IE: I don't think we can, necessarily, do anything about it or set it up.
I'm currently doing some testing on Windows to try and figure out the magic incantation for Windows on RustRover to get the same results, this way we can at least include it in documentation.
Thx for doing the research ๐
Figured out windows. TL;DR it's largely the same as the way you do it on linux. The main exception is that you use PATH instead of LD_LIBRARY_PATH
@fervent locust you may be interested in this
I imagine on OSX/MacOS it would be the same as linux, using LD_LIBRARY_PATH, or you could also probably use DYLD_LIBRARY_PATH or DYLD_FALLBACK_LIBRARY_PATH
If Jetbrains fixed things so you could actually use Path Variables when setting Environment Variables for Cargo Run Configurations it would definitely help
@tacit verge I think your latest PR made the Widgets section of the design docs outdated FYI
@fierce jewel dunno if you knew this, but the CI uses LD_LIBRARY_PATH="$(rustc --print target-libdir)"
might be useful for what you're doing ๐
That...might be very useful
๐
ahh right i forgot to update that
oh right i remember adding that specifically for a weird dynamic linking + doc tests issue
this is likely related
It is related, unfortunately (at least on windows) that does not work.
$(rustc --print target-libdir) does not actually get evaulated.
Also do you just want me to turn the Live Templates section into a more generic RustRover section with subsections for Live Templates and Environment Variables, or just have a separate section on debugging in RustRover with Dynamic Linking?
is windows using powershell instead of bash or something?
AFAIK windows by default uses powershell and cmd.exe. But in RR I do not know what it's using to run the executable and set environment variables, although it might be cmd.exe
Keep in mind RR might be directly executing the program using a system call, like what std::process::Command does, so it might sidestep both cmd.exe and Powershell
It's tricky, and something you can really only figure out through testing ^^
Yeah
But yeah. RustRover (and all JetBrains IDEs in general) have built-in functionality to deal with things that will change from computer to computer but might be needed in things like RunCommands. The issue is, is that the functionality is partially broken it seems. >w>
good news: we can add observers with fn() -> impl Bundle thanks to #ui message
it requires a very small amount of "code that's patching something that should be provided by bevy", and no unsafe
i'll get a PR up in a sec
i don't love that mod audio is public only so that its doc tests compile
doc tests having the visibility of a consumer of the library makes no sense for internal documentation
there is no good solution and it's not being worked on or even discussed, though ๐
Yeah I just removed those docs in question in Foxtrot, haha
btw, upstream plz
i might make a tiny 3rd-party crate with this that should hopefully become obsolete in 0.17
released v0.1.0-rc.1 of bevy_spawn_observer
it's like a verbose version of the old bevy_mod_picking API:
// bevy 0.16 + bevy_spawn_observer + bevy_picking
Children::spawn(SpawnObserver::new(|_: Trigger<Pointer<Click>>| { ... }))
// bevy_mod_picking
On::<Pointer<Click>>::run(|| { ... })
@tacit verge what are your thoughts on implementing pausing and a settings menu the bevy_new_2d way?
Just implementing the settings is easy, organizationally speaking: add a new screen called Settings, treat it like the credits screen, done
Just implementing pausing is also fairly simple: create two substates of Screen::Gameplay called GameplayScreen::Playing and GameplayScreen::Pause, then run most logic only in the former
Draw the pause UI when in the Pause substate, done
Cool, but I'd like to have a settings menu in both the title screen and the pause screen
So sending me from GameplayScreen::Pause directly to Screen::Settings wouldn't be good, as that would reset the game
I could just create a GameplayPauseScreen substate for GameplayScreen::Pause with a variant called GameplayPauseScreen::Settings that duplicates the content of Screen::Settings with the exception of proceeding back into the pause screen or gameplay instead of the main menu
but that feels a bit roundabout and boilerplatey, doesn't it?
Hope I'm illustrating my throughts clearly, otherwise I could make some diagrams of what I mean
That was design question A, now design question B
We currently preload all assets at the start, but shouldn't they be conditional on the level?
The sand level might need totally different assets than the forest level, and we don't really want to load them all at the start of the game
wouldn't it make more sense to preload stuff once we want to start the actual level?
This ofc opens the design problem of "Level A requires loading prop B, which itself loads textures C and D, and sounds D, E, and F"
My first approach prototyping something like that looked like
#[derive(Resource, Asset, Reflect)]
struct Level {
#[dependency]
prop_a: PropAAssets,
#[dependency]
prop_b: PropBAssets,
#[dependency]
prop_c: PropCAssets,
#[dependency]
prop_d: PropDAssets,
}
// This is located in another file
#[derive(Resource, Asset, Reflect)]
struct PropAAssets {
#[dependency]
model: Handle<Scene>,
}
// impl FromWorld for PropAAssets boilerplate goes here
// Repeat for all props
but that quickly started feeling a bit silly once I got a dozen props
Then I switched to
#[derive(Resource, Asset, TypePath)]
struct LevelAssets {
#[dependency]
pub(crate) level: Handle<Scene>,
#[dependency]
pub(crate) props: Vec<UntypedHandle>,
}
This is wayyyy more concise, but does not deal well with nested dependencies -> prop C cannot easily depend of things on its own
So I did this silly implementation:
impl FromWorld for LevelAssets {
fn from_world(world: &mut World) -> Self {
let assets = world.resource::<AssetServer>();
Self {
props: [
Chair::scene_path(),
Table::scene_path(),
Grate::scene_path(),
Bookshelf::scene_path(),
LampSitting::scene_path(),
Crate::scene_path(),
]
.into_iter()
.map(|path| assets.load::<Scene>(path).untyped())
// BurningLogs has subdependencies
.chain(BurningLogs::preload(assets))
.collect(),
}
}
}
Here, BurningLogs brings in a preload function that returns the assets it needs:
impl BurningLogs {
pub(crate) fn preload(asset_server: &AssetServer) -> Vec<UntypedHandle> {
vec![
asset_server
.load::<Scene>(BurningLogs::scene_path())
.untyped(),
asset_server.load::<Image>(TEXTURE_PATH).untyped(),
asset_server.load::<AudioSource>(SOUND_PATH).untyped(),
]
}
}
This works, but looks very out of place when compared with the rest of the template, and frankly feels a bit ugly as well
So am I really stuck with this boilerplate in the end?
If so: how do I actually access the prop's assets? I need to somehow access the handle in the hand. I cannot really get it from Res<LevelAssets> as I'd like to have multiple levels, so I don't want to query a specific one in the logic for e.g. fn animate_flower(). That flower shouldn't need to care what level she's in IMO
Right now, I just solve this with a constant called TEXTURE_PATH etc, as you can see above, which I can then load at runtime with the asset server. That again works, but it is entirely contrary to how we're doing asset loading so far, as our current approach calls the asset server a single time when setting up the resource and then always just fetches the Handle that is already present in the asset resource.
I could of course just insert PropAAssets, PropBAssets, etc. into the world after the level loads, but then they stick around until I close the program. However, they should be dropped when the level that uses them is dropped, imo.
So I could make a shallow copy of them and insert those. But then we have "zombie resources" laying around after exiting the level, all holding invalid handles.
Or, the level removes them all when it is dropped, but that sounds like even more boilerplate and cannot be handled by like a simple for. When you add a prop_z to your level, you better remember to manually add it to the cleanup step as well when dropping the level!
This file here is a good example of my struggles. No clue how to cleanly preload that. Again, the current approach I use works, it's just very different from the rest of the preloading code.
Oh, and I'd like to hear @lunar valve's opinion as well
state stack would be the clean way to do this. lacking that, this can instead be modeled as orthogonal state types. enum Screen for the major screens, Paused(bool) as a substate of Screen::Gameplay to pause and display a popup pause menu, and an orthogonal enum SettingsMenu { None, Main, Audio, Graphics } for navigating a settings menu that covers the whole screen
is SettingsMenu a resource?
a state type
Aaah okay ๐
i say "state type" to be unambiguous
because SettingsMenu::Main is the state, SettingsMenu is the state type
Makes sense
So when we start the level, we are in Screen::Gameplay and the substate Paused(false)?
yep, and SettingsMenu::None as well
Got it
and then when we hit escape, we can enter Paused(true) and SettingsMenu::Main?
we enter Paused(true) and still SettingsMenu::None
and there will be a "Settings" button in the popup pause menu
Oh right, because we still need to click on "Settings"
yep
And e.g. have some logic that checks whether we are in the main menu or the pause menu and style the settings menu differently
oh i figured it would be styled the same for simplicity
Because in-game we might want to keep the background a bit transparent
Although I guess in the main menu, the background could be transparent as well ๐คทโโ๏ธ
Alright, thanks, that answers my first question quite clearly ๐
ok time to read some more
yes, preloading all assets at startup is the simplest approach and it works well for certain types of games (especially jam games), until you need something more sophisticated
honestly i don't know the best practice for asset management, i feel like it's in a weird place right now
Do you think it could make sense to just yeet the FooAssets approach and use good old const TEXTURE_PATH: &str = "assets/foo.gltf";?
At least, that's the only way I could figure out in the BurningLogs example
And then let all asset requiring types have a preload function that returns a Vec<UntypedHandle>
Maybe not for bevy_new_2d specifically, but generally for me as a user of the template that want to split assets by level
agreed that this is no issue at all for jams, sure
Maybe not even for most games, period. 200 MiB of RAM or so is not much to pay
Although asset preloading can take a sweet time on Wasm IME
this is true. what i do in my game is i start the preloading on startup, but i don't wait for assets to fully load before showing the splash screen or even the title screen
and then when you click "Play", if the assets are still not done loading, it'll show you a loading screen. otherwise, it'll skip the loading screen
this gives the assets just a little longer to load in the background
whereas bevy_new_2d does the same thing but goes splash -> loading -> title, with unconditional loading screen even if it's only for 1 frame
3d games tend to load a lot more assets than 2d games, but either way i'd be more concerned with reducing user-facing loading time than RAM usage (at least as a first improvement)
also a loading bar, which bevy_new_2d does not have yet, would improve the UX of waiting :p
yeah makes sense
@trim zealot I think those are valid points you raise on the SpawnObserver PR. The version with SpawnWith doesn't look too bad until we can upstream something
Also personally I'm not concerned about the ergonomics of fn button() itself, but moreso about the viral loss of ergonomics for any entity that has a button as a descendant. So SpawnWith is totally fine because you still return a bundle that includes an observer
If the assets are loaded, cant we just use the asset path to get it and skip the loading stage?
I don't quite understand. Do you mean skip preloading entirely?
Or just remove the loading state?
You can store strong handles in one resource
And use raw path in systems that need those resources
Since they're already loaded you'll just create new strong handles
Without additional loading
BTW just as a note I intend to try and get the docs together for RustRover by this weekend.
thx! Let me know if I should download it again to test them out ๐
@tacit verge I just realized that we removed the design docs for spawner commands, but the level and player very much still do use that pattern 
I think it would be best to either replace it with a bundle or add the pattern back into the docs
Then of course we'd need to say "use the bundle pattern when A, and use the spawn command pattern when B"
I'm not sure which path is best
Will do! It would be useful if someone less familiar with RR did try out the documentation. I also can't help but wonder if this documentation should exist somewhere other than just bevy_new_2d, but that can be discussed later.
Ah, also ping @fervent locust when you're done. RustRover is his main Rust IDE, so he's also a good Guinea Pig for this
Will do!
I'm also going to be checking some of this against Intellij IDEA Ultimate and CLion to see if there's any meaningful differences or things to know when using the Rust Plugin with those IDEs.
Got something mayyyybe controversial: https://github.com/TheBevyFlock/bevy_new_2d/pull/374
Oh, right. They also access resources so the bundle approach is awkward. I'll take a look at this later
Also should my RustRover documentation on debugging be in 362 (The one adding the Cargo Run Config), or should it be a separate PR?
separate plz
ping me if you need a review in 362
Will do!
i'm just gonna pass the system params down the hierarchy as args
i think this is the simplest solution for now
it's not that bad imo (it works, it's just "annoying")
idk if eventually adding a settings menu was controversial (i might not remember)
i'll pick at the code a bit before approving though
Yeah, some people said that a settings menu is Bevy examples and not template territory
ah ok, i would disagree with them then, every game should have a settings menu unless it's more of an artistic experience than a game, in which case they can delete settings.rs
it's (at least) as fundamental as a title screen
i'd consider something to be example territory if it would be useful for some but not all games, or showcases a specific bevy feature
as a potential user of the template for jams I'd def welcome a settings with volume control. It's very nice QoL in a jam entry
As said in my PR, I think a settings menu is non-negotiable if we want to be accessible by default
@finite depot suppose gameplay screen had a HUD with some UI
we'd want a fn spawn_gameplay_screen() { ... } system in gameplay.rs
we'd probably want that system to call commands.spawn(level(...)) in addition to spawning the HUD
so it would have to pass dependencies down
either that or we have two systems gameplay::spawn_gameplay_screen and level::spawn_level both added to OnEnter(Screen::Gameplay)
can i add like a tiny HUD to justify the design? ๐ญ
like it could say Level 1 at the top of the window for example
Why wouldnโt you want two systems?
just seems like spawn_gameplay_screen should be the one to control what gets spawned
if it wants to spawn a HUD or a level or whatever
lol
Let me brood on this for a while
there's no correct design TM ofc
I'm tending toward this being the cleaner / more Bevy-esque option, but let me think some more
I may just be biased against boilerplate
@finite depot @fervent locust if y'all could review the documentation I added here: https://github.com/TheBevyFlock/bevy_new_2d/pull/376 that would be great.
@tacit verge after rolling it around my head a while, I think the cleanest design is to actually run two systems in that case, spawn_level and spawn_hud.
Though I'm ready to give in if someone else jumps in and says otherwise
Iโll try to get to it later today ๐
you're a saint, looking forward to using rust rover! Hope I'll find time to take a look soon, got a lot going on!
That's definitely understandable! Hopefully my instructions are easy enough to understand.
@tacit verge updated my PRs
Ok, I don't fully agree, but it's nbd and I can make that concession for now. Surely in 0.17 there's gonna be an upstream solution for this anyways
I followed them, but my breakpoints are not hitting 
I'm using the default debugger settings:
BTW @fierce jewel I can tell you why the automatic resolution for the LD_LIBRARY_PATH didn't work
it escaped the special symbols:
It doesn't do that on WIndows.
huh
left some comments on the settings pr
Can you copy/paste the LD_LIBRARY_PATH value?
/home/hhh/.rustup/toolchains/nightly-x86_64-unknown-linux-gnu/lib/rustlib/x86_64-unknown-linux-gnu/lib
You also need to add ./target/debug/deps to that as well.
I'm honestly surprised it ran without that.
still same though
I think I may have exported that variable globally
Because I don't want to bother with it ๐
You also need to use the cargo run configuration as well
You can't use the shell scripts
You can add in a new run configuration or use the one from the PR Pyrious merged
oh I see
Is the : correct?
./target/debug/deps:/home/hhh/.rustup/toolchains/nightly-x86_64-unknown-linux-gnu/lib/rustlib/x86_64-unknown-linux-gnu/lib
On Linux, yes
Maybe we can make that part a bit more explicit in the docs
compiling debug now ๐
@fierce jewel break points work now!
๐
Woo. I also found out you can attach the debugger manually in the shell scripts, but it's not great. So there's that.
You run the game, then attach the debugger by going to Run > Attach To Process and then finding the right process. It can then attach.
I feel this should be documented as well, but I'm not quiet sure where.
oh wait, I forgot to remove --no-default-features
Just do that and then rerun it.
Nopes, now getting /home/hhh/git/bevy_new_2d/target/debug/bevy_new_2d: error while loading shared libraries: libstd-bd3f4c5fdfb888bb.so: cannot open shared object file: No such file or directory
I have LD_LIBRARY_PATH set to ./target/debug/deps:/home/hhh/.rustup/toolchains/nightly-x86_64-unknown-linux-gnu/lib/rustlib/x86_64-unknown-linux-gnu/lib
where rustc --print target-libdir prints /home/hhh/.rustup/toolchains/nightly-x86_64-unknown-linux-gnu/lib/rustlib/x86_64-unknown-linux-gnu/lib
Change your channel in the run configuration to nightly
oooh right
Because otherwise it uses the default for the project, which is stable.
same error again
can you copy/paste the LD_LIBRARY_PATH values?
here ^
And you're on Linux?
yep
All right I'm waiting on it to compile on my end
I'm mildly surprised JetBrains doesn't seem to make this automagic considering they have to know IMHO. It's not like they haven't put out several materials regarding RustRover and Bevy
Also thank you for sitting here with me and working through this Jan.
I'm not sure why it's not working...it's working for me when I made those changes...
Can you copy/paste the entire bit that's in Environment Variables? (Not the menu, just the text box next to it)
happy to help ๐
sec
LD_LIBRARY_PATH=./target/debug/deps:/home/hhh/.rustup/toolchains/nightly-x86_64-unknown-linux-gnu/lib/rustlib/x86_64-unknown-linux-gnu/lib
maybe needs "
nope, that wasn't it
If we can't find it out, I'm sure my local code / linux / Rust / overall wizard @hearty cosmos can help tomorrow, if we find the right incantation to motivate them โจ
I did notice there was an extra space, maybe remove that? Aside from that, maybe try switching to stable and see if it works that way?
Because otherwise ours match 1:1, minus the user
all right so I just checked and @finite depot remove the space and try again. when I added in the space it failed.
@tacit verge I addressed your comments
WOW you're right! That's so mean!
Thanks, it works now (on nightly)!
Woo!
I feel I should include a note somewhere in the documentation on that because that is really not intutitive and is super easy to miss.
BTW I think the Web Dev build is broken atm
All right So web dev/release is broken.
It breaks because of line 18-19 in title.rs
#[cfg(not(target_family = "wasm"))] widget::button("Exit", exit_app),
Good catch, fixing that in my PR
Could we add bevy build web to the CI?
All right, and it just happened to break because I wanted to try and see if I could get debugging to work in web (spoiler: I couldn't)
I believe what's happening is that the children! macro does not play nicely with the conditional compilation (I think it's trying to use it as part of the macro?)
I fixed it with:
#[cfg(not(target_family = "wasm"))]
children![
widget::button("Play", enter_gameplay_screen),
widget::button("Credits", enter_credits_screen),
widget::button("Exit", exit_app),
],
#[cfg(target_family = "wasm")]
children![
widget::button("Play", enter_gameplay_screen),
widget::button("Credits", enter_credits_screen),
],
left a few more comments but i'm basically ready to approve
thx!
Oh btw Jan, mind checking out the changes to the docs I just made?
I believe I addressed some of your comments already
done, also added the fix for Wasm
surely there must be a better way, but this at least compiles again
Sure! Could you not force push next time? That makes it easier to review incremental improvements ๐
Ah all right, will do.
I think my two comments are still valid, aren't they?
@tacit verge re: your answer, yeah, I really really want a pause menu with a transparent background
Oh I see what happened. I actually...didn't commit my changes..
oh, the #[cfg] didn't work in children![]?
exactly
All right my changes should be pushed now Jan
๐ maybe we can have it return an empty bundle in wasm
yeah if you know how the macro works internally this error message is what you would expect
that's a big IF though
the cfg ends up inside the Spawn(...) so it has no arguments
Yeah that seems about right
writing an issue now
yeah that's better ๐
Added a little suggestion, otherwise the factual content seems good to me ๐
@tacit verge could you do the style and grammar check?
sure
Added bevy build web to the CI: https://github.com/TheBevyFlock/bevy_new_2d/pull/379
I left tests and doc tests out for now since IME it's enough to just confirm that it even builds on web
@tacit verge bevy test is not a thing, I believe
We could just manually set the compilation target
But there is also something nice about directly using the bevy CLI in the workflow
Added an issue to the CLI https://github.com/TheBevyFlock/bevy_cli/issues/397
ok, sure
resolved your comments
Re: --all-targets, I fully agree! I have already removed that from some workflows in the past, thinking "Oh, I don't want to compile for all targets, that's wasteful". The naming is really really bad in this case!

FWIW I'm just happy I caught that issue with web now, instead of someone mentioning it to us after the jam starts
true
we should trigger a final release workflow before the jam starts though
to test the template on itch.io
i'm gonna take a break and do this later today though
should this say "release"? 
probably not
i noticed in the settings menu when putting the volume very high, we have a second "on hover" sound effect occur on release
I notified the CLI group

it seems it's because we're using the Interaction component instead of observers
it goes back to Interaction::Hovered when it's no longer Interaction::Pressed
why is Pointer<Over> triggered a second time for a button when you hover its text?
is that event bubbling?
๐คทโโ๏ธ sounds weird

So I guess we just leave it as-is for the moment?
yeah.. i'll make a blocked issue
btw we should also only be playing the pressed sfx on click, not on press
so effectively on release
thanks for investigating
what's the difference?
if you hover over a button, press, drag out, and release, it won't activate the button because you canceled your click
Oooh got it
but rn you still get the sfx when you pressed
Yeah, t hat makes sense
that would already work with a Pointer<Click> observer, but i don't want to use an observer for one sfx and a system for the other :p
did an editing pass on the rustrover debugging documentation
once those comments are resolved i'll do a final pass that'll probably just be a few small things. it's a little awkward to continue with all the suggestions breaking up the flow of the text
Thanks Pyrious, I will note I have a very odd writing style, and tend to be a bit more verbose than necessary.
Also thank-you for noting how to specify the channel, I actually had no idea how to do that.
All right I've gone through and updated the documentation based on feedback
ok, i've done my final editing pass now
I've opened https://github.com/TheBevyFlock/bevy_new_2d/pull/381, which may improve our CI caching situation by switching to Swatinem/rust-cache. I can guarantee it works, but it's hard to know if it's faster until we merge it and see how things go
If Swatinem/rust-cache ends up just being better, I may talk with the other maintainers of Leafwing-Studios/cargo-cache about deprecating and archiving it
i found another bug with our buttons
if you hover a button's text, mouse down, move mouse so you're still over the button but not over the text, and mouse up, it won't register as a click
same thing if you start on the button and move to the text
it's easy to verify this with UI debug overlay toggled on by pressing backtick
Dunno how well-known this is, but itch now has a Bevy Engine option for metadata. Updated bevy_new_2d accordingly ๐
great, this has been a thing since december 12th 2024 i think
Rust is an option there too
@finite depot regarding the error here: https://github.com/TheBevyFlock/bevy_new_2d/pull/386#pullrequestreview-2807814388
i'm wondering why you're getting that, it seems to work in the CI that ran on the PR itself
this is the command you're running?
cargo binstall --no-confirm --git=https://github.com/TheBevyFlock/bevy_cli --locked bevy_cli
Yep, only difference is --force because I already have it installed
let me update my binstall, maybe that's the issue
ah ok, it's hitting "already installed" in the CI as well because it's coming from the cache
That would explain why the error does not happen ๐
I also get no error when not running --force
i wonder where it's getting =0.1.0-dev from?
ah right that's in the Cargo.toml of the bevy_cli github repo
it looks like maybe cargo-binstall forgets that you passed a --git argument when it gets to the final "install from source" fallback
it looks for the crates.io version of bevy_cli which is a namesquat bevy reserved crate that only has 0.0.1 released, so it fails
@foggy relic do you want give the template a review before the jam?
Would be nice to have a link to it this time around ๐
Although that is probably already contained within the CLI showcase
I do, but time and health may get in the way ๐
Still sick today :/
Oh sure, I think we all value your well-being more ๐
@finite depot do you know if the windows white flash issue still occurs in bevy 0.16?
I was wondering the same
I haven't noticed it on my end
But that doesn't have to mean it's gone
well the official bevy example we link to that shows how to fix the issue is still in bevy main: https://github.com/bevyengine/bevy/blob/latest/examples/window/window_settings.rs#L31
although we're linking to the bevy 0.14 version of this example
ok i found the upstream issue: https://github.com/bevyengine/bevy/issues/9771
@tacit verge in my comment, I was refering to this: https://necrashter.github.io/bevy-choppy-music-workaround
Using Web Audio API to fix the choppy audio problems on the web builds of Bevy game engine.
I have something about the CLI doing an audio hack for us in mind
don't know if it's exactly this
ah, no, i don't think so
the audio hack is something that every bevy game basically already uses, idk exactly what that's for
the blog post is saying to disable the background music in your game (for web builds only) and instead load it using web apis directly
Alright, I see
which only really works well if your game uses 1 background track the whole time, but when it works it works
Maybe another performance hack could be to disable your Bevy code on web and replace it with web APIs as well /s
lol
also the ending of the blog post is interesting
This approach can be extended by communicating between the Rust and JavaScript code in order to control the music. This code will play the same song in a loop, which was good enough for our game, but it might be severely limited for your use-case.
A more rigorous solution would be to implement a new library that uses the Web Audio API as an audio backend on the web, but that would require a lot of work. Also, there doesnโt seem to be enough interest in this topic in the Bevy community.
saying in theory you could instrument the web audio API from your rust code so you're not so limited
was there a reason we're not using bevy build for native release builds in the release workflow?
we're using it for the web release build only right now
i think the pr that migrated us from trunk to bevy build was just being conservative (https://github.com/TheBevyFlock/bevy_new_2d/pull/312)
so the release workflow was successful, but dev features were compiled in ๐ (see #1278871953721262090 message)
which is kinda neat as part of the showcase on itch.io but not intended
i'll get back to this tomorrow
Yup that was the main reason.
For bevy build there might also be slight differences in the build behaviour
We can also remove the web-release profile and replace it by Bevy CLI config FYI
๐
oh, nice. is this working?
Didn't check yet (am doing level design stuff today)
would we want to add this to .vscode/settings.json?
// Prepend `mod.rs` files with their parent directory.
"workbench.editor.customLabels.patterns": {
"**/mod.rs": "${dirname}/mod.rs"
},
so mod.rs is displayed in the editor tab as util/mod.rs
i'm switching my personal template from foo.rs + foo/ to foo/mod.rs... i gave foo.rs a chance and it was ok but having twice as many names in src/ is annoying
and i think 99% of rust devs prefer foo/mod.rs even though foo.rs is "recommended"
not doing anything for me on Cursor
But it sounds cool
That is also my experience
same
it should be in the tab above the text editor, not the explorer sidebar
box shadows are pretty
This looks super cute ๐
check out the more subtle version after some more tuning c:
it makes the "Game paused" text look kinda flat in comparison but whatever :p
Oh wow this is really good
the buttons also move upwards when you hover and leave the shadows in place
Good job tweaking those knobs
that took some hackery
Whaaa no way
I love the pixelated font as well
thanks i made it myself ๐
i started it during bevy jam simulator and kept working on it for a while
yeah i drew it with aseprite
and then converted into a .ttf with pixel font converter (https://yal.cc/tools/pixel-font/)
Fonts for me always feel like magical artifacts bestowed upon us by absent gods
they're just vector art + kerning data :)
(Saving that link)
the pixel font converter converts a .png grid of pixel art glyphs into vector graphics and lets you add metadata / kerning info
internally i mean. it outputs a ttf
That sounds pretty ergonomic ๐
Thanks for the crash course, haha
btw you may or may not know about inline_tweak. i hadn't used it for a while, but reached for it now because bevy_editor_pls isn't updated to 0.16 yet
it has a new #[tweak_fn] attribute which lets you edit any constant in the decorated function and the new value is "hot reloaded" automatically
as opposed to without the attribute where you have to explicitly wrap all your constants in tweak!(...) before hitting compile
i'm putting #[tweak_fn] on all my impl Bundle functions and it's very convenient
compiled out of release builds ofc
i have to make the entities respawn to see the new values in action, like by closing and re-opening a menu. nbd
i'm trying to look into the running out of space caching issue in CI
zstd: error 70 : Write error : cannot write block : No space left on device
/usr/bin/tar: cache.tzst: Wrote only 4096 of 10240 bytes
/usr/bin/tar: Child returned status 70
/usr/bin/tar: Error is not recoverable: exiting now
Warning: Failed to save: "/usr/bin/tar" failed with error: The process '/usr/bin/tar' failed with exit code 2
i hit this in my personal template in the Test job
its cache is 4GB, which is already a lot, then more disk usage resulting from actually running the test command, and then yet more disk usage from trying to create a compressed file to save as the new cache
Aha! I'm not the only one!
so i suspect it is using the full 14GB
I did not know this, looks hella neat!
my current thought is we're doing too much in the Test job
it takes like 12m fresh and generates 4GB cache
trying to look at how other big rust crates handle CI caching
so far checked serde and rand, they just don't do caching and their commands are smaller
most likely we don't need all of this just to make sure the code isn't broken, which is the goal of CI
by smaller i mean more specific, they test specific feature combinations etc. not everything everywhere all at once
example:
- name: Test rand
run: |
cargo test --target ${{ matrix.target }} --lib --tests --no-default-features
cargo build --target ${{ matrix.target }} --no-default-features --features alloc,os_rng,small_rng,unbiased
cargo test --target ${{ matrix.target }} --lib --tests --no-default-features --features=alloc,os_rng,small_rng
cargo test --target ${{ matrix.target }} --examples
tokio does use caching, via Swatinem/rust-cache, but again more specific commands
you could remove debug info in CI as that's never used and should free a lot of place
I think @tranquil breach recently investigated a different caching action, I think it includes less files in the cache. maybe that could help as well
I believe @tacit verge is using that new action
if we're talking about Swatinem/rust-cache then yes
Ah OK never mind :D
That canโt be relevant to the size of the cache though, can it?
We test exactly one combination: activate all features
How can that take up more space than first testing feature A and then feature B?
I guess if the last feature permutation results in fewer dependencies being pulled in, that could have an effect ๐ค
hmm right, idk then
think i got all features confused with all feature combinations
the other repos have like 100MB caches
i guess we have a lot of dependencies through bevy
Yeah, the CLI and linter have Bevy with all default features disabled in order to decrease CI times and cache sizes
That's not really feasible with a template, though
I've used this example for a bit, but now for a new project I am actually trying to use the CICD integrations with Itch and the Build for Web step is timing out. I haven't even changed anything on the project yet simply generated the initial template.
What do the logs say?
Perhaps we should enable --verbose in CI to aid with debugging
Well I can see that it's simply taking too long to build with whatever default / free runners Github actions have configured, as it's being killed exactly after 30 minutes while it's still building.
At that stage it's installing wasm-bindgen
...
Finished `web` profile [optimized + debuginfo] target(s) in 22m 20s
info: bundling JavaScript bindings...
warning: failed to run wasm-bindgen, trying to find automatic fix...
...
@tacit verge didnโt you just do a release a few days ago? Did that one work?
Thereโs a timeout in the YAML file for the release. Could you remove it and try again?
Okay so in my case with default build runners from github cicd it takes +-32m to finish the build and +-47 for the release. Since I haven't changed anything at all perhaps we should increase that default timeout on the template?
Also one interesting thing that happened to me is that it picked the linux bundle rather than the web bundle on itch.io, so I had to manually change it
Hmm. I have GH cache in releases deactivated for Foxtrot, which has like a bazillion dependencies, and the release build takes 34 min: https://github.com/janhohenheim/foxtrot/actions/runs/14848136992
(31 of which are the Windows runner)
are you using a private or public github repository?
the release workflow is also a lot slower currently due to compiling bevy_cli, especially on the windows runner
I am using a private repo for this one
Perhaps it has different limits on runners
private runners have worse specs
so it seems like private repo + windows runner + compiling bevy_cli now pushes the time very high
fwiw we don't need bevy_cli for anything but web builds, but i modified the workflows to use it anyways in anticipation of hopefully being able to cargo-binstall it soon
yeah this is expected, you have to manually select the web bundle on itch.io as a one-time setup step
You can try installing wasm-bindgen with cargo binstall in a previous step, the Bevy CLI will only install it if it's missing
Just be careful to use the correct version, they have to match exactly
experimenting with some workflow improvements in my personal template ๐
the boxes are all checked by default, but you can modify their defaults by editing release.yaml
setting RUSTFLAGS: -C debuginfo=0 -C incremental=no was very effective at reducing cache size
i haven't tested the flags separately
the first and second cache were about 2.7GB and 3.2GB previously
the third cache is the release workflow caching the web build, and it was about the same size before too, because debug info is already disabled for release builds
and i guess release builds are just significantly smaller overall
ok so i have a proposition that i think is not the right choice for bevy_new_2d but figured i'd mention it
because my personal template is jam-focused, i modified the release workflow to run on every commit to main, only doing a web release, and with caching enabled
then i realized i can remove the build web job from the CI workflow since it's made redundant by actually releasing for web on every commit instead
plus there's the cache size reduction from making that a release build instead of a dev build
the main downside afaict is that "release to itch.io on every commit" is a strange default for a non-jam game
That's amazing to know! Swatinem/rust-cache disables incremental compilation already, so all that data must be taken up by debug info
If you don't mind, could you test how much space debuginfo=1 and debuginfo=line-tables-only take up? I'm hesitant to remove all debug info, since it may help diagnose issues only apparent in CI for tests
The full list of options are here, but those are the 2 I think may have the best fit here
will do
i see, then incremental=no should have no impact on cache size, but may have an impact on runner memory usage (which has a 14GB limit)
debuginfo=0 vs debuginfo=1 (still with incremental=no):
JOB BEFORE AFTER
test 830MB 1GB
build 540MB 540MB
bevy-lint 630MB 670MB
doc 620MB 610MB
clippy 620MB 610MB
debuginfo=0 vs debuginfo=line-tables-only (still with incremental=no):
JOB BEFORE AFTER
test 830MB 1GB
build 540MB 540MB
bevy-lint 630MB 590MB
doc 620MB 610MB
clippy 620MB 580MB
there seems to be some noise, and i think technically we only care about the test job because that one compiles a dev build
so order of +200MB in both cases
i'm going to go with debuginfo=0 for my personal template, but i can see being cautious and going with debuginfo=1 for bevy_new_2d for now. it should be a big win regardless
Thatโs a pretty neat idea ๐
We could have a continuous_release flag or something like that in this template
Though I bet this would cause some people to accidentally cheat the deadline for jams by not remembering that their fixes are landing live, haha
test and build-web on bevy_new_2d went from 1.7GB and 1.9GB cache to 840MB and 960MB ๐
IIRC the upload APIs are blocked when set for the jam, so it should be no different from trying to upload a build from the itch UI. The CI would probly just fail.
ah, nice!
that's really good news!
I've also been thinking whether we can disable cache for everything except test and web. Thoughts?
they better do that, otherwise it would be really easy to cheat that in every jam ๐
edit: sry for the late edit - I wanted to reply to make more sense/add context...
fair enough ;D
I ended stripping the native builds from CI, so I'd welcome this as a workflow.
I thought the main usecase for this templates were jams too
btw. when I was updating my (unpublished ๐
) jam entry to 0.16 based on the template I rewrote the click handler systems to a closure returning fn as the repetition of those systems was bugging me. Should I upstream that or is that just a me thing?
https://github.com/meepleek/porcle/blob/main/src/screen/title.rs#L19-L27
Itโs kinda morphed into a generic 2D template for Bevy that we want to upstream at some point.
Yeah. I still remember when this was quickstart ๐
(FWIW I welcome the morphing into definitely more of a 2nd party template)
I think that goes under "the template should not include more abstractions than necessary to not scare new users"
I like the pattern, though ๐
It's also been immensely useful in providing a resource to point people towards regarding code layout, styling, and design if that makes any sense.
Yeah good point. Got quite a few messages from peeps saying that they used the template as a reference for how to organize themselves ๐
At least for me personally, I've definitely used things that the template does to enhance my own stuff and to get a better understanding of things like custom commands, as it's pretty bare bones. When combined with something like the bevy cheatbook, it becomes really nice.
Yeah I've also completely rewritten Foxtrot based on the lessons learned from collaborating on this ๐
Yeah definitely. I think it's definitely something that trips up new people, so having something official in this capacity would be best, but having something that's definitely more second party at least provides a useful on ramp so new people can both have something to grab to easily start, and also reference for their own thing.
Also with the documentation on RustRover, it's quickly becoming a more useful resource for things like Bevy and RustRover...and probably has the most comprehensive documentation on setting things up to work (like with the Debugging with dynamic linking), as otherwise you have to scour and piece together a few different bug reports, messages in this Discord, and/or reddit posts.
I saw!
Thanks again for doing that ๐
Also bevy_new_2d, even as a 2nd party resource, does fill in a nice niche/need for Bevy -- that is a quick 2d project template. Which is something that I know several game engines have, which definitely help with onboarding.
My pleasure! I'm partially surprised that JetBrains hasn't done better in this regard, considering they've been using Bevy with RustRover pretty decently in their blog posts and the like.
But even their official blog posts don't mention anything regarding debugging with Dynamic Linking and the like .
also cargo generate is great
Can you ping them somewhere?
I think theyโd be happy to link to it
Or yoink it
I don't have any contact with JetBrains beyond being a customer, unfortunately and I'm uncertain if there's anyone from JB (although, tbh, I'm sure there are a few people that are here.)
I meant maybe they have an issue tracker somewhere for RustRover
Oh, well the issue tracker is just YouTrack, and it's what they use for all of their products.
(YouTrack is also JetBrain's own Issue Tracking software)
Fair enough. I'm gonna use my own template heavily based on this one anyway ๐
You'll be able to use this once we release v0.1.0 of the linter, since that release will include prebuilt binaries
the other jobs can take like 6m fresh so i think it's good to keep them cached
Got around to trying it again. You're right, this is great!
I think that's a pretty good thing to do!
ah, beautiful cache hits!
finally fast CI again
FYI
Still leaves the workspace-related issues
@tacit verge are you planning on implementing pausing in bevy_new_2d?
i am
Sweet ๐
i have pausing in my personal template already, although that's using pyri_state, but it should be reasonable to translate
i just wanted to figure out the title -> settings vs pause -> settings thing in my personal template first before bringing it to bevy_new_2d
I was just thinking about implementing it on my own, but I trust your ability more in this regard
BTW, you don't happen to have any idea what is up with mouse locking on itch.io pages on Firefox, right?
i use firefox/linux so i can help test, but i've never attempted mouse locking
10s of testing the mouse it seems to work fine, but choppy audio :)
huh, interesting
Yeah the audio is choppy AF for the first few seconds
Really not sure what to do about that except call the web APIs directly
wall jumps would be cool with these walls lol, not to add scope creep but i assume bevy_tnua has support
Thinking of making a crate that just observes OnAdd, AudioPlayer, despawns them instantly and calls web APIs on web
also Esc to take back cursor control also putting you back in title screen, and then have to respawn the level which takes like 5s
It kinda has since the last update ๐
Yeah, that's why I really really want pausing!
That, it's needed to be able to easily tweak mouse sensitivity and FOV
going back to the title screen for that and then reloading the level makes no sense
yeah makes sense
i was gonna research what actual games do for this
is it the same settings menu from title vs pause or different
or mostly same with different bg
I've seen both
either approach can be implemented but just need to know which one
Most older games tend to do this (e.g. Quake)
^ by that I mean exactly the same menu, sorry
Which is fine, but for FOV having a slightly transparent BG is very nice
Also for eventual graphics options
makes sense
So that is what I've been seeing in newer releases
so most likely we'd want the same menu but a different backing overlay
exactly
Yeah makes sense
That also means being able to differentiate options that don't really make sense in-game
interesting, do you have an example?
e.g. a button for "Setup my TrenchBroom directory on my computer so that I can create my own levels plz"
ok so they definitely should be separate
i wonder if older games used the same menu to save storage space or w/e
Some games also have some graphics options only available when in the main menu
But I don't know if that is just sloppyness lol
they probably don't want to implement hot reloading :p
Same here on FF/linux.
FYI. Locked is not supported on Win (and Confined not on Mac) ๐ข
https://docs.rs/bevy/latest/bevy/window/enum.CursorGrabMode.html
btw. the shader compilation got stuck for me on my first try, but worked after a refresh.
Defines if and how the cursor is grabbed by a Window.
is there an upstream rustc issue for this? i don't see it linked anywhere
Wait whatโฝ baah
Does it just noop in those cases
Donโt remember, sorry
Hello, I am trying to load my levels from toml, and that works, and I am doing it from the AssetServer identically to what is done for the footsteps audio in the example.
#[derive(Resource, Asset, Reflect, Clone)]
pub struct LevelAssets {
#[dependency]
pub levels: Vec<Handle<Level>>,
}
impl LevelAssets {
pub const PATH_LEVEL_1: &'static str = "test.level.toml";
pub const PATH_LEVEL_2: &'static str = "test2.level.toml";
}
impl FromWorld for LevelAssets {
fn from_world(world: &mut World) -> Self {
let assets = world.resource::<AssetServer>();
Self {
levels: vec![
assets.load(LevelAssets::PATH_LEVEL_1),
assets.load(LevelAssets::PATH_LEVEL_2),
],
}
}
}
I was trying to access the actual loaded levels but I've been struggling to find out how, since it seems all I can get are handles. I was originally trying to do it in a command from_world but I've even gave up on that to simplify, however I still don't understand how to go from a Vec<Handle<Level>> to the concrete level I want.
I messed around with try_downcast_ref as is level_ref: &dyn PartialReflect but no luck.
fn update_level(current: Res<CurrentLevel>, level_assets: Res<LevelAssets>) {
// TODO despawn existing level
if let Some(level_ref) = level_assets.levels.iter().nth(current.level) {
if let Some(level) = level_ref.try_downcast_ref::<Level>() {
error!("loaded level positions {}", level.positions.len());
} else {
error!("failed downcast");
}
} else {
error!("level {} not found", current.level);
}
}
IIRC Confined tries to fallback to locked and vice versa
Since Windows and macOS have different CursorGrabMode support, we first try to set the grab mode that was asked for. If it doesnโt work then use the alternate grab mode.
try levels: Res<Assets<Level>> and then levels.get(my_handle)
Okay so this works:
fn update_level(level_assets: Res<LevelAssets>, levels: Res<Assets<Level>>) {
// let get: Option<Handle<Level>> = level_assets.levels.get(0);
if let Some(level_handle) = level_assets.levels.get(0) {
if let Some(level) = level_handle.try_downcast_ref::<Handle<Level>>() {
if let Some(level) = levels.get(level) {
trace!("level positions {:?}", level.positions);
}
} else {
panic!("Failed to load level!");
}
}
}
However I don't understand why I need to try_downcast_ref to Handle<Level> since the compilers knows that what I have is a vector of Handle<Level> anyway.
I would expect let get: Option<Handle<Level>> = level_assets.levels.get(0); to succeed, however instead
mismatched types
expected enum `std::option::Option<bevy::prelude::Handle<level_assets::Level>>`
found enum `std::option::Option<&(dyn PartialReflect + 'static)>` [E0308]
Either way, thanks!
How come you donโt have a handle?
Oh wait I see
No, wait, you do have them
The heck?
FYI you can also skip reading the handles completely and just load the level with an asset server again. Since the preloaded handle is still in memory inside a resource, loading the level a second time uses the already loaded data.
That can save you some boilerplate
But I'm very confused why you had to go through this song and dance in the first place
@trim zealot how much in advance of the jam do you think the video should be?
Asking so we can make sure our bigger changes are done in time ๐
Publishing at least a couple days before would be good. Gives a marketing beat for the jam and gives people a day or two to actually take a look at the templates and play with them before deciding to use them for the jam. I think jam plan is still first week of June right?
I think the CLI is going to publish before then too, so planning to cover that as well. Would be great to be able to use the bevy cli with the flock templates for that video.
That monitor stuff is...rather annoying from what I saw while looking into it fwiw.
winit itself has current_monitor() on windows, which returns an Option<MonitorHandle> which is an handle to the Monitor, if the window is on one.
Unfortunately I'm not quite sure how to access that from Bevy, and there may not be a way?
if not then there should be an issue on bevy to expose it
it's probably just an API gap
Yeah looks like this has been at least complained about once, back around 0.9
This issue was brought up: https://github.com/bevyengine/bevy/issues/6993
In which due to changes in how windowing worked, something broke. However the ability to get the monitor the window is on wasn't really added it seems.
The changes were later reverted or otherwise changed, so the issue was closed.
Which one of us wants to open the issue? ๐
i'll open one real quick :)
actually, remind me why we want to get the index of the monitor a window is on for our particular use case?
does MonitorSelection::Current not work?
idk if i was missing something previously or if i'm missing something now
As far as I can tell, MonitorSelection::Current tells you absolutely nothing about the monitor it's on
for the purposes of a video mode selector, as long as it stays in the same monitor when it becomes fullscreen, that would be fine right?
Sure, but we can't tell what monitor the window is on in the first place. So we can't limit resolutions to what a specific monitor provides.
So, for example, if you have two monitors and they both support different resolutions, the game has no way to limit the resolutions we get to only the monitor it's on AFAICT
ahhh yes right
that's what i was missing, thanks
Yeah. Technically there is a way to determine what window we are on, but it's kinda hacky.
And I can only test on Linux -- and particularly X11 atm.
TL;DR if you get the window position, and then get all the monitors you can calculate whether or not the window is within the physical position of one of the monitors.
Although if WindowPosition is ever Automatic we can't tell
created the issue: https://github.com/bevyengine/bevy/issues/19169
Here's a system that should work, at least on Linux under X11:
fn detect_window_monitor(window: Single<&Window, (Changed<Window>, With<PrimaryWindow>)>, monitors: Query<&Monitor>) {
println!("POS: {:#?}", window.position);
let position = match window.position {
WindowPosition::Automatic => return,
WindowPosition::Centered(_) => return,
WindowPosition::At(ivec) => ivec,
};
for monitor in monitors {
let extents = [
monitor.physical_position,
monitor.physical_position + monitor.physical_size().as_ivec2()
];
if position.x >= extents[0].x && position.x <= extents[1].x && position.y >= extents[0].y && position.y <= extents[1].y {
println!("Within {:?}", &monitor.name);
}
}
}
This is limited to one window, and I use Changed so I don't get spammed with output, but.
oh lol i see, yeah that's not nice. definitely not bevy_new_2d material
If window.position is WindowPosition::Automatic then we can't tell.
if window.position is WindowPosition::Current we can't tell.
so the other option for bevy 0.16 is to include a monitor selector in our settings menu as well?
Yeah.
ok, i think that would be reasonable enough to add to the template for now anyways
Even then if the window is moved, and it's not 'sticky' then it could be incorrect. But.
yep
Represents a window.
i'll link to that in the issue
Cool. also the following code would provide a function that can -- roughly -- determine the monitor a window is on (at least on Linux):
fn determine_monitor<'a>(window: &Window, monitors: Vec<(&'a Monitor, Option<&PrimaryMonitor>, Entity)>) -> Option<&'a Monitor>{
match window.position {
WindowPosition::Automatic => None, // we can not determine the monitor it's on at all.
WindowPosition::At(window_pos) => {
let mut zero_monitor = None;
for (monitor, ..) in monitors {
let extents = [
monitor.physical_position,
monitor.physical_position + monitor.physical_size().as_ivec2()
];
if monitor.physical_position.x == 0 && monitor.physical_position.y == 0 {
zero_monitor = Some(monitor);
}
if window_pos.x >= extents[0].x && window_pos.x <= extents[1].x && window_pos.y >= extents[0].y && window_pos.y <= extents[1].y {
return Some(monitor)
}
}
zero_monitor
}
WindowPosition::Centered(selection) => match selection {
MonitorSelection::Current => None, // We can not actually determine position.
MonitorSelection::Index(idx) => None,
MonitorSelection::Primary => monitors.into_iter().find(|(_, p, ..)| p.is_some()).map(|(m, ..)| m),
MonitorSelection::Entity(entity) => monitors.into_iter().find(|(.., e)| *e == entity).map(|(m, ..)| m),
}
}
}
That works under a handful of conditions, but there are some conditions where I just don't think we can tell. For example, when Monitor Index is used, we can't tell which monitor is at which index, as Bevy also does not expose that information.
If the MonitorSelection is current, then we can't know because we don't have any way to get that information.
If Window Position is automatic, there is no way to tell where it's at.
We can only determine the window's position with absolute certainty in one case, and we can likely determine the window's position in about half of the potential paths.
Apologies for the rambling btw, I just wanted to at least somewhat document what I've found and what could be done as a work around just incase someone is looking through the discord to find how to do this in the meantime.
iirc WindowPosition::Centered and Automatic are temporary variants that get converted to At, so maybe you can ignore those cases
Yeah. That could work, although there are some cases where it could be triggered.
Namely if you set the window position with Centered and then the system that determines the Monitor the window is on on runs afterwards, then it might still have WindowPosition::Centered
maybe you can run after the system that resolves the window position to At?
it seems to happen in the changed_windows system which runs in the Last schedule, but not if the window manager has to be the one to set the window position, aka in the WindowPosition::Automatic case. anyways yeah not ideal
Could you put that in a mini crate?
Sure! I was thinking about maybe putting it in my bevy_resolutions crate.
But I could put it in its own crate too.
Not sure what to name it tho...
wait mini crate?
i refactored my personal template, moving pretty much everything in UI into widget.rs, and it's much nicer this way
makes me think the two settings menus (from title vs from pause) should just use widgets as code sharing
aka put the entire volume, video mode, etc. widgets in widget.rs
there would still be duplication in the actual spawning code for the two menus, but i think that's correct, so it's easy to change one menu without affecting the other
and it'd only be like 10 duplicated lines at worst
well.. maybe a more involved settings menu would have more duplication
but you could split into pages (e.g. audio, graphics, etc.) and have entire pages be widgets
there is the risk that a user will add something to one settings menu but forget to add it to the other i guess
so i suppose this is worth it even with one page
if you want to make that one page different, then you'd have to replace the widget with inline code yourself. or make it 2 widgets that share a helper function
Yeah just a tiny dedicated crate ๐
bevy_link_window_to_monitor
Could automatically insert a Monitor component into Windows in PreUpdate ๐