idk
This commit is contained in:
parent
075ccc5a55
commit
7b727d797c
1356
Cargo.lock
generated
1356
Cargo.lock
generated
File diff suppressed because it is too large
Load Diff
@ -5,7 +5,7 @@ edition = "2021"
|
|||||||
|
|
||||||
[dependencies]
|
[dependencies]
|
||||||
avian3d = "0.1.2"
|
avian3d = "0.1.2"
|
||||||
bevy = { version = "0.14.2", features = ["jpeg"] }
|
bevy = { version = "0.14", features = ["jpeg"] }
|
||||||
bevy_dolly = "0.0.4"
|
bevy_dolly = "0.0.4"
|
||||||
bevy_editor_pls = "0.10.0"
|
bevy_editor_pls = "0.10.0"
|
||||||
blenvy = "0.1.0-alpha.1"
|
blenvy = "0.1.0-alpha.1"
|
||||||
@ -14,6 +14,8 @@ clap = { version = "4.5.20", features = ["derive"] }
|
|||||||
lazy_static = "1.5.0"
|
lazy_static = "1.5.0"
|
||||||
lightyear = { version = "0.17.1", features = ["avian3d"] }
|
lightyear = { version = "0.17.1", features = ["avian3d"] }
|
||||||
serde = { version = "1.0.213", features = ["derive"] }
|
serde = { version = "1.0.213", features = ["derive"] }
|
||||||
|
bevy-steamworks = { version = "0.12", features = ["serde"] }
|
||||||
|
bevy_framepace = "0.17.0"
|
||||||
|
|
||||||
[profile.dev.package."*"]
|
[profile.dev.package."*"]
|
||||||
opt-level = 3
|
opt-level = 3
|
||||||
|
|||||||
BIN
art/crooks.blend
BIN
art/crooks.blend
Binary file not shown.
Binary file not shown.
@ -1,10 +1,6 @@
|
|||||||
(
|
(
|
||||||
assets:
|
assets:
|
||||||
[
|
[
|
||||||
("Player", File ( path: "blueprints/Player.glb" )),
|
|
||||||
("glasses.001", File ( path: "materials/glasses.001.glb" )),
|
|
||||||
("head.001", File ( path: "materials/head.001.glb" )),
|
|
||||||
("body.001", File ( path: "materials/body.001.glb" )),
|
|
||||||
("Hotel", File ( path: "blueprints/Hotel.glb" )),
|
("Hotel", File ( path: "blueprints/Hotel.glb" )),
|
||||||
("floor", File ( path: "materials/floor.glb" )),
|
("floor", File ( path: "materials/floor.glb" )),
|
||||||
]
|
]
|
||||||
|
|||||||
1304
assets/registry.json
1304
assets/registry.json
File diff suppressed because it is too large
Load Diff
@ -2,11 +2,30 @@
|
|||||||
use avian3d::{math::*, prelude::*};
|
use avian3d::{math::*, prelude::*};
|
||||||
use bevy::{ecs::query::Has, prelude::*, window::PrimaryWindow};
|
use bevy::{ecs::query::Has, prelude::*, window::PrimaryWindow};
|
||||||
|
|
||||||
|
#[derive(Clone, Copy, PartialEq, Eq, PartialOrd, Ord, Default, Debug, Hash, Resource)]
|
||||||
|
pub enum GameCursorMode {
|
||||||
|
#[default]
|
||||||
|
Locked,
|
||||||
|
Unlocked,
|
||||||
|
}
|
||||||
|
|
||||||
|
impl GameCursorMode {
|
||||||
|
#[must_use]
|
||||||
|
pub fn switch(self) -> Self {
|
||||||
|
match self {
|
||||||
|
GameCursorMode::Locked => GameCursorMode::Unlocked,
|
||||||
|
GameCursorMode::Unlocked => GameCursorMode::Locked,
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
pub struct CharacterControllerPlugin;
|
pub struct CharacterControllerPlugin;
|
||||||
|
|
||||||
impl Plugin for CharacterControllerPlugin {
|
impl Plugin for CharacterControllerPlugin {
|
||||||
fn build(&self, app: &mut App) {
|
fn build(&self, app: &mut App) {
|
||||||
app.add_event::<MovementAction>()
|
app.insert_resource(GameCursorMode::default())
|
||||||
|
.add_event::<MovementAction>()
|
||||||
|
.add_systems(Update, set_cursor_vis)
|
||||||
.add_systems(
|
.add_systems(
|
||||||
Update,
|
Update,
|
||||||
(
|
(
|
||||||
@ -105,6 +124,24 @@ impl MovementBundle {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
fn set_cursor_vis(
|
||||||
|
buttons: Res<ButtonInput<MouseButton>>,
|
||||||
|
mut cursor_mode: ResMut<GameCursorMode>,
|
||||||
|
mut q_windows: Query<&mut Window, With<PrimaryWindow>>,
|
||||||
|
) {
|
||||||
|
let right_clicked = buttons.just_pressed(MouseButton::Right);
|
||||||
|
|
||||||
|
if right_clicked {
|
||||||
|
*cursor_mode = cursor_mode.switch();
|
||||||
|
}
|
||||||
|
|
||||||
|
if right_clicked || cursor_mode.is_changed() {
|
||||||
|
if let Ok(mut window) = q_windows.get_single_mut() {
|
||||||
|
window.cursor.visible = *cursor_mode == GameCursorMode::Unlocked;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
impl Default for MovementBundle {
|
impl Default for MovementBundle {
|
||||||
fn default() -> Self {
|
fn default() -> Self {
|
||||||
Self::new(30.0, 0.9, 7.0, PI * 0.45)
|
Self::new(30.0, 0.9, 7.0, PI * 0.45)
|
||||||
@ -146,9 +183,13 @@ impl CharacterControllerBundle {
|
|||||||
}
|
}
|
||||||
|
|
||||||
fn cursor_input(
|
fn cursor_input(
|
||||||
|
cursor_mode: Res<GameCursorMode>,
|
||||||
mut q_windows: Query<&mut Window, With<PrimaryWindow>>,
|
mut q_windows: Query<&mut Window, With<PrimaryWindow>>,
|
||||||
mut ew_movement: EventWriter<MovementAction>,
|
mut ew_movement: EventWriter<MovementAction>,
|
||||||
) {
|
) {
|
||||||
|
if *cursor_mode == GameCursorMode::Unlocked {
|
||||||
|
return;
|
||||||
|
}
|
||||||
let mut window = q_windows.single_mut();
|
let mut window = q_windows.single_mut();
|
||||||
|
|
||||||
let window_center = window.size() / 2.;
|
let window_center = window.size() / 2.;
|
||||||
|
|||||||
@ -1,14 +1,19 @@
|
|||||||
use bevy::prelude::*;
|
use bevy::prelude::*;
|
||||||
use lightyear::prelude::ClientConnectEvent;
|
use lightyear::prelude::{client::ClientCommands, ClientConnectEvent};
|
||||||
|
|
||||||
pub struct MyClientPlugin;
|
pub struct MyClientPlugin;
|
||||||
|
|
||||||
impl Plugin for MyClientPlugin {
|
impl Plugin for MyClientPlugin {
|
||||||
fn build(&self, app: &mut App) {
|
fn build(&self, app: &mut App) {
|
||||||
app.add_systems(Update, handle_events);
|
app.add_systems(Startup, connect_to_server)
|
||||||
|
.add_systems(Update, handle_events);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
pub fn connect_to_server(mut commands: Commands) {
|
||||||
|
commands.connect_client();
|
||||||
|
}
|
||||||
|
|
||||||
pub fn handle_events(
|
pub fn handle_events(
|
||||||
mut er_client_events: EventReader<ClientConnectEvent>,
|
mut er_client_events: EventReader<ClientConnectEvent>,
|
||||||
// mut er_server_events: EventReader<ServerConnectEvent>,
|
// mut er_server_events: EventReader<ServerConnectEvent>,
|
||||||
|
|||||||
51
src/main.rs
51
src/main.rs
@ -1,5 +1,6 @@
|
|||||||
use avian3d::prelude::PhysicsDebugPlugin;
|
use avian3d::prelude::PhysicsDebugPlugin;
|
||||||
use avian3d::PhysicsPlugins;
|
use avian3d::PhysicsPlugins;
|
||||||
|
use bevy::log::LogPlugin;
|
||||||
use bevy::prelude::*;
|
use bevy::prelude::*;
|
||||||
use bevy_editor_pls::prelude::*;
|
use bevy_editor_pls::prelude::*;
|
||||||
use blenvy::BlenvyPlugin;
|
use blenvy::BlenvyPlugin;
|
||||||
@ -20,6 +21,9 @@ lazy_static::lazy_static! {
|
|||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
|
const LOG_FILTER: &str = "wgpu=error,naga=warn,blenvy=warn";
|
||||||
|
// const LOG_FILTER: &str = "wgpu=error,naga=warn,blenvy=warn,lightyear=debug";
|
||||||
|
|
||||||
#[derive(Parser)]
|
#[derive(Parser)]
|
||||||
#[command(version, about, long_about = None)]
|
#[command(version, about, long_about = None)]
|
||||||
pub struct Cli {
|
pub struct Cli {
|
||||||
@ -40,25 +44,35 @@ fn main() {
|
|||||||
|
|
||||||
#[cfg(feature = "client")]
|
#[cfg(feature = "client")]
|
||||||
let app = app
|
let app = app
|
||||||
.add_plugins(DefaultPlugins)
|
// .add_plugins(SteamworksPlugin::init_app(480).unwrap())
|
||||||
|
.add_plugins(DefaultPlugins.set(LogPlugin {
|
||||||
|
filter: LOG_FILTER.to_string(),
|
||||||
|
level: bevy::log::Level::INFO,
|
||||||
|
custom_layer: |_| None,
|
||||||
|
}))
|
||||||
.add_plugins(lightyear::client::plugin::ClientPlugins::new(
|
.add_plugins(lightyear::client::plugin::ClientPlugins::new(
|
||||||
shared_net::client_config(),
|
shared_net::client_config(),
|
||||||
))
|
))
|
||||||
.add_plugins(EditorPlugin::default())
|
.add_plugins(EditorPlugin::default())
|
||||||
|
.add_plugins(bevy_framepace::FramepacePlugin)
|
||||||
.add_plugins(client::MyClientPlugin);
|
.add_plugins(client::MyClientPlugin);
|
||||||
|
|
||||||
#[cfg(feature = "server")]
|
#[cfg(feature = "server")]
|
||||||
app.add_plugins(
|
app.add_plugins(
|
||||||
DefaultPlugins.build(), // disable some plugins on the server
|
DefaultPlugins.build().set(LogPlugin {
|
||||||
// .disable::<RenderPlugin>()
|
filter: LOG_FILTER.to_string(),
|
||||||
// .disable::<PbrPlugin>()
|
level: bevy::log::Level::INFO,
|
||||||
// .disable::<CorePipelinePlugin>()
|
custom_layer: |_| None,
|
||||||
// .disable::<ImagePlugin>()
|
}), // disable some plugins on the server
|
||||||
// .disable::<TextPlugin>()
|
// .disable::<RenderPlugin>()
|
||||||
// .disable::<SpritePlugin>()
|
// .disable::<PbrPlugin>()
|
||||||
// .disable::<WindowPlugin>()
|
// .disable::<CorePipelinePlugin>()
|
||||||
// .disable::<WinitPlugin>()
|
// .disable::<ImagePlugin>()
|
||||||
// .disable::<GizmoPlugin>()
|
// .disable::<TextPlugin>()
|
||||||
|
// .disable::<SpritePlugin>()
|
||||||
|
// .disable::<WindowPlugin>()
|
||||||
|
// .disable::<WinitPlugin>()
|
||||||
|
// .disable::<GizmoPlugin>()
|
||||||
)
|
)
|
||||||
.add_plugins(lightyear::server::plugin::ServerPlugins::new(
|
.add_plugins(lightyear::server::plugin::ServerPlugins::new(
|
||||||
shared_net::server_config(),
|
shared_net::server_config(),
|
||||||
@ -73,7 +87,20 @@ fn main() {
|
|||||||
CharacterControllerPlugin,
|
CharacterControllerPlugin,
|
||||||
))
|
))
|
||||||
.add_plugins(protocol::ProtocolPlugin)
|
.add_plugins(protocol::ProtocolPlugin)
|
||||||
.add_plugins(BlenvyPlugin::default());
|
.add_plugins(BlenvyPlugin::default())
|
||||||
|
// .add_systems(Startup, steam_system);
|
||||||
|
;
|
||||||
|
|
||||||
app.run();
|
app.run();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// fn steam_system(steam_client: Res<Client>) {
|
||||||
|
// for friend in steam_client.friends().get_friends(FriendFlags::IMMEDIATE) {
|
||||||
|
// println!(
|
||||||
|
// "Friend: {:?} - {}({:?})",
|
||||||
|
// friend.id(),
|
||||||
|
// friend.name(),
|
||||||
|
// friend.state()
|
||||||
|
// );
|
||||||
|
// }
|
||||||
|
// }
|
||||||
|
|||||||
@ -1,14 +1,19 @@
|
|||||||
use bevy::prelude::*;
|
use bevy::prelude::*;
|
||||||
use lightyear::prelude::ServerConnectEvent;
|
use lightyear::prelude::{server::ServerCommands, ServerConnectEvent};
|
||||||
|
|
||||||
pub struct MyServerPlugin;
|
pub struct MyServerPlugin;
|
||||||
|
|
||||||
impl Plugin for MyServerPlugin {
|
impl Plugin for MyServerPlugin {
|
||||||
fn build(&self, app: &mut App) {
|
fn build(&self, app: &mut App) {
|
||||||
app.add_systems(Update, handle_events);
|
app.add_systems(Startup, start_server)
|
||||||
|
.add_systems(Update, handle_events);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
pub fn start_server(mut commands: Commands) {
|
||||||
|
commands.start_server();
|
||||||
|
}
|
||||||
|
|
||||||
pub fn handle_events(mut er_server_events: EventReader<ServerConnectEvent>) {
|
pub fn handle_events(mut er_server_events: EventReader<ServerConnectEvent>) {
|
||||||
for server_connect in er_server_events.read() {
|
for server_connect in er_server_events.read() {
|
||||||
println!("Server Connect: {:?}", server_connect);
|
println!("Server Connect: {:?}", server_connect);
|
||||||
|
|||||||
77
src/setup.rs
77
src/setup.rs
@ -1,9 +1,9 @@
|
|||||||
use avian3d::{
|
use avian3d::{
|
||||||
math::{Scalar, Vector},
|
math::{Scalar, Vector},
|
||||||
prelude::Collider,
|
prelude::{Collider, PhysicsSet},
|
||||||
};
|
};
|
||||||
use bevy::prelude::*;
|
use bevy::prelude::*;
|
||||||
use bevy_dolly::{prelude::Rig, system::Dolly};
|
use bevy_dolly::prelude::Rig;
|
||||||
use blenvy::{BlueprintInfo, GameWorldTag, HideUntilReady, SpawnBlueprint};
|
use blenvy::{BlueprintInfo, GameWorldTag, HideUntilReady, SpawnBlueprint};
|
||||||
|
|
||||||
use crate::char_controller::CharacterControllerBundle;
|
use crate::char_controller::CharacterControllerBundle;
|
||||||
@ -27,16 +27,22 @@ impl Plugin for SetupPlugin {
|
|||||||
app.register_type::<Player>()
|
app.register_type::<Player>()
|
||||||
.register_type::<PlayerHead>()
|
.register_type::<PlayerHead>()
|
||||||
.add_systems(Startup, setup)
|
.add_systems(Startup, setup)
|
||||||
|
// .add_systems(
|
||||||
|
// Update,
|
||||||
|
// (update_camera_rig, Dolly::<MainCamera>::update_active).chain(),
|
||||||
|
// )
|
||||||
.add_systems(
|
.add_systems(
|
||||||
Update,
|
PostUpdate,
|
||||||
(update_camera_rig, Dolly::<MainCamera>::update_active),
|
update_camera_location
|
||||||
)
|
.after(PhysicsSet::Sync)
|
||||||
// TODO: change to component hooks
|
.before(TransformSystem::TransformPropagate),
|
||||||
.add_systems(Update, setup_player);
|
);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
fn setup(mut commands: Commands) {
|
fn setup(world: &mut World) {
|
||||||
|
let mut commands = world.commands();
|
||||||
|
|
||||||
use bevy_dolly::prelude::*;
|
use bevy_dolly::prelude::*;
|
||||||
commands.spawn((
|
commands.spawn((
|
||||||
MainCamera, // The rig component tag
|
MainCamera, // The rig component tag
|
||||||
@ -45,9 +51,9 @@ fn setup(mut commands: Commands) {
|
|||||||
// Adds a driver for rotation
|
// Adds a driver for rotation
|
||||||
.with(Rotation::new(Quat::IDENTITY))
|
.with(Rotation::new(Quat::IDENTITY))
|
||||||
// Interpolation when the translation is updated, also known as smoothing
|
// Interpolation when the translation is updated, also known as smoothing
|
||||||
.with(Smooth::new_position(0.3))
|
// .with(Smooth::new_position(0.03))
|
||||||
// Interpolation when the rotation is updated (updated via the YawPitch driver)
|
// Interpolation when the rotation is updated (updated via the YawPitch driver)
|
||||||
.with(Smooth::new_rotation(0.3))
|
// .with(Smooth::new_rotation(0.03))
|
||||||
// Moves the camera point out in the Z direction and uses the position as the pivot
|
// Moves the camera point out in the Z direction and uses the position as the pivot
|
||||||
// .with(Arm::new(Vec3::Z * 4.0))
|
// .with(Arm::new(Vec3::Z * 4.0))
|
||||||
.build(),
|
.build(),
|
||||||
@ -92,23 +98,26 @@ fn setup(mut commands: Commands) {
|
|||||||
HideUntilReady,
|
HideUntilReady,
|
||||||
GameWorldTag,
|
GameWorldTag,
|
||||||
));
|
));
|
||||||
}
|
|
||||||
|
|
||||||
fn setup_player(
|
#[cfg(feature = "client")]
|
||||||
mut commands: Commands,
|
commands.spawn((
|
||||||
q_player: Query<Entity, (With<Player>, Without<Collider>)>,
|
BlueprintInfo::from_path("blueprints/Player.glb"),
|
||||||
) {
|
SpawnBlueprint,
|
||||||
let Ok(player_entity) = q_player.get_single() else {
|
HideUntilReady,
|
||||||
return;
|
GameWorldTag,
|
||||||
};
|
));
|
||||||
|
|
||||||
commands.entity(player_entity).insert(
|
world
|
||||||
CharacterControllerBundle::new(
|
.register_component_hooks::<Player>()
|
||||||
Collider::capsule_endpoints(1., Vec3::Y, Vec3::Y * 3.),
|
.on_add(|mut world, e, _| {
|
||||||
Vector::NEG_Y * 9.81 * 2.0,
|
world.commands().entity(e).insert(
|
||||||
)
|
CharacterControllerBundle::new(
|
||||||
.with_movement(30.0, 0.92, 7.0, (30.0 as Scalar).to_radians()),
|
Collider::capsule_endpoints(1., Vec3::Y, Vec3::Y * 3.),
|
||||||
);
|
Vector::NEG_Y * 9.81 * 2.0,
|
||||||
|
)
|
||||||
|
.with_movement(30.0, 0.92, 7.0, (30.0 as Scalar).to_radians()),
|
||||||
|
);
|
||||||
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
fn update_camera_rig(
|
fn update_camera_rig(
|
||||||
@ -129,3 +138,21 @@ fn update_camera_rig(
|
|||||||
d_pos.position = pos;
|
d_pos.position = pos;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
fn update_camera_location(
|
||||||
|
q_player_head: Query<&GlobalTransform, (With<PlayerHead>, Without<Camera>)>,
|
||||||
|
mut q_camera: Query<&mut Transform, (With<Camera>, With<MainCamera>)>,
|
||||||
|
) {
|
||||||
|
let Ok(player_head_transform) = q_player_head.get_single() else {
|
||||||
|
warn!("No player head!");
|
||||||
|
return;
|
||||||
|
};
|
||||||
|
let Ok(mut camera_transform) = q_camera.get_single_mut() else {
|
||||||
|
warn!("No main camera!");
|
||||||
|
return;
|
||||||
|
};
|
||||||
|
|
||||||
|
let (_, rot, pos) = player_head_transform.to_scale_rotation_translation();
|
||||||
|
camera_transform.translation = pos;
|
||||||
|
camera_transform.rotation = rot;
|
||||||
|
}
|
||||||
|
|||||||
@ -6,17 +6,19 @@ use std::time::Duration;
|
|||||||
pub const PRIVIATE_KEY: Key = [12; 32];
|
pub const PRIVIATE_KEY: Key = [12; 32];
|
||||||
pub const FIXED_TIMESTEP_HZ: f64 = 64.0;
|
pub const FIXED_TIMESTEP_HZ: f64 = 64.0;
|
||||||
pub const REPLICATION_INTERVAL: Duration = Duration::from_millis(100);
|
pub const REPLICATION_INTERVAL: Duration = Duration::from_millis(100);
|
||||||
|
pub const LOCAL_IP: &str = "127.0.0.1:7000";
|
||||||
|
pub const ANY_IP: &str = "0.0.0.0:0";
|
||||||
|
|
||||||
pub fn client_config() -> ClientConfig {
|
pub fn client_config() -> ClientConfig {
|
||||||
let auth = Authentication::Manual {
|
let auth = Authentication::Manual {
|
||||||
server_addr: "127.0.0.1:7000".parse().unwrap(),
|
server_addr: "127.0.0.1:7001".parse().unwrap(),
|
||||||
client_id: 2,
|
client_id: 2,
|
||||||
private_key: PRIVIATE_KEY,
|
private_key: PRIVIATE_KEY,
|
||||||
protocol_id: 0,
|
protocol_id: 0,
|
||||||
};
|
};
|
||||||
let netcode_config = client::NetcodeConfig::default();
|
let netcode_config = client::NetcodeConfig::default();
|
||||||
let io_config = client::IoConfig {
|
let io_config = client::IoConfig {
|
||||||
transport: client::ClientTransport::UdpSocket("127.0.0.1:7000".parse().unwrap()),
|
transport: client::ClientTransport::UdpSocket(ANY_IP.parse().unwrap()),
|
||||||
conditioner: None,
|
conditioner: None,
|
||||||
compression: CompressionConfig::default(),
|
compression: CompressionConfig::default(),
|
||||||
};
|
};
|
||||||
@ -33,9 +35,13 @@ pub fn client_config() -> ClientConfig {
|
|||||||
}
|
}
|
||||||
|
|
||||||
pub fn server_config() -> ServerConfig {
|
pub fn server_config() -> ServerConfig {
|
||||||
let netcode_config = server::NetcodeConfig::default();
|
let netcode_config = server::NetcodeConfig {
|
||||||
|
protocol_id: 0,
|
||||||
|
private_key: PRIVIATE_KEY,
|
||||||
|
..Default::default()
|
||||||
|
};
|
||||||
let io_config = server::IoConfig {
|
let io_config = server::IoConfig {
|
||||||
transport: server::ServerTransport::UdpSocket("127.0.0.1:7000".parse().unwrap()),
|
transport: server::ServerTransport::UdpSocket(LOCAL_IP.parse().unwrap()),
|
||||||
conditioner: None,
|
conditioner: None,
|
||||||
compression: CompressionConfig::default(),
|
compression: CompressionConfig::default(),
|
||||||
};
|
};
|
||||||
|
|||||||
Loading…
Reference in New Issue
Block a user