fancy text
This commit is contained in:
@@ -8,6 +8,7 @@ layout(push_constant) uniform PushConstants {
|
|||||||
layout(binding = 0) uniform ObjectUniformData {
|
layout(binding = 0) uniform ObjectUniformData {
|
||||||
mat4 view;
|
mat4 view;
|
||||||
mat4 projection;
|
mat4 projection;
|
||||||
|
mat4 ortho_projection;
|
||||||
float time;
|
float time;
|
||||||
vec3 light_position;
|
vec3 light_position;
|
||||||
vec3 light_directional_rotation;
|
vec3 light_directional_rotation;
|
||||||
|
|||||||
Binary file not shown.
@@ -8,6 +8,7 @@ layout(push_constant) uniform PushConstants {
|
|||||||
layout(binding = 0) uniform ObjectUniformData {
|
layout(binding = 0) uniform ObjectUniformData {
|
||||||
mat4 view;
|
mat4 view;
|
||||||
mat4 projection;
|
mat4 projection;
|
||||||
|
mat4 ortho_projection;
|
||||||
float time;
|
float time;
|
||||||
vec3 light_position;
|
vec3 light_position;
|
||||||
vec3 light_directional_rotation;
|
vec3 light_directional_rotation;
|
||||||
@@ -16,7 +17,6 @@ layout(binding = 0) uniform ObjectUniformData {
|
|||||||
|
|
||||||
layout(location = 0) in vec3 position;
|
layout(location = 0) in vec3 position;
|
||||||
layout(location = 1) in vec2 uv;
|
layout(location = 1) in vec2 uv;
|
||||||
layout(location = 2) in vec3 normal;
|
|
||||||
|
|
||||||
layout(location = 0) out vec2 tex_coords;
|
layout(location = 0) out vec2 tex_coords;
|
||||||
|
|
||||||
@@ -25,15 +25,16 @@ out gl_PerVertex {
|
|||||||
};
|
};
|
||||||
|
|
||||||
void main() {
|
void main() {
|
||||||
|
float scale = 0.01;
|
||||||
mat4 invert = mat4(
|
mat4 invert = mat4(
|
||||||
1., 0., 0., 0.,
|
scale, 0., 0., 0.,
|
||||||
0., -1., 0., 0.,
|
0., scale, 0., 0.,
|
||||||
0., 0., 1., 0.,
|
0., 0., scale, 0.,
|
||||||
0., 0., 0., 1.
|
0., 0., 0., 1.
|
||||||
);
|
);
|
||||||
|
|
||||||
// Vertex position in camera
|
// Vertex position in camera
|
||||||
gl_Position = ubo.projection * ubo.view * invert * push.model * vec4(position, 1.0);
|
gl_Position = ubo.ortho_projection * vec4(position, 1.0);
|
||||||
|
|
||||||
// Just interpolate UV coords, no transformation needed
|
// Just interpolate UV coords, no transformation needed
|
||||||
tex_coords = uv;
|
tex_coords = uv;
|
||||||
|
|||||||
Binary file not shown.
@@ -9,6 +9,7 @@ layout(push_constant) uniform PushConstants {
|
|||||||
layout(binding = 0) uniform ObjectUniformData {
|
layout(binding = 0) uniform ObjectUniformData {
|
||||||
mat4 view;
|
mat4 view;
|
||||||
mat4 projection;
|
mat4 projection;
|
||||||
|
mat4 ortho_projection;
|
||||||
float time;
|
float time;
|
||||||
vec3 light_position;
|
vec3 light_position;
|
||||||
vec3 light_directional_rotation;
|
vec3 light_directional_rotation;
|
||||||
|
|||||||
Binary file not shown.
@@ -9,6 +9,7 @@ layout(push_constant) uniform PushConstants {
|
|||||||
layout(binding = 0) uniform ObjectUniformData {
|
layout(binding = 0) uniform ObjectUniformData {
|
||||||
mat4 view;
|
mat4 view;
|
||||||
mat4 projection;
|
mat4 projection;
|
||||||
|
mat4 ortho_projection;
|
||||||
float time;
|
float time;
|
||||||
vec3 light_position;
|
vec3 light_position;
|
||||||
vec3 light_directional_rotation;
|
vec3 light_directional_rotation;
|
||||||
|
|||||||
Binary file not shown.
@@ -3,7 +3,7 @@ use cgmath::{Deg, Euler, Quaternion, vec3};
|
|||||||
use glyph_brush::{BrushAction, BrushError, GlyphBrushBuilder, Section, Text};
|
use glyph_brush::{BrushAction, BrushError, GlyphBrushBuilder, Section, Text};
|
||||||
use glyph_brush::ab_glyph::FontArc;
|
use glyph_brush::ab_glyph::FontArc;
|
||||||
use vulkano::format::Format;
|
use vulkano::format::Format;
|
||||||
use vulkano::sampler::Filter;
|
use vulkano::sampler::{Filter, SamplerAddressMode};
|
||||||
use winit::event::Event;
|
use winit::event::Event;
|
||||||
|
|
||||||
use level::{load_level, save_level};
|
use level::{load_level, save_level};
|
||||||
@@ -89,6 +89,7 @@ impl Game for TestGame {
|
|||||||
ObjectUniformData {
|
ObjectUniformData {
|
||||||
view: self.player.camera.view.into(),
|
view: self.player.camera.view.into(),
|
||||||
projection: self.player.camera.proj.into(),
|
projection: self.player.camera.proj.into(),
|
||||||
|
ortho_projection: self.player.camera.ortho_proj.into(),
|
||||||
time,
|
time,
|
||||||
light_position: light_pos.into(),
|
light_position: light_pos.into(),
|
||||||
light_directional_rotation: [45.0, 45.0, 0.0],
|
light_directional_rotation: [45.0, 45.0, 0.0],
|
||||||
@@ -120,27 +121,32 @@ impl TestGame {
|
|||||||
|
|
||||||
let font = FontArc::try_from_slice(include_bytes!("../../models/OverpassRegular.ttf")).unwrap();
|
let font = FontArc::try_from_slice(include_bytes!("../../models/OverpassRegular.ttf")).unwrap();
|
||||||
let mut glyph_brush = GlyphBrushBuilder::using_font(font).build();
|
let mut glyph_brush = GlyphBrushBuilder::using_font(font).build();
|
||||||
glyph_brush.queue(Section::default().add_text(Text::new("penis lol")));
|
|
||||||
|
let mut tex_min_size = None;
|
||||||
|
let mut tex_max_size = None;
|
||||||
|
|
||||||
|
glyph_brush.queue(Section::default().add_text(Text::new("penis lol").with_scale(100.)));
|
||||||
match glyph_brush.process_queued(|rect, text_data| {
|
match glyph_brush.process_queued(|rect, text_data| {
|
||||||
renderer.upload_texture(text_data, rect.width(), rect.height(), Format::R8Unorm, Filter::Nearest, renderer.device.clone());
|
renderer.upload_texture(text_data, rect.width(), rect.height(), Format::R8Unorm, Filter::Nearest, SamplerAddressMode::ClampToEdge, renderer.device.clone());
|
||||||
self.texture_index_counter += 1;
|
self.texture_index_counter += 1;
|
||||||
|
tex_max_size = Some(u32::max(rect.width(), rect.height()));
|
||||||
|
tex_min_size = Some(u32::min(rect.width(), rect.height()));
|
||||||
}, |vertex_data| {
|
}, |vertex_data| {
|
||||||
println!("vd: {:?}", vertex_data);
|
println!("VD: {:?}", vertex_data);
|
||||||
let result = vec![
|
let result = vec![
|
||||||
TextVertex { position: [vertex_data.pixel_coords.min.x, vertex_data.pixel_coords.min.y, 0.], uv: [vertex_data.tex_coords.min.x, vertex_data.tex_coords.min.y * 256. / 10.], normal: [0., 0., 1.] },
|
TextVertex { position: [vertex_data.pixel_coords.min.x, vertex_data.pixel_coords.min.y, 0.], uv: [vertex_data.tex_coords.min.x, vertex_data.tex_coords.min.y] },
|
||||||
TextVertex { position: [vertex_data.pixel_coords.min.x, vertex_data.pixel_coords.max.y, 0.], uv: [vertex_data.tex_coords.min.x, vertex_data.tex_coords.max.y * 256. / 10.], normal: [0., 0., 1.] },
|
TextVertex { position: [vertex_data.pixel_coords.min.x, vertex_data.pixel_coords.max.y, 0.], uv: [vertex_data.tex_coords.min.x, vertex_data.tex_coords.max.y] },
|
||||||
TextVertex { position: [vertex_data.pixel_coords.max.x, vertex_data.pixel_coords.min.y, 0.], uv: [vertex_data.tex_coords.max.x, vertex_data.tex_coords.min.y * 256. / 10.], normal: [0., 0., 1.] },
|
TextVertex { position: [vertex_data.pixel_coords.max.x, vertex_data.pixel_coords.min.y, 0.], uv: [vertex_data.tex_coords.max.x, vertex_data.tex_coords.min.y] },
|
||||||
TextVertex { position: [vertex_data.pixel_coords.max.x, vertex_data.pixel_coords.max.y, 0.], uv: [vertex_data.tex_coords.max.x, vertex_data.tex_coords.max.y * 256. / 10.], normal: [0., 0., 1.] },
|
TextVertex { position: [vertex_data.pixel_coords.max.x, vertex_data.pixel_coords.max.y, 0.], uv: [vertex_data.tex_coords.max.x, vertex_data.tex_coords.max.y] },
|
||||||
];
|
];
|
||||||
result
|
result
|
||||||
}) {
|
}) {
|
||||||
Ok(BrushAction::Draw(quads)) => {
|
Ok(BrushAction::Draw(quads)) => {
|
||||||
|
|
||||||
let mut final_vertices = vec![];
|
let mut final_vertices = vec![];
|
||||||
let mut final_indices: Vec<u32> = vec![];
|
let mut final_indices: Vec<u32> = vec![];
|
||||||
let mut index_offset = 0;
|
let mut index_offset = 0;
|
||||||
for quad in quads {
|
for quad in quads {
|
||||||
final_vertices.append(&mut quad.iter().map(|v| CPUVertex::VertexText(v.clone())).collect());
|
final_vertices.append(&mut quad.iter().map(|v| CPUVertex::VertexText(TextVertex { position: v.position, uv: [v.uv[0], v.uv[1] * (tex_max_size.unwrap() as f32) / (tex_min_size.unwrap() as f32) ] })).collect());
|
||||||
final_indices.append(&mut [0, 2, 3, 0, 3, 1].iter().map(|x| *x + index_offset).collect());
|
final_indices.append(&mut [0, 2, 3, 0, 3, 1].iter().map(|x| *x + index_offset).collect());
|
||||||
index_offset += quad.len() as u32;
|
index_offset += quad.len() as u32;
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -17,6 +17,7 @@ pub struct Camera {
|
|||||||
pub rotation: Quaternion<f32>,
|
pub rotation: Quaternion<f32>,
|
||||||
pub view: Matrix4<f32>,
|
pub view: Matrix4<f32>,
|
||||||
pub proj: Matrix4<f32>,
|
pub proj: Matrix4<f32>,
|
||||||
|
pub ortho_proj: Matrix4<f32>,
|
||||||
}
|
}
|
||||||
|
|
||||||
impl Camera {
|
impl Camera {
|
||||||
@@ -27,6 +28,7 @@ impl Camera {
|
|||||||
rotation: Quaternion::one(),
|
rotation: Quaternion::one(),
|
||||||
view: Matrix4::identity(),
|
view: Matrix4::identity(),
|
||||||
proj: Matrix4::identity(),
|
proj: Matrix4::identity(),
|
||||||
|
ortho_proj: Matrix4::identity(),
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -38,15 +40,20 @@ impl Camera {
|
|||||||
// Create matrices
|
// Create matrices
|
||||||
self.view = Matrix4::from(self.rotation) * Matrix4::from_translation(self.position * -1.);
|
self.view = Matrix4::from(self.rotation) * Matrix4::from_translation(self.position * -1.);
|
||||||
|
|
||||||
|
let width = renderer.game_data.dimensions[0] as f32;
|
||||||
|
let height = renderer.game_data.dimensions[1] as f32;
|
||||||
|
|
||||||
self.proj = cgmath::perspective(
|
self.proj = cgmath::perspective(
|
||||||
Rad::from(Deg(self.fov_y)),
|
Rad::from(Deg(self.fov_y)),
|
||||||
renderer.game_data.dimensions[0] as f32 / renderer.game_data.dimensions[1] as f32,
|
width / height,
|
||||||
0.1,
|
0.1,
|
||||||
100.0
|
100.0
|
||||||
);
|
);
|
||||||
// Why?
|
// Why?
|
||||||
self.proj.y.y *= -1.0;
|
self.proj.y.y *= -1.0;
|
||||||
|
|
||||||
|
self.ortho_proj = cgmath::ortho(-width / 2., width / 2., -height / 2., height / 2., -1., 1.);
|
||||||
|
|
||||||
// Upload
|
// Upload
|
||||||
renderer.game_data.line_push_constants.view = self.view.into();
|
renderer.game_data.line_push_constants.view = self.view.into();
|
||||||
renderer.game_data.line_push_constants.projection = self.proj.into();
|
renderer.game_data.line_push_constants.projection = self.proj.into();
|
||||||
|
|||||||
@@ -1,6 +1,6 @@
|
|||||||
use std::{convert::TryInto, io::Read};
|
use std::{convert::TryInto, io::Read};
|
||||||
|
|
||||||
use vulkano::{format::Format, sampler::Filter};
|
use vulkano::{format::Format, sampler::{Filter, SamplerAddressMode}};
|
||||||
|
|
||||||
use super::VulkanRenderer;
|
use super::VulkanRenderer;
|
||||||
|
|
||||||
@@ -26,14 +26,14 @@ pub fn upload_texture_from_file(path: &str, renderer: &mut VulkanRenderer) -> Re
|
|||||||
|
|
||||||
if is_dxt1
|
if is_dxt1
|
||||||
{
|
{
|
||||||
renderer.upload_texture(&tex_bytes[128..], tex_width, tex_height, Format::BC1_RGBUnormBlock, Filter::Linear, renderer.device.clone());
|
renderer.upload_texture(&tex_bytes[128..], tex_width, tex_height, Format::BC1_RGBUnormBlock, Filter::Linear, SamplerAddressMode::Repeat, renderer.device.clone());
|
||||||
}
|
}
|
||||||
if is_dx10
|
if is_dx10
|
||||||
{
|
{
|
||||||
let dxgi_type = u32::from_ne_bytes(tex_bytes[128..132].try_into()?);
|
let dxgi_type = u32::from_ne_bytes(tex_bytes[128..132].try_into()?);
|
||||||
assert!(dxgi_type == 83); // BC5 Unorm Typeless
|
assert!(dxgi_type == 83); // BC5 Unorm Typeless
|
||||||
|
|
||||||
renderer.upload_texture(&tex_bytes[128+20..], tex_width, tex_height, Format::BC5UnormBlock, Filter::Linear, renderer.device.clone());
|
renderer.upload_texture(&tex_bytes[128+20..], tex_width, tex_height, Format::BC5UnormBlock, Filter::Linear, SamplerAddressMode::Repeat, renderer.device.clone());
|
||||||
}
|
}
|
||||||
|
|
||||||
Ok(())
|
Ok(())
|
||||||
|
|||||||
@@ -65,9 +65,12 @@ vulkano::impl_vertex!(LinePoint, position);
|
|||||||
pub struct TextVertex {
|
pub struct TextVertex {
|
||||||
pub position: [f32; 3],
|
pub position: [f32; 3],
|
||||||
pub uv: [f32; 2],
|
pub uv: [f32; 2],
|
||||||
pub normal: [f32; 3],
|
|
||||||
}
|
}
|
||||||
vulkano::impl_vertex!(TextVertex, position, uv, normal);
|
vulkano::impl_vertex!(TextVertex, position, uv);
|
||||||
|
|
||||||
|
#[derive(Default, Debug, Clone)]
|
||||||
|
pub struct TextInstanceData {}
|
||||||
|
vulkano::impl_vertex!(TextInstanceData);
|
||||||
|
|
||||||
pub trait Game {
|
pub trait Game {
|
||||||
/// Returns true if event should be ignored by the vulkan handler
|
/// Returns true if event should be ignored by the vulkan handler
|
||||||
@@ -271,6 +274,7 @@ impl VulkanRenderer {
|
|||||||
let uniform_buffer = vs::ty::ObjectUniformData {
|
let uniform_buffer = vs::ty::ObjectUniformData {
|
||||||
view: Matrix4::identity().into(),
|
view: Matrix4::identity().into(),
|
||||||
projection: Matrix4::identity().into(),
|
projection: Matrix4::identity().into(),
|
||||||
|
ortho_projection: Matrix4::identity().into(),
|
||||||
time: 0.0,
|
time: 0.0,
|
||||||
light_position: [0.0, 0.0, 0.0],
|
light_position: [0.0, 0.0, 0.0],
|
||||||
light_directional_rotation: [0.0, 0.0, 0.0],
|
light_directional_rotation: [0.0, 0.0, 0.0],
|
||||||
@@ -448,6 +452,7 @@ impl VulkanRenderer {
|
|||||||
CPUVertex::Vertex3D(_) => None,
|
CPUVertex::Vertex3D(_) => None,
|
||||||
CPUVertex::VertexText(vert) => Some(vert)
|
CPUVertex::VertexText(vert) => Some(vert)
|
||||||
}).collect();
|
}).collect();
|
||||||
|
|
||||||
let vertex_buffer = CpuAccessibleBuffer::from_iter(self.device.clone(), BufferUsage::vertex_buffer(), false, verts.into_iter()).unwrap();
|
let vertex_buffer = CpuAccessibleBuffer::from_iter(self.device.clone(), BufferUsage::vertex_buffer(), false, verts.into_iter()).unwrap();
|
||||||
self.game_data.meshes_text.push(Mesh { vertex_buffer, index_buffer, original_path });
|
self.game_data.meshes_text.push(Mesh { vertex_buffer, index_buffer, original_path });
|
||||||
self.game_data.meshes_text.len() - 1
|
self.game_data.meshes_text.len() - 1
|
||||||
@@ -455,7 +460,7 @@ impl VulkanRenderer {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn upload_texture(self: &mut Self, bytes: &[u8], width: u32, height: u32, format: Format, filter: Filter, device: Arc<Device>) {
|
pub fn upload_texture(self: &mut Self, bytes: &[u8], width: u32, height: u32, format: Format, filter: Filter, wrap: SamplerAddressMode, device: Arc<Device>) {
|
||||||
let dimensions = Dimensions::Dim2d { width, height };
|
let dimensions = Dimensions::Dim2d { width, height };
|
||||||
|
|
||||||
let usage = ImageUsage {
|
let usage = ImageUsage {
|
||||||
@@ -540,8 +545,8 @@ impl VulkanRenderer {
|
|||||||
future.flush().unwrap();
|
future.flush().unwrap();
|
||||||
|
|
||||||
let sampler = Sampler::new(device.clone(), filter, filter,
|
let sampler = Sampler::new(device.clone(), filter, filter,
|
||||||
MipmapMode::Linear, SamplerAddressMode::Repeat, SamplerAddressMode::Repeat,
|
MipmapMode::Linear, wrap, wrap, wrap,
|
||||||
SamplerAddressMode::Repeat, 0.0, 1.0, 0.0, (image_view.mipmap_levels() - 1) as f32).unwrap();
|
0.0, 1.0, 0.0, (image_view.mipmap_levels() - 1) as f32).unwrap();
|
||||||
|
|
||||||
self.game_data.textures.push(Texture { image: image_view, sampler });
|
self.game_data.textures.push(Texture { image: image_view, sampler });
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -1,6 +1,6 @@
|
|||||||
use std::{convert::TryInto, io::{self, ErrorKind, Read, Write}, path::PathBuf, sync::Arc};
|
use std::{convert::TryInto, io::{self, ErrorKind, Read, Write}, path::PathBuf, sync::Arc};
|
||||||
|
|
||||||
use vulkano::{command_buffer::AutoCommandBufferBuilder, descriptor::{descriptor::ShaderStages, descriptor_set::PersistentDescriptorSet}, pipeline::shader::{ShaderModule}};
|
use vulkano::{command_buffer::AutoCommandBufferBuilder, descriptor::{descriptor::ShaderStages, descriptor_set::PersistentDescriptorSet}, pipeline::{shader::{ShaderModule}}};
|
||||||
use vulkano::command_buffer::DynamicState;
|
use vulkano::command_buffer::DynamicState;
|
||||||
use vulkano::device::Device;
|
use vulkano::device::Device;
|
||||||
use vulkano::framebuffer::RenderPassAbstract;
|
use vulkano::framebuffer::RenderPassAbstract;
|
||||||
@@ -9,7 +9,7 @@ use vulkano::pipeline::GraphicsPipeline;
|
|||||||
use vulkano::pipeline::GraphicsPipelineAbstract;
|
use vulkano::pipeline::GraphicsPipelineAbstract;
|
||||||
use vulkano::pipeline::shader::GraphicsShaderType;
|
use vulkano::pipeline::shader::GraphicsShaderType;
|
||||||
|
|
||||||
use crate::{GameObject, vulkan::TextVertex};
|
use crate::{GameObject, vulkan::{TextVertex}};
|
||||||
use crate::vulkan::{LinePoint, Vertex};
|
use crate::vulkan::{LinePoint, Vertex};
|
||||||
use crate::vulkan::GameData;
|
use crate::vulkan::GameData;
|
||||||
use crate::VulkanRenderer;
|
use crate::VulkanRenderer;
|
||||||
@@ -230,7 +230,7 @@ impl LineShader {
|
|||||||
}
|
}
|
||||||
|
|
||||||
impl Drawcall for LineShader {
|
impl Drawcall for LineShader {
|
||||||
fn draw(self: &Self, builder: &mut AutoCommandBufferBuilder, _fb_index: usize, game_objects: Vec<&GameObject>, game_data: &GameData, dynamic_state: &DynamicState) {
|
fn draw(self: &Self, builder: &mut AutoCommandBufferBuilder, _fb_index: usize, _game_objects: Vec<&GameObject>, game_data: &GameData, dynamic_state: &DynamicState) {
|
||||||
builder.draw(self.pipeline.clone(),
|
builder.draw(self.pipeline.clone(),
|
||||||
&dynamic_state,
|
&dynamic_state,
|
||||||
vec![self.vertex_buffer.clone()],
|
vec![self.vertex_buffer.clone()],
|
||||||
@@ -311,7 +311,7 @@ impl TextShader {
|
|||||||
.depth_stencil_simple_depth()
|
.depth_stencil_simple_depth()
|
||||||
.fragment_shader(fs_entry, ())
|
.fragment_shader(fs_entry, ())
|
||||||
.blend_alpha_blending()
|
.blend_alpha_blending()
|
||||||
.cull_mode_back()
|
.cull_mode_disabled()
|
||||||
.render_pass(sub_pass.clone())
|
.render_pass(sub_pass.clone())
|
||||||
.build(device.clone())
|
.build(device.clone())
|
||||||
.unwrap());
|
.unwrap());
|
||||||
|
|||||||
Reference in New Issue
Block a user