amethyst / specs

Specs - Parallel ECS
https://amethyst.github.io/specs/
Apache License 2.0
2.49k stars 219 forks source link

How do I access all entities with a certain component? #740

Closed eboatwright closed 2 years ago

eboatwright commented 2 years ago

To learn specs, I'm working on making a breakout clone. So, for the Ball component, I need to be able to access the Paddle to get it's position (for collisions). And, I can't figure out how to do it :(

zesterer commented 2 years ago

Have you read through the SPECS book?

eboatwright commented 2 years ago

Yeah I've read through it :( Basically, what I need is a way to just do like "Entities.get_entity_with_tag("paddle")" or something like that. Because, I need to access the Transform component on the paddle Entity from the ball System to check for collisions.

eboatwright commented 2 years ago

I figured out a temporary solution. Is this good? struct BallSystem;

impl<'a> System<'a> for BallSystem { type SystemData = ( ReadStorage<'a, Transform>, WriteStorage<'a, RigidBody>, ReadStorage<'a, Ball>, ReadStorage<'a, Paddle>, );

fn run(&mut self, (transform, mut rigidbody, ball, paddle): Self::SystemData) {
    for (e_transform, e_rigidbody, e_ball) in (&transform, &mut rigidbody, &ball).join() {
        if is_key_pressed(KeyCode::Space)
        && e_rigidbody.velocity == Vec2::ZERO {
            e_rigidbody.velocity = vec2(e_ball.move_speed, -e_ball.move_speed);
        }

        if e_transform.position.x < 0.0
        || e_transform.position.x > SCREEN_WIDTH as f32 - 13.0 {
            e_rigidbody.velocity.x *= -1.0;
        }

        if e_transform.position.y < 0.0 {
            e_rigidbody.velocity.y *= -1.0;
        }

        for (p_transform, _p_paddle) in (&transform, &paddle).join() {
            if e_transform.position.y + 13.0 > p_transform.position.y
            && e_transform.position.x + 13.0 > p_transform.position.x
            && e_transform.position.x < p_transform.position.x + 80.0
            && e_rigidbody.velocity.y > 0.0 {
                e_rigidbody.velocity.y *= -1.0;
            }
        }
    }
}

}

zesterer commented 2 years ago

I figured out a temporary solution. Is this good?

Yes. SPECS does not support querying for specific entities with certain components, only the set of all entities with a particular set of components.

If specific entities have a special meaning in your project then I'd advise storing their Entity in some global resource to make finding them faster.

eboatwright commented 2 years ago

Ok! Thank you for your help! I'm not very experienced with Rust if you couldn't tell XD