type-render
korin 3 years ago
commit 289c318804
  1. 31
      src/_catlas.rs
  2. 14
      src/font_build.rs
  3. 234
      src/main.rs

@ -0,0 +1,31 @@
//let sdl_context = sdl2::init()?;
//let video_subsys = sdl_context.video()?;
//let ttf_context = sdl2::ttf::init().map_err(|e| e.to_string())?;
const GLYPH_METRICS_CAPACITY: usize = 128;
struct GlyphMetric {
ax: f32, // advance.x
ay: f32, // advance.y
bw: f32, // bitmap.width;
bh: f32, // bitmap.rows;
bl: f32, // bitmap_left;
bt: f32, // bitmap_top;
tx: f32, // x offset of glyph in texture coordinates
}
struct FreeGlyphAtlas {
atlas_width: usize, // TODO: Get FT_Uint from FT2build
atlas_height: usize,
glyphs_texture: GLuint,
metrics: [GlyphMetric; GLYPH_METRICS_CAPACITY],
}
fn free_glyph_atlas_init(atlas: FreeGlyphAtlas, face: FT_Face) {
for i in 32..127 {
// something something sdl2::ttf::GlyphMetrics
}
}

@ -0,0 +1,14 @@
use std::fs;
struct TypeFace {
type_char: [[bool; 8]; 14],
}
fn get_font() {
let file_path = "./fonts/Terminus14x8.data";
println!("In file {}", file_path);
let contents = fs::read_to_string(file_path)
.expect("File could not be read");
}

@ -0,0 +1,234 @@
extern crate sdl2;
use std::path::Path;
use sdl2::event::Event;
use sdl2::keyboard::Keycode;
use sdl2::pixels::Color;
use sdl2::rect::Rect;
use sdl2::render::TextureQuery;
//mod _catlas;
//use _catlas::*;
mod font_build;
use font_build::*;
static SCREEN_WIDTH: u32 = 1680;
static SCREEN_HEIGHT: u32 = 945;
struct ModifierKeys {
alt: bool,
ctrl: bool,
shift: bool,
}
// handle the annoying Rect i32
macro_rules! rect(
($x:expr, $y:expr, $w:expr, $h:expr) => (
Rect::new($x as i32, $y as i32, $w as u32, $h as u32)
)
);
// Scale fonts to a reasonable size when they're too big (though they might look less smooth)
/*
fn get_centered_rect(rect_width: u32, rect_height: u32, cons_width: u32, cons_height: u32) -> Rect {
let wr = rect_width as f32 / cons_width as f32;
let hr = rect_height as f32 / cons_height as f32;
let (w, h) = if wr > 1f32 || hr > 1f32 {
if wr > hr {
println!("Scaling down! The text will look worse!");
let h = (rect_height as f32 / wr) as i32;
(cons_width as i32, h)
} else {
println!("Scaling down! The text will look worse!");
let w = (rect_width as f32 / hr) as i32;
(w, cons_height as i32)
}
} else {
(rect_width as i32, rect_height as i32)
};
let cx = (SCREEN_WIDTH as i32 - w) / 2;
let cy = (SCREEN_HEIGHT as i32 - h) / 2;
rect!(cx, cy, w, h)
}
*/
fn get_corner_rect(rect_width: u32, rect_height: u32) -> Rect {
let (w,h) = (rect_width as i32, rect_height as i32);
let cx = 15;
let cy = 15;
rect!(cx, cy, w, h)
}
pub fn main() -> Result<(), String> {
let font_path: &Path = Path::new("./fonts/Monoid-Regular.ttf");
let sdl_context = sdl2::init()?;
let video_subsys = sdl_context.video()?;
let ttf_context = sdl2::ttf::init().map_err(|e| e.to_string())?;
let window = video_subsys
.window("SDL2_TTF Example", SCREEN_WIDTH, SCREEN_HEIGHT)
.position_centered()
.opengl()
.build()
.map_err(|e| e.to_string())?;
let mut canvas = window.into_canvas().build().map_err(|e| e.to_string())?;
let texture_creator = canvas.texture_creator();
// Load a font
let mut font = ttf_context.load_font(font_path, 12)?;
font.set_style(sdl2::ttf::FontStyle::BOLD);
let mut buffer = String::new();
let mut cursor_position = 0;
let mut draw_text = |text: &str| -> Result<(), String> {
// render a surface, and convert it to a texture bound to the canvas
let surface = font
.render(text)
.blended(Color::RGBA(255, 255, 255, 255))
.map_err(|e| e.to_string())?;
let texture = texture_creator
.create_texture_from_surface(&surface)
.map_err(|e| e.to_string())?;
canvas.set_draw_color(Color::RGB(32, 32, 32));
canvas.clear();
let TextureQuery { width, height, .. } = texture.query();
// If the example text is too big for the screen, downscale it (and center regardless)
// let padding = 64;
let target = get_corner_rect(
width,
height,
);
canvas.copy(&texture, None, Some(target))?;
canvas.present();
Ok(())
};
let mut modifier_keys = ModifierKeys {alt: false, ctrl: false, shift: false};
'mainloop: loop {
for event in sdl_context.event_pump()?.poll_iter() {
match event {
// ESC or SIGKILL
Event::KeyDown { keycode: Some(Keycode::Escape), .. } |
Event::Quit { .. } => break 'mainloop,
// ALT down
Event::KeyDown { keycode: Some(Keycode::LAlt), .. } |
Event::KeyDown { keycode: Some(Keycode::RAlt), .. } => {
modifier_keys.alt = true
},
// ALT up
Event::KeyUp { keycode: Some(Keycode::LAlt), .. } |
Event::KeyUp { keycode: Some(Keycode::RAlt), .. } => {
modifier_keys.alt = false
},
// CTRL down
Event::KeyDown { keycode: Some(Keycode::LCtrl), .. } |
Event::KeyDown { keycode: Some(Keycode::RCtrl), .. } => {
modifier_keys.ctrl = true
},
// CTRL up
Event::KeyUp { keycode: Some(Keycode::LCtrl), .. } |
Event::KeyUp { keycode: Some(Keycode::RCtrl), .. } => {
modifier_keys.ctrl = false
},
// SHIFT down
Event::KeyDown { keycode: Some(Keycode::LShift), .. } |
Event::KeyDown { keycode: Some(Keycode::RShift), .. } => {
modifier_keys.shift = true
},
// SHIFT up
Event::KeyUp { keycode: Some(Keycode::LShift), .. } |
Event::KeyUp { keycode: Some(Keycode::RShift), .. } => {
modifier_keys.shift = false
},
// Ignore SUPER
Event::KeyDown { keycode: Some(Keycode::LGui), .. } |
Event::KeyDown { keycode: Some(Keycode::RGui), .. } => (),
// Type spacebar
Event::KeyDown { keycode: Some(Keycode::Space), .. } => {
buffer.insert(cursor_position, ' ');
cursor_position += 1;
draw_text(&buffer)?
},
// Backspace
Event::KeyDown { keycode: Some(Keycode::Backspace), .. } => {
buffer.remove(cursor_position - 1);
cursor_position -= 1;
draw_text(&buffer)?
},
// Enter
Event::KeyDown { keycode: Some(Keycode::Return), .. } => {
let key = '\n';
buffer.insert(cursor_position, key);
cursor_position += 1;
draw_text(&buffer)?
},
// Left/Back arrow
Event::KeyDown { keycode: Some(Keycode::Left), .. } => {
cursor_position = usize::checked_sub(cursor_position, 1)
.unwrap_or(0)
},
// Home key
Event::KeyDown { keycode: Some(Keycode::Home), .. } => {
cursor_position = 0
},
// End key
Event::KeyDown { keycode: Some(Keycode::End), .. } => {
cursor_position = buffer.len()
},
// Right/Forward arrow
Event::KeyDown { keycode: Some(Keycode::Right), .. } => {
cursor_position = (cursor_position + 1).min(buffer.len())
},
Event::KeyDown { keycode, .. } => {
let key = keycode.unwrap().to_string();
// Ignore multi-char keycodes
if key.len() > 1 { break }
let key_case = match modifier_keys.shift {
true => key.to_uppercase(),
false => key.to_lowercase()
}.chars().nth(0).expect("Empty");
buffer.insert(cursor_position, key_case);
cursor_position += 1;
draw_text(&buffer)?;
println!("{key}");
},
_ => {}
}
}
}
Ok(())
}
Loading…
Cancel
Save