mirror of
https://codeberg.org/schrottkatze/mgd2-tram-championships.git
synced 2025-05-20 09:38:00 +00:00
do a basic scene and way too much organization and fail to implement panning
This commit is contained in:
parent
08069c9224
commit
6d269d0c14
6 changed files with 156 additions and 29 deletions
13
src/camera.rs
Normal file
13
src/camera.rs
Normal file
|
@ -0,0 +1,13 @@
|
||||||
|
//! The general app camera module, not to be confused with the `game::camera`¹ module.
|
||||||
|
//!
|
||||||
|
//! 1: I can't link to out of scope private items, so you'll have to navigate there yourself.
|
||||||
|
use bevy::prelude::*;
|
||||||
|
|
||||||
|
/// Sets up the camera for the entire app, with a starting position for the game. (TODO: probably change that)
|
||||||
|
/// This camera is also used for menu rendering etc.
|
||||||
|
pub fn setup(mut c: Commands) {
|
||||||
|
c.spawn((
|
||||||
|
Camera3d::default(),
|
||||||
|
Transform::from_xyz(-20., 15., 0.).looking_at(Vec3::ZERO, Vec3::Y),
|
||||||
|
));
|
||||||
|
}
|
14
src/cleanup.rs
Normal file
14
src/cleanup.rs
Normal file
|
@ -0,0 +1,14 @@
|
||||||
|
//! Defines generic despawn/cleanup function and cleanup marker components
|
||||||
|
|
||||||
|
use bevy::prelude::*;
|
||||||
|
|
||||||
|
/// Despawn/cleanup every entity with `T`.
|
||||||
|
/// See the [bevy cheatbook's cleanup example](https://bevy-cheatbook.github.io/patterns/generic-systems.html#example-cleanup).
|
||||||
|
pub fn despawn<T: Component>(mut c: Commands, q: Query<Entity, With<T>>) {
|
||||||
|
for e in q {
|
||||||
|
c.entity(e).despawn();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
#[derive(Component)]
|
||||||
|
pub struct Scene;
|
23
src/game.rs
Normal file
23
src/game.rs
Normal file
|
@ -0,0 +1,23 @@
|
||||||
|
use bevy::prelude::*;
|
||||||
|
|
||||||
|
use crate::{
|
||||||
|
AppState,
|
||||||
|
cleanup::{self, despawn},
|
||||||
|
};
|
||||||
|
|
||||||
|
mod camera;
|
||||||
|
mod scene;
|
||||||
|
|
||||||
|
/// Gameplay system set. All functions in this control the gameplay (duh).
|
||||||
|
#[derive(SystemSet, Debug, Clone, PartialEq, Eq, Hash)]
|
||||||
|
struct GameplaySet;
|
||||||
|
|
||||||
|
pub fn plugin(app: &mut App) {
|
||||||
|
app.add_plugins(camera::plugin)
|
||||||
|
.add_systems(OnEnter(AppState::Ingame), scene::setup.in_set(GameplaySet))
|
||||||
|
.add_systems(
|
||||||
|
OnExit(AppState::Ingame),
|
||||||
|
despawn::<cleanup::Scene>.in_set(GameplaySet),
|
||||||
|
);
|
||||||
|
app.configure_sets(Update, GameplaySet.run_if(in_state(AppState::Ingame)));
|
||||||
|
}
|
65
src/game/camera.rs
Normal file
65
src/game/camera.rs
Normal file
|
@ -0,0 +1,65 @@
|
||||||
|
//! Sets up the game's camera controls etc.
|
||||||
|
|
||||||
|
use bevy::{
|
||||||
|
input::mouse::{AccumulatedMouseMotion, MouseButtonInput},
|
||||||
|
prelude::*,
|
||||||
|
};
|
||||||
|
|
||||||
|
use super::GameplaySet;
|
||||||
|
|
||||||
|
pub fn plugin(app: &mut App) {
|
||||||
|
app.init_resource::<MouseButtonsPressed>().add_systems(
|
||||||
|
Update,
|
||||||
|
(
|
||||||
|
detect_mouse_button_press,
|
||||||
|
panning_basic.after(detect_mouse_button_press),
|
||||||
|
)
|
||||||
|
.in_set(GameplaySet),
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
/// Resource to store current mouse button state.
|
||||||
|
#[derive(Resource, Default)]
|
||||||
|
struct MouseButtonsPressed {
|
||||||
|
left: bool,
|
||||||
|
}
|
||||||
|
|
||||||
|
/// Detect whether mouse buttons (currently only left) are pressed.
|
||||||
|
fn detect_mouse_button_press(
|
||||||
|
mut button_events: EventReader<MouseButtonInput>,
|
||||||
|
mut pressed: ResMut<MouseButtonsPressed>,
|
||||||
|
) {
|
||||||
|
for event in button_events.read() {
|
||||||
|
if event.button == MouseButton::Left {
|
||||||
|
pressed.left = dbg!(event.state.is_pressed());
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/// is SUPPOSED to do proper panning
|
||||||
|
/// i hate 3d math
|
||||||
|
fn panning_basic(
|
||||||
|
accumulated_mouse_motion: Res<AccumulatedMouseMotion>,
|
||||||
|
mut cam_transform: Single<&mut Transform, With<Camera>>,
|
||||||
|
pressed: Res<MouseButtonsPressed>,
|
||||||
|
) {
|
||||||
|
if pressed.left && accumulated_mouse_motion.delta != Vec2::ZERO {
|
||||||
|
let yaw = Quat::from_rotation_y(accumulated_mouse_motion.delta.x / 150.);
|
||||||
|
// cam_transform.rotate_around(Vec3::ZERO, yaw);
|
||||||
|
cam_transform.rotation *= yaw;
|
||||||
|
|
||||||
|
let pitch = Quat::from_rotation_x(accumulated_mouse_motion.delta.y / 150.);
|
||||||
|
let new_rot = cam_transform.rotation * pitch;
|
||||||
|
// cam_transform.rotate_around(Vec3::ZERO, pitch);
|
||||||
|
// cam_transform.rotation *= pitch;
|
||||||
|
let up_vector = new_rot * Vec3::Y;
|
||||||
|
if up_vector.y > 0.0 {
|
||||||
|
cam_transform.rotation = new_rot;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
// ???????
|
||||||
|
// TODO: figure out/understand how they do it https://github.com/The-DevBlog/bevy_third_person_camera/blob/a7c6b458573fcb0730b65eda6507ca27fb58f571/src/mouse.rs#L29-L74
|
||||||
|
//
|
||||||
|
let rot_matrix = Mat3::from_quat(cam_transform.rotation);
|
||||||
|
cam_transform.translation = rot_matrix.mul_vec3(Vec3::new(0.0, 0.0, 20.));
|
||||||
|
}
|
25
src/game/scene.rs
Normal file
25
src/game/scene.rs
Normal file
|
@ -0,0 +1,25 @@
|
||||||
|
use bevy::prelude::*;
|
||||||
|
|
||||||
|
use crate::cleanup;
|
||||||
|
|
||||||
|
const NORMALSPUR: f32 = 1.435;
|
||||||
|
|
||||||
|
pub fn setup(
|
||||||
|
mut c: Commands,
|
||||||
|
mut meshes: ResMut<Assets<Mesh>>,
|
||||||
|
mut materials: ResMut<Assets<StandardMaterial>>,
|
||||||
|
) {
|
||||||
|
// spawn in floor plane
|
||||||
|
c.spawn((
|
||||||
|
Mesh3d(meshes.add(Plane3d::default().mesh().size(128., 128.))),
|
||||||
|
MeshMaterial3d(materials.add(Color::srgb(0.3, 0.8, 0.4))),
|
||||||
|
cleanup::Scene,
|
||||||
|
));
|
||||||
|
|
||||||
|
// track (temporary)
|
||||||
|
c.spawn((
|
||||||
|
Mesh3d(meshes.add(Cuboid::new(NORMALSPUR, 0.25, 96.))),
|
||||||
|
MeshMaterial3d(materials.add(Color::BLACK)),
|
||||||
|
cleanup::Scene,
|
||||||
|
));
|
||||||
|
}
|
45
src/main.rs
45
src/main.rs
|
@ -1,36 +1,23 @@
|
||||||
use bevy::prelude::*;
|
use bevy::prelude::*;
|
||||||
|
|
||||||
|
mod camera;
|
||||||
|
mod cleanup;
|
||||||
|
mod game;
|
||||||
|
|
||||||
|
#[derive(States, Default, Debug, Clone, PartialEq, Eq, Hash)]
|
||||||
|
#[allow(unused)]
|
||||||
|
enum AppState {
|
||||||
|
Menus,
|
||||||
|
#[default]
|
||||||
|
Ingame,
|
||||||
|
PostGame,
|
||||||
|
}
|
||||||
|
|
||||||
fn main() {
|
fn main() {
|
||||||
App::new()
|
App::new()
|
||||||
.add_plugins(DefaultPlugins)
|
.add_plugins(DefaultPlugins)
|
||||||
.add_systems(Startup, yeet)
|
.init_state::<AppState>()
|
||||||
|
.add_plugins(game::plugin)
|
||||||
|
.add_systems(Startup, camera::setup)
|
||||||
.run();
|
.run();
|
||||||
}
|
}
|
||||||
|
|
||||||
fn yeet(
|
|
||||||
mut commands: Commands,
|
|
||||||
mut meshes: ResMut<Assets<Mesh>>,
|
|
||||||
mut materials: ResMut<Assets<StandardMaterial>>,
|
|
||||||
) {
|
|
||||||
commands.spawn((
|
|
||||||
Mesh3d(meshes.add(Cuboid::new(1.0, 1.0, 1.0))),
|
|
||||||
MeshMaterial3d(materials.add(Color::srgb_u8(255, 255, 255))),
|
|
||||||
Transform::from_xyz(0.0, 0.5, 0.0),
|
|
||||||
));
|
|
||||||
commands.spawn((
|
|
||||||
Mesh3d(meshes.add(Plane3d::new(Vec3::Y, vec2(4., 4.)))),
|
|
||||||
MeshMaterial3d(materials.add(Color::srgb_u8(255, 255, 255))),
|
|
||||||
Transform::from_xyz(0., 0., 0.),
|
|
||||||
));
|
|
||||||
commands.spawn((
|
|
||||||
PointLight {
|
|
||||||
shadows_enabled: true,
|
|
||||||
..default()
|
|
||||||
},
|
|
||||||
Transform::from_xyz(4.0, 8.0, 4.0),
|
|
||||||
));
|
|
||||||
commands.spawn((
|
|
||||||
Camera3d::default(),
|
|
||||||
Transform::from_xyz(-4.5, 3.5, 4.5).looking_at(Vec3::ZERO, Vec3::Y),
|
|
||||||
));
|
|
||||||
}
|
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue