Expand description
A thin game engine (hence the name). Drawing done with glium
, game variables done with
glium-types
, windowing done with winit
and input done with winit-input-map
. It has easy fxaa
support and low boilerplate despite having lots of control.
use thin_engine::{prelude::*, meshes::screen};
use std::{cell::RefCell, rc::Rc};
use Action::*;
#[derive(Hash, PartialEq, Eq, Clone, Copy)]
enum Action {
Left,
Right,
Jump,
Exit
}
let event_loop = EventLoop::new().unwrap();
event_loop.set_control_flow(ControlFlow::Poll);
let mut input = { use base_input_codes::*; input_map!(
(Left, KeyA, MouseButton::Left, ArrowLeft, DPadLeft),
(Right, KeyD, MouseButton::Right, ArrowRight, DPadRight),
(Jump, KeyW, ArrowUp, Space, GamepadInput::South),
(Exit, Escape, GamepadInput::Start)
)};
struct Graphics {
box_indices: IndexBuffer<u32>,
box_vertices: VertexBuffer<Vertex>,
box_uvs: VertexBuffer<TextureCoords>,
box_normals: VertexBuffer<Normal>,
box_shader: Program
}
let graphics: Rc<RefCell<Option<Graphics>>> = Rc::default();
let graphics_setup = graphics.clone();
let mut player_pos = Vec2::ZERO;
let mut player_gravity = 0.0;
let mut player_can_jump = true;
// camera matrix must be inverse
let camera = Mat4::from_scale(Vec3::splat(10.0)).inverse();
let settings = Settings::from_fps(60); // target of 60 fps
let mut frame_start = Instant::now();
thin_engine::builder(input).with_setup(move |display, window, _| {
// some computers will panic when a vertex buffer is used but not passed a value. so we must
// initialise empty vertex buffers.
let (box_indices, box_vertices, box_uvs, box_normals) = mesh!(
display, &screen::INDICES, &screen::VERTICES,
&[] as &[TextureCoords; 0], &[] as &[Normal; 0]
);
let box_shader = Program::from_source(
display, shaders::VERTEX,
"#version 140
out vec4 colour;
void main() {
colour = vec4(1.0, 0.0, 0.0, 1.0);
}", None
).unwrap();
graphics_setup.replace(Some(Graphics {
box_vertices, box_uvs, box_normals, box_indices, box_shader
}));
}).with_update(move |input, display, _settings, target, window| {
// gets time between frames
let delta_time = frame_start.elapsed().as_secs_f32();
frame_start = Instant::now();
if input.pressed(Exit) { target.exit() }
// game logic
player_pos.x += input.axis(Right, Left) * 10.0 * delta_time;
player_gravity += delta_time * 50.0;
player_pos.y -= player_gravity * delta_time;
if player_pos.y < 0.0 {
player_pos.y = 0.0;
player_can_jump = true;
}
if player_can_jump && input.pressed(Jump) {
player_gravity = -20.0;
player_can_jump = false;
}
let graphics = graphics.borrow();
let Graphics {
box_vertices, box_uvs, box_normals, box_indices, box_shader
} = graphics.as_ref().unwrap();
// set up frame
let mut frame = display.draw();
let view2d = Mat4::view_matrix_2d(frame.get_dimensions());
// draw
frame.clear_color(0.0, 0.0, 0.0, 1.0);
frame.draw(
(box_vertices, box_uvs, box_normals), box_indices,
box_shader, &uniform! {
view: view2d, camera: camera,
model: Mat4::from_pos(player_pos.extend(0.0)),
}, &DrawParameters::default()
);
window.pre_present_notify();
frame.finish().unwrap();
}).with_settings(Settings::from_fps(60))
.build(event_loop).unwrap();
Re-exports§
pub use gilrs;
pub use glium;
pub use glium_types;
pub use winit;
pub use winit_input_map as input_map;
Modules§
Structs§
- Resizable
Depth Texture2d - resizable depth texture. use with gliums
SimpleFrameBuffer::WithDepthTexture()
to create a texture you can draw on! usefull for things like fog and fxaa. - Resizable
Texture2d - resizable depth texture. recomended to use with gliums
SimpleFrameBuffer
to draw onto a texture you can use in another shader! usefull for fxaa - Settings
- run time settings for thin engine including gamepad settings (through gilrs) and fps settings.
when running
default()
the gamepads may fail to initialise and the program will continue running after printing the error. if this is undesirable usewith_gamepads()
instead.