Added basic radar
parent
8fbbf7f110
commit
fa8a0f5761
|
@ -209,6 +209,12 @@ impl Content {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// Get a texture from a handle
|
||||||
|
pub fn get_texture_handle(&self, name: &str) -> TextureHandle {
|
||||||
|
return *self.texture_index.get(name).unwrap();
|
||||||
|
// TODO: handle errors
|
||||||
|
}
|
||||||
|
|
||||||
/// Get a texture from a handle
|
/// Get a texture from a handle
|
||||||
pub fn get_texture(&self, h: TextureHandle) -> &Texture {
|
pub fn get_texture(&self, h: TextureHandle) -> &Texture {
|
||||||
// In theory, this could fail if h has a bad index, but that shouldn't ever happen.
|
// In theory, this could fail if h has a bad index, but that shouldn't ever happen.
|
||||||
|
|
|
@ -1,4 +1,4 @@
|
||||||
use cgmath::Point2;
|
use cgmath::{Deg, InnerSpace, Point2};
|
||||||
use galactica_content::FactionHandle;
|
use galactica_content::FactionHandle;
|
||||||
use std::time::Instant;
|
use std::time::Instant;
|
||||||
use winit::event::{ElementState, MouseButton, MouseScrollDelta, TouchPhase, VirtualKeyCode};
|
use winit::event::{ElementState, MouseButton, MouseScrollDelta, TouchPhase, VirtualKeyCode};
|
||||||
|
@ -9,10 +9,61 @@ use crate::{
|
||||||
content::Content,
|
content::Content,
|
||||||
inputstatus::InputStatus,
|
inputstatus::InputStatus,
|
||||||
physics::{util, Physics, ShipHandle},
|
physics::{util, Physics, ShipHandle},
|
||||||
render::Sprite,
|
render::{AnchoredUiPosition, ObjectSprite, UiSprite},
|
||||||
shipbehavior::{self, ShipBehavior},
|
shipbehavior::{self, ShipBehavior},
|
||||||
};
|
};
|
||||||
|
|
||||||
|
struct Ui {}
|
||||||
|
|
||||||
|
impl Ui {
|
||||||
|
fn new() -> Self {
|
||||||
|
Self {}
|
||||||
|
}
|
||||||
|
|
||||||
|
fn build_radar(&self, player: &ShipHandle, physics: &Physics, ct: &Content) -> Vec<UiSprite> {
|
||||||
|
let mut out = Vec::new();
|
||||||
|
|
||||||
|
let radar_range = 2000.0;
|
||||||
|
let radar_size = 300.0;
|
||||||
|
|
||||||
|
out.push(UiSprite {
|
||||||
|
texture: ct.get_texture_handle("ui::radar"),
|
||||||
|
pos: AnchoredUiPosition::NorthWest(Point2 { x: 10.0, y: -10.0 }),
|
||||||
|
dimensions: Point2 {
|
||||||
|
x: radar_size,
|
||||||
|
y: radar_size,
|
||||||
|
},
|
||||||
|
angle: Deg(0.0),
|
||||||
|
});
|
||||||
|
|
||||||
|
let (_, pr) = physics.get_ship_body(player).unwrap();
|
||||||
|
let pr = util::rigidbody_position(pr);
|
||||||
|
for (s, r) in physics.iter_ship_body() {
|
||||||
|
if s.physics_handle == *player {
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
let r = util::rigidbody_position(r);
|
||||||
|
let d = r - pr;
|
||||||
|
let m = d.magnitude() / radar_range;
|
||||||
|
if m < 0.8 {
|
||||||
|
out.push(UiSprite {
|
||||||
|
texture: ct.get_texture_handle("ui::blip"),
|
||||||
|
pos: AnchoredUiPosition::NorthWest(
|
||||||
|
Point2 {
|
||||||
|
x: radar_size / 2.0 + 10.0,
|
||||||
|
y: radar_size / -2.0 - 10.0,
|
||||||
|
} + (d / radar_range * 150.0),
|
||||||
|
),
|
||||||
|
dimensions: Point2 { x: 1.0, y: 1.0 } * 5.0f32.min((0.8 - m) * 50.0),
|
||||||
|
angle: Deg(0.0),
|
||||||
|
});
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return out;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
pub struct Game {
|
pub struct Game {
|
||||||
pub input: InputStatus,
|
pub input: InputStatus,
|
||||||
pub last_update: Instant,
|
pub last_update: Instant,
|
||||||
|
@ -22,6 +73,7 @@ pub struct Game {
|
||||||
paused: bool,
|
paused: bool,
|
||||||
pub time_scale: f32,
|
pub time_scale: f32,
|
||||||
|
|
||||||
|
ui: Ui,
|
||||||
physics: Physics,
|
physics: Physics,
|
||||||
shipbehaviors: Vec<Box<dyn ShipBehavior>>,
|
shipbehaviors: Vec<Box<dyn ShipBehavior>>,
|
||||||
content: Content,
|
content: Content,
|
||||||
|
@ -84,6 +136,7 @@ impl Game {
|
||||||
physics,
|
physics,
|
||||||
shipbehaviors,
|
shipbehaviors,
|
||||||
content: ct,
|
content: ct,
|
||||||
|
ui: Ui::new(),
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -140,8 +193,8 @@ impl Game {
|
||||||
self.last_update = Instant::now();
|
self.last_update = Instant::now();
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn get_sprites(&self) -> Vec<Sprite> {
|
pub fn get_object_sprites(&self) -> Vec<ObjectSprite> {
|
||||||
let mut sprites: Vec<Sprite> = Vec::new();
|
let mut sprites: Vec<ObjectSprite> = Vec::new();
|
||||||
|
|
||||||
sprites.append(&mut self.system.get_sprites());
|
sprites.append(&mut self.system.get_sprites());
|
||||||
sprites.extend(self.physics.get_ship_sprites());
|
sprites.extend(self.physics.get_ship_sprites());
|
||||||
|
@ -158,4 +211,10 @@ impl Game {
|
||||||
|
|
||||||
return sprites;
|
return sprites;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
pub fn get_ui_sprites(&self) -> Vec<UiSprite> {
|
||||||
|
return self
|
||||||
|
.ui
|
||||||
|
.build_radar(&self.player, &self.physics, &self.content);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -1,7 +1,7 @@
|
||||||
use cgmath::{Deg, Point3};
|
use cgmath::{Deg, Point3};
|
||||||
use content::{OutfitSpace, TextureHandle};
|
use content::{OutfitSpace, TextureHandle};
|
||||||
|
|
||||||
use crate::{content, render::SubSprite};
|
use crate::{content, render::ObjectSubSprite};
|
||||||
|
|
||||||
/// Represents a gun attached to a specific ship at a certain gunpoint.
|
/// Represents a gun attached to a specific ship at a certain gunpoint.
|
||||||
#[derive(Debug)]
|
#[derive(Debug)]
|
||||||
|
@ -77,7 +77,7 @@ pub struct ShipOutfits {
|
||||||
|
|
||||||
// Minor performance optimization, since we
|
// Minor performance optimization, since we
|
||||||
// rarely need to re-compute these.
|
// rarely need to re-compute these.
|
||||||
engine_flare_sprites: Vec<SubSprite>,
|
engine_flare_sprites: Vec<ObjectSubSprite>,
|
||||||
}
|
}
|
||||||
|
|
||||||
impl<'a> ShipOutfits {
|
impl<'a> ShipOutfits {
|
||||||
|
@ -177,7 +177,7 @@ impl<'a> ShipOutfits {
|
||||||
self.engine_flare_sprites = self
|
self.engine_flare_sprites = self
|
||||||
.enginepoints
|
.enginepoints
|
||||||
.iter()
|
.iter()
|
||||||
.map(|p| SubSprite {
|
.map(|p| ObjectSubSprite {
|
||||||
pos: Point3 {
|
pos: Point3 {
|
||||||
x: p.pos.x,
|
x: p.pos.x,
|
||||||
y: p.pos.y,
|
y: p.pos.y,
|
||||||
|
@ -190,7 +190,7 @@ impl<'a> ShipOutfits {
|
||||||
.collect();
|
.collect();
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn get_engine_flares(&self) -> Vec<SubSprite> {
|
pub fn get_engine_flares(&self) -> Vec<ObjectSubSprite> {
|
||||||
return self.engine_flare_sprites.clone();
|
return self.engine_flare_sprites.clone();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -2,7 +2,7 @@ use cgmath::{Point3, Vector2};
|
||||||
use rand::{self, Rng};
|
use rand::{self, Rng};
|
||||||
|
|
||||||
use super::SystemObject;
|
use super::SystemObject;
|
||||||
use crate::{consts, content, render::Sprite};
|
use crate::{consts, content, render::ObjectSprite};
|
||||||
|
|
||||||
pub struct StarfieldStar {
|
pub struct StarfieldStar {
|
||||||
/// Star coordinates, in world space.
|
/// Star coordinates, in world space.
|
||||||
|
@ -59,7 +59,7 @@ impl System {
|
||||||
return s;
|
return s;
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn get_sprites(&self) -> Vec<Sprite> {
|
pub fn get_sprites(&self) -> Vec<ObjectSprite> {
|
||||||
return self.bodies.iter().map(|x| x.get_sprite()).collect();
|
return self.bodies.iter().map(|x| x.get_sprite()).collect();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -1,7 +1,7 @@
|
||||||
use cgmath::{Deg, Point3};
|
use cgmath::{Deg, Point3};
|
||||||
use galactica_content::TextureHandle;
|
use galactica_content::TextureHandle;
|
||||||
|
|
||||||
use crate::render::Sprite;
|
use crate::render::ObjectSprite;
|
||||||
|
|
||||||
pub struct SystemObject {
|
pub struct SystemObject {
|
||||||
pub sprite_texture: TextureHandle,
|
pub sprite_texture: TextureHandle,
|
||||||
|
@ -11,8 +11,8 @@ pub struct SystemObject {
|
||||||
}
|
}
|
||||||
|
|
||||||
impl SystemObject {
|
impl SystemObject {
|
||||||
pub(super) fn get_sprite(&self) -> Sprite {
|
pub(super) fn get_sprite(&self) -> ObjectSprite {
|
||||||
return Sprite {
|
return ObjectSprite {
|
||||||
texture: self.sprite_texture,
|
texture: self.sprite_texture,
|
||||||
pos: self.pos,
|
pos: self.pos,
|
||||||
angle: self.angle,
|
angle: self.angle,
|
||||||
|
|
|
@ -5,7 +5,7 @@ use rapier2d::{
|
||||||
geometry::{ColliderBuilder, ColliderHandle},
|
geometry::{ColliderBuilder, ColliderHandle},
|
||||||
};
|
};
|
||||||
|
|
||||||
use crate::{physics::util, render::Sprite};
|
use crate::{physics::util, render::ObjectSprite};
|
||||||
|
|
||||||
pub struct ProjectileBuilder {
|
pub struct ProjectileBuilder {
|
||||||
pub rigid_body: RigidBodyBuilder,
|
pub rigid_body: RigidBodyBuilder,
|
||||||
|
@ -51,14 +51,14 @@ impl Projectile {
|
||||||
return self.lifetime < 0.0;
|
return self.lifetime < 0.0;
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn get_sprite(&self, r: &RigidBody) -> Sprite {
|
pub fn get_sprite(&self, r: &RigidBody) -> ObjectSprite {
|
||||||
let pos = util::rigidbody_position(r);
|
let pos = util::rigidbody_position(r);
|
||||||
let rot = util::rigidbody_rotation(r);
|
let rot = util::rigidbody_rotation(r);
|
||||||
|
|
||||||
// Sprites point north at 0 degrees
|
// Sprites point north at 0 degrees
|
||||||
let ang: Deg<f32> = rot.angle(Vector2 { x: 1.0, y: 0.0 }).into();
|
let ang: Deg<f32> = rot.angle(Vector2 { x: 1.0, y: 0.0 }).into();
|
||||||
|
|
||||||
Sprite {
|
ObjectSprite {
|
||||||
texture: self.sprite_texture,
|
texture: self.sprite_texture,
|
||||||
pos: Point3 {
|
pos: Point3 {
|
||||||
x: pos.x,
|
x: pos.x,
|
||||||
|
|
|
@ -13,7 +13,7 @@ use crate::{
|
||||||
content,
|
content,
|
||||||
game::outfits,
|
game::outfits,
|
||||||
physics::{util, ShipHandle},
|
physics::{util, ShipHandle},
|
||||||
render::Sprite,
|
render::ObjectSprite,
|
||||||
};
|
};
|
||||||
|
|
||||||
pub struct ShipTickResult {
|
pub struct ShipTickResult {
|
||||||
|
@ -157,14 +157,14 @@ impl Ship {
|
||||||
return ShipTickResult { projectiles: p };
|
return ShipTickResult { projectiles: p };
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn get_sprite(&self, r: &RigidBody) -> Sprite {
|
pub fn get_sprite(&self, r: &RigidBody) -> ObjectSprite {
|
||||||
let ship_pos = util::rigidbody_position(r);
|
let ship_pos = util::rigidbody_position(r);
|
||||||
let ship_rot = util::rigidbody_rotation(r);
|
let ship_rot = util::rigidbody_rotation(r);
|
||||||
|
|
||||||
// Sprites point north at 0 degrees
|
// Sprites point north at 0 degrees
|
||||||
let ship_ang: Deg<f32> = ship_rot.angle(Vector2 { x: 0.0, y: 1.0 }).into();
|
let ship_ang: Deg<f32> = ship_rot.angle(Vector2 { x: 0.0, y: 1.0 }).into();
|
||||||
|
|
||||||
Sprite {
|
ObjectSprite {
|
||||||
pos: (ship_pos.x, ship_pos.y, 1.0).into(),
|
pos: (ship_pos.x, ship_pos.y, 1.0).into(),
|
||||||
texture: self.sprite_texture,
|
texture: self.sprite_texture,
|
||||||
angle: -ship_ang,
|
angle: -ship_ang,
|
||||||
|
|
|
@ -6,5 +6,5 @@ pub use physics::Physics;
|
||||||
|
|
||||||
use rapier2d::{dynamics::RigidBodyHandle, geometry::ColliderHandle};
|
use rapier2d::{dynamics::RigidBodyHandle, geometry::ColliderHandle};
|
||||||
|
|
||||||
#[derive(Debug, Copy, Clone)]
|
#[derive(Debug, Copy, Clone, PartialEq, Eq)]
|
||||||
pub struct ShipHandle(pub(super) RigidBodyHandle, ColliderHandle);
|
pub struct ShipHandle(pub(super) RigidBodyHandle, ColliderHandle);
|
||||||
|
|
|
@ -10,7 +10,7 @@ use rapier2d::{
|
||||||
use std::{collections::HashMap, f32::consts::PI};
|
use std::{collections::HashMap, f32::consts::PI};
|
||||||
|
|
||||||
use super::{wrapper::Wrapper, ShipHandle};
|
use super::{wrapper::Wrapper, ShipHandle};
|
||||||
use crate::{content, game::outfits, objects, render::Sprite};
|
use crate::{content, game::outfits, objects, render::ObjectSprite};
|
||||||
|
|
||||||
/// Keeps track of all objects in the world that we can interact with.
|
/// Keeps track of all objects in the world that we can interact with.
|
||||||
/// Also wraps our physics engine
|
/// Also wraps our physics engine
|
||||||
|
@ -205,13 +205,13 @@ impl Physics {
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn get_ship_sprites(&self) -> impl Iterator<Item = Sprite> + '_ {
|
pub fn get_ship_sprites(&self) -> impl Iterator<Item = ObjectSprite> + '_ {
|
||||||
self.ships
|
self.ships
|
||||||
.values()
|
.values()
|
||||||
.map(|x| x.get_sprite(&self.wrapper.rigid_body_set[x.physics_handle.0]))
|
.map(|x| x.get_sprite(&self.wrapper.rigid_body_set[x.physics_handle.0]))
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn get_projectile_sprites(&self) -> impl Iterator<Item = Sprite> + '_ {
|
pub fn get_projectile_sprites(&self) -> impl Iterator<Item = ObjectSprite> + '_ {
|
||||||
self.projectiles
|
self.projectiles
|
||||||
.values()
|
.values()
|
||||||
.map(|x| x.get_sprite(&self.wrapper.rigid_body_set[x.rigid_body]))
|
.map(|x| x.get_sprite(&self.wrapper.rigid_body_set[x.rigid_body]))
|
||||||
|
|
|
@ -4,20 +4,24 @@ use cgmath::{Deg, EuclideanSpace, Matrix4, Point2, Vector2, Vector3};
|
||||||
use galactica_content::Content;
|
use galactica_content::Content;
|
||||||
use std::{iter, rc::Rc};
|
use std::{iter, rc::Rc};
|
||||||
use wgpu;
|
use wgpu;
|
||||||
use winit::{self, dpi::PhysicalSize, window::Window};
|
use winit::{
|
||||||
|
self,
|
||||||
|
dpi::{LogicalSize, PhysicalSize},
|
||||||
|
window::Window,
|
||||||
|
};
|
||||||
|
|
||||||
use super::{
|
use super::{
|
||||||
consts::{OPENGL_TO_WGPU_MATRIX, SPRITE_INSTANCE_LIMIT, STARFIELD_INSTANCE_LIMIT},
|
consts::{OPENGL_TO_WGPU_MATRIX, SPRITE_INSTANCE_LIMIT, STARFIELD_INSTANCE_LIMIT},
|
||||||
globaldata::{GlobalData, GlobalDataContent},
|
globaldata::{GlobalData, GlobalDataContent},
|
||||||
pipeline::PipelineBuilder,
|
pipeline::PipelineBuilder,
|
||||||
sprite::SubSprite,
|
sprite::ObjectSubSprite,
|
||||||
texturearray::TextureArray,
|
texturearray::TextureArray,
|
||||||
vertexbuffer::{
|
vertexbuffer::{
|
||||||
consts::{SPRITE_INDICES, SPRITE_VERTICES},
|
consts::{SPRITE_INDICES, SPRITE_VERTICES},
|
||||||
types::{SpriteInstance, StarfieldInstance, TexturedVertex},
|
types::{SpriteInstance, StarfieldInstance, TexturedVertex},
|
||||||
VertexBuffer,
|
VertexBuffer,
|
||||||
},
|
},
|
||||||
Sprite,
|
ObjectSprite, UiSprite,
|
||||||
};
|
};
|
||||||
use crate::{consts, game::Game};
|
use crate::{consts, game::Game};
|
||||||
|
|
||||||
|
@ -197,15 +201,15 @@ impl GPUState {
|
||||||
self.update_starfield_buffer(game)
|
self.update_starfield_buffer(game)
|
||||||
}
|
}
|
||||||
|
|
||||||
/// Create a SpriteInstance for s and add it to instances.
|
/// Create a SpriteInstance for an object and add it to `instances`.
|
||||||
/// Also handles child sprites.
|
/// Also handles child sprites.
|
||||||
fn push_sprite(
|
fn push_object_sprite(
|
||||||
&self,
|
&self,
|
||||||
game: &Game,
|
game: &Game,
|
||||||
instances: &mut Vec<SpriteInstance>,
|
instances: &mut Vec<SpriteInstance>,
|
||||||
clip_ne: Point2<f32>,
|
clip_ne: Point2<f32>,
|
||||||
clip_sw: Point2<f32>,
|
clip_sw: Point2<f32>,
|
||||||
s: Sprite,
|
s: ObjectSprite,
|
||||||
) {
|
) {
|
||||||
// Position adjusted for parallax
|
// Position adjusted for parallax
|
||||||
// TODO: adjust parallax for zoom?
|
// TODO: adjust parallax for zoom?
|
||||||
|
@ -284,18 +288,18 @@ impl GPUState {
|
||||||
// Add children
|
// Add children
|
||||||
if let Some(children) = s.children {
|
if let Some(children) = s.children {
|
||||||
for c in children {
|
for c in children {
|
||||||
self.push_subsprite(game, instances, c, pos, s.angle);
|
self.push_object_subsprite(game, instances, c, pos, s.angle);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/// Add a sprite's subsprite to instance.
|
/// Add an object sprite's subsprite to `instances`.
|
||||||
/// Only called by push_sprite.
|
/// Only called by `self.push_object_sprite`.
|
||||||
fn push_subsprite(
|
fn push_object_subsprite(
|
||||||
&self,
|
&self,
|
||||||
game: &Game,
|
game: &Game,
|
||||||
instances: &mut Vec<SpriteInstance>,
|
instances: &mut Vec<SpriteInstance>,
|
||||||
s: SubSprite,
|
s: ObjectSubSprite,
|
||||||
parent_pos: Point2<f32>,
|
parent_pos: Point2<f32>,
|
||||||
parent_angle: Deg<f32>,
|
parent_angle: Deg<f32>,
|
||||||
) {
|
) {
|
||||||
|
@ -332,6 +336,41 @@ impl GPUState {
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// Create a SpriteInstance for a ui sprite and add it to `instances`
|
||||||
|
fn push_ui_sprite(&self, instances: &mut Vec<SpriteInstance>, s: UiSprite) {
|
||||||
|
let logical_size: LogicalSize<f32> =
|
||||||
|
self.window_size.to_logical(self.window.scale_factor());
|
||||||
|
|
||||||
|
let texture = self.texture_array.get_texture(s.texture);
|
||||||
|
let width = s.dimensions.x;
|
||||||
|
let height = s.dimensions.y;
|
||||||
|
|
||||||
|
let scale = Matrix4::from_nonuniform_scale(
|
||||||
|
width / logical_size.width,
|
||||||
|
height / logical_size.height,
|
||||||
|
1.0,
|
||||||
|
);
|
||||||
|
let rotate = Matrix4::from_angle_z(s.angle);
|
||||||
|
let translate = Matrix4::from_translation(match s.pos {
|
||||||
|
super::AnchoredUiPosition::NorthWest(p) => Vector3 {
|
||||||
|
// Note the signs. Positive y points north!
|
||||||
|
x: -1.0 + (width / 2.0 + p.x) / (logical_size.width / 2.0),
|
||||||
|
y: 1.0 - (height / 2.0 - p.y) / (logical_size.height / 2.0),
|
||||||
|
z: 0.0,
|
||||||
|
},
|
||||||
|
_ => Vector3 {
|
||||||
|
x: 0.0,
|
||||||
|
y: 0.0,
|
||||||
|
z: 0.0,
|
||||||
|
},
|
||||||
|
});
|
||||||
|
|
||||||
|
instances.push(SpriteInstance {
|
||||||
|
transform: (OPENGL_TO_WGPU_MATRIX * translate * rotate * scale).into(),
|
||||||
|
texture_index: texture.index,
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
/// Make a SpriteInstance for each of the game's visible sprites.
|
/// Make a SpriteInstance for each of the game's visible sprites.
|
||||||
/// Will panic if SPRITE_INSTANCE_LIMIT is exceeded.
|
/// Will panic if SPRITE_INSTANCE_LIMIT is exceeded.
|
||||||
///
|
///
|
||||||
|
@ -344,8 +383,12 @@ impl GPUState {
|
||||||
let clip_ne = Point2::from((-self.window_aspect, 1.0)) * game.camera.zoom;
|
let clip_ne = Point2::from((-self.window_aspect, 1.0)) * game.camera.zoom;
|
||||||
let clip_sw = Point2::from((self.window_aspect, -1.0)) * game.camera.zoom;
|
let clip_sw = Point2::from((self.window_aspect, -1.0)) * game.camera.zoom;
|
||||||
|
|
||||||
for s in game.get_sprites() {
|
for s in game.get_object_sprites() {
|
||||||
self.push_sprite(game, &mut instances, clip_ne, clip_sw, s);
|
self.push_object_sprite(game, &mut instances, clip_ne, clip_sw, s);
|
||||||
|
}
|
||||||
|
|
||||||
|
for s in game.get_ui_sprites() {
|
||||||
|
self.push_ui_sprite(&mut instances, s);
|
||||||
}
|
}
|
||||||
|
|
||||||
// Enforce sprite limit
|
// Enforce sprite limit
|
||||||
|
|
|
@ -7,4 +7,4 @@ mod texturearray;
|
||||||
mod vertexbuffer;
|
mod vertexbuffer;
|
||||||
|
|
||||||
pub use gpustate::GPUState;
|
pub use gpustate::GPUState;
|
||||||
pub use sprite::{Sprite, SubSprite};
|
pub use sprite::{AnchoredUiPosition, ObjectSprite, ObjectSubSprite, UiSprite};
|
||||||
|
|
|
@ -1,12 +1,46 @@
|
||||||
use cgmath::{Deg, Point3};
|
use cgmath::{Deg, Point2, Point3};
|
||||||
use galactica_content::TextureHandle;
|
use galactica_content::TextureHandle;
|
||||||
|
|
||||||
|
/// The location of a UI element, in one of a few
|
||||||
|
/// possible coordinate systems.
|
||||||
|
///
|
||||||
|
/// Positive Y always points up,
|
||||||
|
/// positive X always points right.
|
||||||
#[derive(Debug, Clone)]
|
#[derive(Debug, Clone)]
|
||||||
pub struct Sprite {
|
pub enum AnchoredUiPosition {
|
||||||
/// The sprite texture to draw
|
/// Position of this sprite's nw corner,
|
||||||
|
/// relative to the nw corner of the window.
|
||||||
|
NorthWest(Point2<f32>),
|
||||||
|
|
||||||
|
/// Position of this sprite's sw corner,
|
||||||
|
/// relative to the sw corner of the window.
|
||||||
|
SouthWest(Point2<f32>),
|
||||||
|
}
|
||||||
|
|
||||||
|
/// A sprite that represents a ui element
|
||||||
|
#[derive(Debug, Clone)]
|
||||||
|
pub struct UiSprite {
|
||||||
|
/// The texture to use for this sprite
|
||||||
pub texture: TextureHandle,
|
pub texture: TextureHandle,
|
||||||
|
|
||||||
/// This object's position, in world coordinates.
|
/// This object's position, in logical (dpi-adjusted) pixels
|
||||||
|
pub pos: AnchoredUiPosition,
|
||||||
|
|
||||||
|
/// The size of this sprite, in logical (dpi-adjusted) pixels
|
||||||
|
pub dimensions: Point2<f32>,
|
||||||
|
|
||||||
|
/// This sprite's rotation, measured ccw
|
||||||
|
pub angle: Deg<f32>,
|
||||||
|
}
|
||||||
|
|
||||||
|
/// A sprite that represents a world object:
|
||||||
|
/// Ships, planets, debris, etc
|
||||||
|
#[derive(Debug, Clone)]
|
||||||
|
pub struct ObjectSprite {
|
||||||
|
/// The texture to use for this sprite
|
||||||
|
pub texture: TextureHandle,
|
||||||
|
|
||||||
|
/// This object's center, in world coordinates.
|
||||||
pub pos: Point3<f32>,
|
pub pos: Point3<f32>,
|
||||||
|
|
||||||
/// The size of this sprite,
|
/// The size of this sprite,
|
||||||
|
@ -15,14 +49,15 @@ pub struct Sprite {
|
||||||
|
|
||||||
/// This sprite's rotation
|
/// This sprite's rotation
|
||||||
/// (relative to north, measured ccw)
|
/// (relative to north, measured ccw)
|
||||||
|
/// Note that this is different from the angle used by our physics system.
|
||||||
pub angle: Deg<f32>,
|
pub angle: Deg<f32>,
|
||||||
|
|
||||||
/// Sprites that should be drawn relative to this sprite.
|
/// Sprites that should be drawn relative to this sprite.
|
||||||
pub children: Option<Vec<SubSprite>>,
|
pub children: Option<Vec<ObjectSubSprite>>,
|
||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Debug, Clone)]
|
#[derive(Debug, Clone)]
|
||||||
pub struct SubSprite {
|
pub struct ObjectSubSprite {
|
||||||
/// The sprite texture to draw
|
/// The sprite texture to draw
|
||||||
pub texture: TextureHandle,
|
pub texture: TextureHandle,
|
||||||
|
|
||||||
|
|
Loading…
Reference in New Issue