Git Product home page Git Product logo

bevy_rts_camera's Introduction

Crates.io docs.rs Bevy tracking

Bevy RTS Camera

A screen recording showing camera movement

Summary

Bevy RTS Camera provides an RTS-style camera for Bevy Engine, to get your game up and running quickly. Designed for simple use cases, and does not try to cover advanced requirements.

Features:

  • Pan, zoom, and rotation
  • Automatically follows whatever you mark as 'ground'
  • Smoothed movement
  • Customisable controls and other settings
  • Comes with optional controller, or you can control it yourself

Default Controller

A default controller is included with these default controls:

  • Arrow Keys: pan
  • Mouse Wheel: zoom
  • Middle Mouse: rotate

You can also 'edge pan' by moving the mouse to the edge of the screen.

Quick Start

Add the plugin:

.add_plugins(RtsCameraPlugin)

Add RtsCamera to a camera:

commands.spawn((
    Camera3dBundle::default(),
    RtsCamera::default(),
    RtsCameraControls::default(),  // Optional
));

Add Ground to your ground/terrain entities:

commands.spawn((
    PbrBundle {
        mesh: meshes.add(Plane3d::default().mesh().size(80.0, 80.0)),
        ..default()
    },
    Ground,
));

This will set up a camera at world origin with good defaults based on a roughly realistic scale (where an average human is 1.75 units tall).

Check out the advanced example to see the possible configuration options.

Version Compatibility

bevy bevy_rts_camera
0.14 0.8
0.13 0.1-0.7

License

All code in this repository is dual-licensed under either:

at your option. This means you can select the license you prefer! This dual-licensing approach is the de-facto standard in the Rust ecosystem and there are very good reasons to include both.

bevy_rts_camera's People

Contributors

plonq avatar juliohq avatar tad-lispy avatar ptfoplayer avatar daddy-cool avatar sschneiders avatar

Stargazers

 avatar  avatar Vladimir avatar Ben Follington avatar DaoLendaye avatar Fabio Dias Rollo avatar cats2333 avatar  avatar Philip Linden avatar Michael Knopke avatar a avatar Stephan Seitz avatar  avatar Nanai Jua avatar xla avatar Tristan Murphy avatar Ömer Mevlüt avatar Martijn Gribnau avatar Andre Azeredo avatar Val Packett avatar Per Johansson avatar fwcd avatar 7d avatar xuyue avatar  avatar Stephan van Stekelenburg avatar  avatar Josef21296 avatar  avatar  avatar Ilshat Sultanov avatar  avatar  avatar  avatar  avatar Виталий Артемьев avatar Roger Küng avatar  avatar  avatar rewin avatar Nilay Savant avatar Ame アメ avatar Mitchell Mosure avatar  avatar Marko Lazić avatar  avatar Will Hart avatar Lucas Luz avatar bley avatar  avatar

Watchers

 avatar  avatar

bevy_rts_camera's Issues

Panics when minimising window

I'm on windows, and when minimising the game window while the rts camera is active, the game panics, complaining of a call to Result::unwrap on an Err:

image

Focus not on the ground?

Hi again! I'm trying to implement custom controls for my camera and for that I need to know where the camera is pointing at on the ground. My understanding was that the focus or target_focus contain this information, but when reading those properties I'm getting a point high above the ground (large y coordinate), even if I manually set the target focus to be at y = 0.0. It also changes when zoom is changed. I think it basically contains the current camera height. Is this intentional? Could you please advise how to get the coordinates on the ground?

My naive way of doing that is as follows, but it doesn't account for any ground topology.

let ground_focus = camera.focus.translation.xz().extend(0.0).xzy();

Window grab mode isn't restored properly

Setting the window grab mode to Confined a la

    app.add_plugins(DefaultPlugins.set(WindowPlugin {
        primary_window: Some(Window {
            cursor: Cursor {
                grab_mode: bevy::window::CursorGrabMode::Confined,
                ..default()
            },
            ..default()
        }),
        ..default()
    }));

storing it somewhere to be used during restoration instead of None should fix it

primary_window.cursor.grab_mode = CursorGrabMode::None;

primary_window.cursor.grab_mode = CursorGrabMode::None;

Zoom increments are too large

Hello!

Love the crate so far.

I was curious if there was a way to adjust the zoom increments? I can't seem to find any settings that do this.

No way to reset camera smoothing

Sometimes you might want to reset the camera smoothing (e.g. either when you add the RTS camera to your app or to position it manually via code), but there doesn't seem to be a way to do that right now.

Commenting out the following line fixes the first issue though:

cam.target_focus.translation.y = cam.height_max.lerp(cam.height_min, cam.zoom);

The second issue is fixed by my recent PR.

How to use a mesh from a GLTF asset as a ground

Another question. I hope I don't bother you too much.

In my app I'm importing a "map" from a GLTF asset exported from Blender. It has multiple objects (trees, rocks, etc.) and one that should serve as the ground. It is named "Ground" so I can access it by name in my program. I tried the following:

    let scene = scenes_assets.get_mut(scene_handle.clone()).unwrap();

    let ground = scene
        .world
        .query::<(Entity, &Name)>()
        .iter(&scene.world)
        .filter_map(|(entity, name)| {
            if name.as_str() == "Ground" {
                Some(entity)
            } else {
                None
            }
        })
        .collect_vec();

    for entity in ground {
        scene
            .world
            .entity_mut(entity)
            .insert(Ground)
            .insert(Name::new("Ground"));
    }

This causes a runtime error:

thread 'main' panicked at /home/tad/.cargo/registry/src/index.crates.io-6f17d22bba15001f/bevy_scene-0.13.2/src/scene_spawner.rs:431:35:
scene contains the unregistered type `bevy_rts_camera::Ground`. consider reflecting it with `#[derive(Reflect)]` and registering the type using `app.register_type::<T>()`
note: run with `RUST_BACKTRACE=1` environment variable to display a backtrace
Encountered a panic in exclusive system `bevy_scene::scene_spawner::scene_spawner_system`!
Encountered a panic in system `bevy_app::main_schedule::Main::run_main`!

It's a bit strange, since I can add the Ground component to entities spawned in the "main" world (with commands.spawn). It makes me think that I'm doing something wrong. Following the advice from the error message (to derive Reflect on Ground) seems impossible since they are both external to my crate, but I did call app.register_type::<Ground>(), alas with no effect. Any advice?

For reference, here is the code in my program where I want this to work: https://gitlab.com/otterhide/otterhide/-/blob/5ca98f1103d4836f86a3200fe28a28c1fa3fb1cb/src/ground.rs#L86-160

Temporarily turn off movement at will

The problem

I'll explain what I want to do:
When focusing on the game's UI, the camera shouldn't react to the player's input. For example, if there's a side panel that the player must click, the camera shouldn't move when approaching the window edge. If there's a list to scroll through, the camera shouldn't zoom when the mouse is over that list.

Possible solution

Provide a resource, for example

#[derive(Resource, Default)]
pub struct SkipMovement;

That you can add when you need to keep the camera still, and then in src/controller.rs

impl Plugin for RtsCameraControlsPlugin {
    fn build(&self, app: &mut App) {
        app.add_plugins(DefaultRaycastingPlugin).add_systems(
            Update,
            (zoom, pan, grab_pan, rotate)
                .run_if(not(resource_exists::<SkipMovement>()))
                .before(RtsCameraSystemSet),
        );
    }
}

That way, while the resource exists, the camera won't react to the player's input, and you can remove the resource when defocusing the UI.

Allow macos “middle mouse click” panning alternative using keyboard

Out of the box, middle mouse click works great when your mouse is connected. When on the laptop trackpad only I don’t think panning has an equivalent action.

It would be cool if you could shift and move two fingers to pan. I think this is what blender does, but any action common to RTS games on laptops would work.

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. 📊📈🎉

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google ❤️ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.