X-Git-Url: https://codewiz.org/gitweb?a=blobdiff_plain;f=text.rs;h=e020156cd08956f226d9c36c0117dcaa24069452;hb=29b275596efed3b3064072483aa6d8c4cba1e3d4;hp=ff87a793417ca02328c7a7d7f6cb6a16ef8c6935;hpb=decdaf948575e3d519086f6af6200c2a60cf00d6;p=mandelwow.git diff --git a/text.rs b/text.rs index ff87a79..e020156 100644 --- a/text.rs +++ b/text.rs @@ -1,9 +1,48 @@ use cgmath::conv::array4x4; -use cgmath::{Matrix4, One}; +use cgmath::Matrix4; use glium; -use glium::{Surface, texture}; -use image; -use std::io::Cursor; +use glium::{Display, Program, Surface, implement_vertex, texture, uniform}; +use std; + +fn gamma(x: T) -> f32 +where + f32: From, + T: Copy, +{ + ((f32::from(x)) / 255.).powf(2.2) +} + +fn srgb(c: [T; 3]) -> [f32; 4] +where + f32: From, + T: Copy, +{ + [gamma(c[0]), gamma(c[1]), gamma(c[2]), 0.0] +} + +#[cfg(feature = "image")] +fn c64_font() -> (u32, u32, Vec) { + let image = image::load_from_memory_with_format( + &include_bytes!("textures/c64-font.png")[..], + image::PNG, + ).unwrap() + .to_luma(); + let (w, h) = image.dimensions(); + (w, h, image.into_raw()) +} + +#[cfg(not(feature = "image"))] +fn c64_font() -> (u32, u32, Vec) { + let pixels = &include_bytes!("textures/c64-font.gray")[..]; + (128, 128, Vec::from(pixels)) +} + +pub fn text_program(display: &Display) -> Program { + //load_program(display, "shaders/text.vert", "shaders/text.frag"); + let vertex_shader_src = include_str!("shaders/text.vert"); + let fragment_shader_src = include_str!("shaders/text.frag"); + Program::from_source(display, vertex_shader_src, fragment_shader_src, None).unwrap() +} #[derive(Copy, Clone)] struct Vertex { @@ -12,24 +51,29 @@ struct Vertex { } implement_vertex!(Vertex, position, tex_coords); -pub struct Text<'a> { - tex: texture::CompressedSrgbTexture2d, +pub struct Text { + tex: texture::Texture2d, vertex_buffer: glium::VertexBuffer, index_buffer: glium::IndexBuffer, program: glium::Program, - params: glium::DrawParameters<'a>, - model: Matrix4, + params: glium::DrawParameters<'static>, } -impl<'a> Text<'a> { - pub fn new(display: &glium::Display) -> Text { - let image = image::load(Cursor::new(&include_bytes!("c64-font.png")[..]), image::PNG) - .unwrap() - .to_rgba(); - let dimensions = image.dimensions(); - let image = - glium::texture::RawImage2d::from_raw_rgba_reversed(image.into_raw(), dimensions); - let tex = glium::texture::CompressedSrgbTexture2d::new(display, image).unwrap(); +impl Text { + pub fn new(display: &Display) -> Text { + let (w, h, pixels) = c64_font(); + let image = glium::texture::RawImage2d { + data: std::borrow::Cow::from(pixels), + width: w, + height: h, + format: glium::texture::ClientFormat::U8, + }; + let tex = glium::texture::Texture2d::with_format( + display, + image, + glium::texture::UncompressedFloatFormat::U8, + glium::texture::MipmapsOption::NoMipmap, + ).unwrap(); // building the vertex buffer, which contains all the vertices that we will draw let vertex_buffer = { @@ -37,21 +81,21 @@ impl<'a> Text<'a> { display, &[ Vertex { - position: [-1.0, -1.0], - tex_coords: [0.0, 0.0], - }, - Vertex { - position: [-1.0, 1.0], + position: [-0.5, -0.5], tex_coords: [0.0, 1.0], }, Vertex { - position: [1.0, 1.0], - tex_coords: [1.0, 1.0], + position: [-0.5, 0.5], + tex_coords: [0.0, 0.0], }, Vertex { - position: [1.0, -1.0], + position: [0.5, 0.5], tex_coords: [1.0, 0.0], }, + Vertex { + position: [0.5, -0.5], + tex_coords: [1.0, 1.0], + }, ], ).unwrap() }; @@ -62,44 +106,6 @@ impl<'a> Text<'a> { &[1 as u16, 2, 0, 3], ).unwrap(); - // compiling shaders and linking them together - let program = program!(display, - 140 => { - vertex: " - #version 140 - - uniform mat4 model; - uniform mat4 perspview; - uniform int index; - - in vec2 position; - in vec2 tex_coords; - - out vec2 v_tex_coords; - - void main() { - gl_Position = perspview * model * vec4(position, 0.0, 1.0); - - // Characters are arranged in a 16x16 square. - // Texture oordinates originate in the bottom-left corner. - int xpos = index % 16; - int ypos = 15 - index / 16; - v_tex_coords = (tex_coords) / 16.0 + vec2(xpos / 16., ypos / 16.); - } - ", - - fragment: " - #version 140 - uniform sampler2D tex; - in vec2 v_tex_coords; - out vec4 f_color; - - void main() { - f_color = texture(tex, v_tex_coords); - } - " - }).unwrap(); - let params = glium::DrawParameters { depth: glium::Depth { test: glium::draw_parameters::DepthTest::IfLess, @@ -111,22 +117,25 @@ impl<'a> Text<'a> { }; Text { - model: Matrix4::one(), tex: tex, vertex_buffer: vertex_buffer, index_buffer: index_buffer, - program: program, + program: text_program(display), params: params, } } - pub fn draw(&self, frame: &mut glium::Frame, perspview: &[[f32; 4]; 4]) { - let uniforms = uniform! { - model: array4x4(self.model), + pub fn draw(&self, frame: &mut glium::Frame, c: char, model: &Matrix4, perspview: &[[f32; 4]; 4]) { + let uniforms = + uniform! { + model: array4x4(*model), perspview: *perspview, tex: self.tex.sampled() .magnify_filter(glium::uniforms::MagnifySamplerFilter::Nearest), - index: 'A' as i32, + index: c as i32, + // RGB values from http://unusedino.de/ec64/technical/misc/vic656x/colors/ + bgcolor: srgb([ 64, 50, 133u8]), // 6 - blue + fgcolor: srgb([120, 106, 189u8]), // 14 - light blue }; frame .draw(