Skip to content
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

What "first" & "second" are referring to is inconsistent #211

Open
iiYese opened this issue Dec 12, 2024 · 2 comments
Open

What "first" & "second" are referring to is inconsistent #211

iiYese opened this issue Dec 12, 2024 · 2 comments

Comments

@iiYese
Copy link
Contributor

iiYese commented Dec 12, 2024

This example shows just one instance of this. .with::<&X>().set_second_name("$x") being synonymous with .with_first_name::<&X>("$x") is confusing. In the prior "second" is referring to the name of second part of the pair but in the later "first" is referring to the type parameter not the name of the second part of the pair.

@Indra-db
Copy link
Owner

@iiYese I see what you mean. set_first and set_second are meant as isolated "builder" functions for the pair. I think ideally I'd like to keep first and second referring to the typed, generic parameter, but as you pointed out, it does conflict with those "isolated" functions where you're only setting one part of the pair. Hmm.

Any suggestions besides making first and second refer to the function input parameter? Any preferences?

@iiYese
Copy link
Contributor Author

iiYese commented Dec 22, 2024

You could remove those APIs & use tuples to overload set et al?

impl EntityView {
    // ..
    
    fn set(input: impl IntoField) {
        // ..
    }
    
    fn add(input: impl IntoTag) {
        // ..
    }
}

trait IntoField {
    // maybe don't need the world param?
    fn id(self, world: &World) -> Entity;
}

impl<T: ComponentId> IntoField for T {
    // ..
}

impl<T: ComponentId> IntoField for (T, Entity) {
    // ..
}

impl<T: ComponentId> IntoField for (Entity, T) {
    // ..
}

impl<T: ComponentId, U: ComponentId> IntoField for (T, Id<U>) {
    // ..
}

impl<T: ComponentId, U: ComponentId> IntoField for (Id<T>, U) {
    // ..
}

trait IntoTag {
    // maybe don't need the world param?
    fn id(self, world: &World) -> Entity;
}

// Ik we can't check for ZSTs like this yet, just to illustrate
impl<T: ComponentId + ZST> IntoTag for Id<T> {
    // ..
}

impl<T: ComponentId + ZST> IntoTag for (Id<T>, Entity) {
    // ..
}

impl<T: ComponentId + ZST> IntoTag for (Entity, Id<T>) {
    // ..
}

impl<T: ComponentId + ZST> IntoTag for (Entity, Entity) {
    // ..
}

impl<T: ComponentId + ZST, U: ComponentId + ZST> IntoTag for (Id<T>, Id<U>) {
    // ..
}

// And any combinations I missed

struct Id<T: ComponentId> {
    _phantom: PhantomData<T>;
}

fn id<T: ComponentId>() -> Id<T> {
    Id { _phantom: PhantomData }
}

Then the api wouldn't have first, seconds.

entity.set((Eats { amount: 5 }, id::<Apples>()));

You should be able to use this to overload on &'static strs as well to remove "name" variants too.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

2 participants