1pub mod automatic;
2mod control;
3mod transform;
4
5pub use control::Controller;
6pub use transform::LookTransform;
7
8use bevy::prelude::*;
9
10pub struct OrbitCameraPlugin;
11impl Plugin for OrbitCameraPlugin {
12 fn build(&self, app: &mut App) {
13 app.init_resource::<automatic::AutomaticRotation>()
14 .add_systems(
15 Update,
16 (control::system, automatic::update, transform::system).chain(),
17 );
18 }
19}
20
21#[derive(Bundle)]
22pub struct OrbitCameraBundle {
23 controller: control::Controller,
24 controller_state: control::OrbitControllerState,
25 look_transform: transform::LookTransform,
26 transform: Transform,
27}
28impl OrbitCameraBundle {
29 pub fn new(controller: control::Controller, eye: Vec3, target: Vec3, up: Vec3) -> Self {
30 let look_transform = transform::LookTransform::new(eye, target, up);
31 let up = up.try_normalize().unwrap_or(Vec3::Y);
32 let controller_state = (target - eye)
33 .try_normalize()
34 .map(|forward| control::OrbitControllerState::from_forward(forward, up))
35 .unwrap_or_else(|| control::OrbitControllerState::from_forward(Vec3::NEG_Z, up));
36
37 Self {
38 controller,
39 controller_state,
40 look_transform,
41 transform: look_transform.into(),
42 }
43 }
44}