101 lines
2.1 KiB
Rust
101 lines
2.1 KiB
Rust
use cgmath::{Deg, InnerSpace, Vector2};
|
|
use nalgebra::vector;
|
|
|
|
use rapier2d::dynamics::RigidBody;
|
|
|
|
use crate::{util, ShipPhysicsHandle};
|
|
use galactica_content as content;
|
|
use galactica_gameobject as object;
|
|
use galactica_render::ObjectSprite;
|
|
|
|
pub struct ShipControls {
|
|
pub left: bool,
|
|
pub right: bool,
|
|
pub thrust: bool,
|
|
pub guns: bool,
|
|
}
|
|
|
|
impl ShipControls {
|
|
pub fn new() -> Self {
|
|
ShipControls {
|
|
left: false,
|
|
right: false,
|
|
thrust: false,
|
|
guns: false,
|
|
}
|
|
}
|
|
}
|
|
|
|
/// A ship instance in the physics system
|
|
pub struct ShipWorldObject {
|
|
/// TODO
|
|
pub physics_handle: ShipPhysicsHandle,
|
|
|
|
/// TODO
|
|
pub ship: object::Ship,
|
|
|
|
/// TODO
|
|
pub controls: ShipControls,
|
|
}
|
|
|
|
impl ShipWorldObject {
|
|
/// Make a new ship
|
|
pub fn new(ship: object::Ship, physics_handle: ShipPhysicsHandle) -> Self {
|
|
ShipWorldObject {
|
|
physics_handle,
|
|
ship,
|
|
controls: ShipControls::new(),
|
|
}
|
|
}
|
|
|
|
/// Step this ship's state by t seconds
|
|
pub fn step(&mut self, r: &mut RigidBody, t: f32) {
|
|
let ship_rot = util::rigidbody_rotation(r);
|
|
let engine_force = ship_rot * t;
|
|
|
|
if self.controls.thrust {
|
|
r.apply_impulse(
|
|
vector![engine_force.x, engine_force.y]
|
|
* self.ship.outfits.stat_sum().engine_thrust,
|
|
true,
|
|
);
|
|
}
|
|
|
|
if self.controls.right {
|
|
r.apply_torque_impulse(self.ship.outfits.stat_sum().steer_power * -100.0 * t, true);
|
|
}
|
|
|
|
if self.controls.left {
|
|
r.apply_torque_impulse(self.ship.outfits.stat_sum().steer_power * 100.0 * t, true);
|
|
}
|
|
|
|
for i in self.ship.outfits.iter_guns() {
|
|
i.cooldown -= t;
|
|
}
|
|
}
|
|
|
|
/// Get this ship's sprite
|
|
pub fn get_sprite(&self, ct: &content::Content, r: &RigidBody) -> ObjectSprite {
|
|
let ship_pos = util::rigidbody_position(r);
|
|
let ship_rot = util::rigidbody_rotation(r);
|
|
|
|
// Sprites point north at 0 degrees
|
|
let ship_ang: Deg<f32> = ship_rot.angle(Vector2 { x: 0.0, y: 1.0 }).into();
|
|
|
|
let s = ct.get_ship(self.ship.handle);
|
|
|
|
ObjectSprite {
|
|
pos: (ship_pos.x, ship_pos.y, 1.0).into(),
|
|
texture: s.sprite_texture,
|
|
angle: -ship_ang,
|
|
size: s.size,
|
|
|
|
children: if self.controls.thrust {
|
|
Some(self.ship.outfits.get_engine_flares())
|
|
} else {
|
|
None
|
|
},
|
|
}
|
|
}
|
|
}
|