-
-
Notifications
You must be signed in to change notification settings - Fork 3.6k
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Add Label type #1423
Add Label type #1423
Conversation
This looks way more complex than it needs to be. Why not have separate derivable traits for labels of different types, instead of requiring an extra argument for the derive macro? E.g., #[derive(Debug, Hash, PartialEq, Eq, Clone, IntoLabel)]
#[label_type(StageLabel)]
enum Stages {
SceneStage,
} could be just #[derive(Debug, Hash, PartialEq, Eq, Clone, StageLabel)]
enum Stages {
SceneStage,
} and type BoxedStageLabel = Box<dyn StageLabel>; (I'm not sure why does it have to be an
To prevent getting stuck beyond the bikeshedding event horizon of infinite potential, I would leave replacing all labels out of the PR, and instead implemented Unrelated, system labels don't seem to be plumbed in everywhere. |
Being able to refer to other systems by their type in some form rather than relying on always having to explicitly label your systems would be a really impressive win from an ergonomics perspective. This would make the beginner experience a lot nicer and avoid really tedious boilerplate. You'll usually only have one system for each function, and dependencies will usually be defined between systems in the same module. I'm not super qualified on how you'd do so (default the label field using reflection?) but feel free to bug #ecs if you need mad science help and I can dig in. Otherwise, Ratys's comments look solid. |
We don't have a better way of doing this. Type name, or anything derived from just the signature, is about the only unambiguous thing we can get from a function without In any case, this is insufficient, because we may need multiple instances of the same type: not everything that's a system is a distinct function. It also muddles encapsulation of systems' labels and encapsulation of systems themselves: a plugin might not want to expose a system, to prevent multiple instances of it (potentially a safety concern), but would like to allow its users to order their systems relative to it.
I'll raise my point from Discord again: putting the schedule together is not something a user would be doing constantly. Barring pathological cases, any boilerplate we may introduce will stand out only in sterile demo code. |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I still think that changing all the labels everywhere should be a separate PR: it's a lot of small, bikesheddable changes everywhere, it distracts from the implementation itself.
Tests should definitely not be touched: we continue to enable the simple stringly-typed labels for a reason.
Co-authored-by: bjorn3 <[email protected]>
Co-authored-by: Alexander Sepity <[email protected]>
They're changes that need to be done eventually, why wait? They're already done
That's a fair point though, I'll revert the changes in tests |
Yes, I forgot to add "but they're already done, so never mind" - I don't think you should revert them now, but I haven't changed my opinion on them in general. |
I've started experimenting on this branch, and some things keep nagging at me. The derive macro is All methods using labels take In my original prototype |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
This looks good to me, but I agree with @Ratysz's assessment of the trait/derive.
We should also discuss removing the Eq
constraint from labels (and changing DynEq to DynPartialEq). Its not strictly needed and would cut down on label declaration boilerplate. However (1) that might not work with @Ratysz 's proposed changes and (2) Eq
is still correct "semantically", which imo is the main argument to include it.
I'm also about to push some (hopefully) non-contentious code style changes.
/// The names of the default App startup stages | ||
pub mod startup_stage; | ||
#[derive(Debug, Hash, PartialEq, Eq, Clone, StageLabel)] | ||
pub enum StartupStage { |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I like to use the following order for imports:
- mod declarations
- public imports
- private imports
- code
These labels are used in hashmaps which need Eq, so I don't think removing that is an option. For the derives, I initally had an |
Here are the results: diff with Bevy master, diff with this branch. I'm biased, but I think this is cleaner. Things that can be tweaked:
|
fn derive_label(input: DeriveInput, label_type: Ident) -> TokenStream2 { | ||
let ident = input.ident; | ||
|
||
let manifest = Manifest::new().unwrap(); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
This won't work for examples and doc tests if bevy_ecs
is used in the main dependencies and bevy
in the dev-dependencies
.
Searching in the main deps first and otherwise in the dev-dependencies like here should work better.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
This test passes, for what it's worth.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
If bevy
was added to the dev-dependencies it would fail. Or rather, the test would work but the other derives would fail.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
yeah its probably worth adopting that method here.
But the user-defined label type isn't actually the type used in the hashmap (in the original impl we were discussing). We could remove the Eq impl in the user-defined type and still implement Eq on the wrapper type that is actually stored. I know this works because I implemented it before leaving the comment 😄 @Ratysz |
So... What should we do then? |
Hmm I'm guessing you don't have the ability to push commits here. I think the only important outcome is both authors getting credited. So if you create a new pr with @TheRawMeatball's commits in the history, then that works. Or alternatively @TheRawMeatball can apply your commits to this pr. |
And to be clear, i think we should only use |
It's also possible to open a PR to his repo and merge changes with rebase, so no merge commit will be in the history of this PR. |
Explicit execution order ambiguities API.
Something went very, very wrong during conflict resolution. The PR lives on as #1473. |
1473 is now merged, closing. |
Maybe potentially solves #103 and some similar issues.
Using these for RenderGraph nodes and slots is planned.