mirror of
https://github.com/enduro2d/enduro2d.git
synced 2025-12-15 00:11:55 +07:00
vertex and index declarations
This commit is contained in:
@@ -11,5 +11,6 @@
|
|||||||
#include "debug.hpp"
|
#include "debug.hpp"
|
||||||
#include "input.hpp"
|
#include "input.hpp"
|
||||||
#include "render.hpp"
|
#include "render.hpp"
|
||||||
|
#include "render.inl"
|
||||||
#include "vfs.hpp"
|
#include "vfs.hpp"
|
||||||
#include "window.hpp"
|
#include "window.hpp"
|
||||||
|
|||||||
@@ -16,7 +16,6 @@ namespace e2d
|
|||||||
class mouse;
|
class mouse;
|
||||||
class keyboard;
|
class keyboard;
|
||||||
class input;
|
class input;
|
||||||
class vertex;
|
|
||||||
class shader;
|
class shader;
|
||||||
class texture;
|
class texture;
|
||||||
class index_buffer;
|
class index_buffer;
|
||||||
|
|||||||
@@ -4,6 +4,8 @@
|
|||||||
* Copyright (C) 2018 Matvey Cherevko
|
* Copyright (C) 2018 Matvey Cherevko
|
||||||
******************************************************************************/
|
******************************************************************************/
|
||||||
|
|
||||||
|
#ifndef E2D_INCLUDE_GUARD_64EC1BED88C24F57851A315A761E9D48
|
||||||
|
#define E2D_INCLUDE_GUARD_64EC1BED88C24F57851A315A761E9D48
|
||||||
#pragma once
|
#pragma once
|
||||||
|
|
||||||
#include "_core.hpp"
|
#include "_core.hpp"
|
||||||
@@ -11,16 +13,141 @@
|
|||||||
namespace e2d
|
namespace e2d
|
||||||
{
|
{
|
||||||
//
|
//
|
||||||
// vertex
|
// index_declaration
|
||||||
//
|
//
|
||||||
|
|
||||||
class vertex {
|
class index_declaration final {
|
||||||
public:
|
public:
|
||||||
v3f pos;
|
enum class index_type : u8 {
|
||||||
v2f uv[2];
|
unsigned_byte,
|
||||||
color32 color;
|
unsigned_short
|
||||||
|
};
|
||||||
|
|
||||||
|
class index_info final {
|
||||||
|
public:
|
||||||
|
index_type type = index_type::unsigned_short;
|
||||||
|
public:
|
||||||
|
index_info() noexcept = default;
|
||||||
|
~index_info() noexcept = default;
|
||||||
|
|
||||||
|
index_info(const index_info&) noexcept = default;
|
||||||
|
index_info& operator=(const index_info&) noexcept = default;
|
||||||
|
|
||||||
|
explicit index_info(index_type type) noexcept;
|
||||||
|
};
|
||||||
|
public:
|
||||||
|
index_declaration() noexcept;
|
||||||
|
~index_declaration() noexcept;
|
||||||
|
|
||||||
|
index_declaration(const index_declaration&) noexcept = default;
|
||||||
|
index_declaration& operator=(const index_declaration&) noexcept = default;
|
||||||
|
|
||||||
|
explicit index_declaration(index_type index_type) noexcept;
|
||||||
|
|
||||||
|
const index_info& index() const noexcept;
|
||||||
|
std::size_t index_size() const noexcept;
|
||||||
|
private:
|
||||||
|
index_info index_;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
bool operator==(
|
||||||
|
const index_declaration& l,
|
||||||
|
const index_declaration& r) noexcept;
|
||||||
|
bool operator!=(
|
||||||
|
const index_declaration& l,
|
||||||
|
const index_declaration& r) noexcept;
|
||||||
|
bool operator==(
|
||||||
|
const index_declaration::index_info& l,
|
||||||
|
const index_declaration::index_info& r) noexcept;
|
||||||
|
bool operator!=(
|
||||||
|
const index_declaration::index_info& l,
|
||||||
|
const index_declaration::index_info& r) noexcept;
|
||||||
|
|
||||||
|
//
|
||||||
|
// vertex_declaration
|
||||||
|
//
|
||||||
|
|
||||||
|
class vertex_declaration final {
|
||||||
|
public:
|
||||||
|
constexpr static std::size_t max_attribute_name = 128;
|
||||||
|
constexpr static std::size_t max_attribute_count = 16;
|
||||||
|
|
||||||
|
enum class attribute_type : u8 {
|
||||||
|
signed_byte,
|
||||||
|
unsigned_byte,
|
||||||
|
signed_short,
|
||||||
|
unsigned_short,
|
||||||
|
floating_point
|
||||||
|
};
|
||||||
|
|
||||||
|
class attribute_info final {
|
||||||
|
public:
|
||||||
|
char name[max_attribute_name] = {0};
|
||||||
|
std::size_t rows = 0;
|
||||||
|
std::size_t columns = 0;
|
||||||
|
std::size_t stride = 0;
|
||||||
|
attribute_type type = attribute_type::floating_point;
|
||||||
|
bool normalized = false;
|
||||||
|
public:
|
||||||
|
attribute_info() noexcept = default;
|
||||||
|
~attribute_info() noexcept = default;
|
||||||
|
|
||||||
|
attribute_info(const attribute_info&) noexcept = default;
|
||||||
|
attribute_info& operator=(const attribute_info&) noexcept = default;
|
||||||
|
|
||||||
|
attribute_info(
|
||||||
|
str_view name,
|
||||||
|
std::size_t rows,
|
||||||
|
std::size_t columns,
|
||||||
|
std::size_t stride,
|
||||||
|
attribute_type type,
|
||||||
|
bool normalized);
|
||||||
|
|
||||||
|
std::size_t row_size() const noexcept;
|
||||||
|
};
|
||||||
|
public:
|
||||||
|
vertex_declaration() noexcept;
|
||||||
|
~vertex_declaration() noexcept;
|
||||||
|
|
||||||
|
vertex_declaration(const vertex_declaration&) noexcept = default;
|
||||||
|
vertex_declaration& operator=(const vertex_declaration&) noexcept = default;
|
||||||
|
|
||||||
|
template < typename T >
|
||||||
|
vertex_declaration& add_attribute(str_view name) noexcept;
|
||||||
|
vertex_declaration& normalized() noexcept;
|
||||||
|
|
||||||
|
vertex_declaration& skip_bytes(
|
||||||
|
std::size_t bytes) noexcept;
|
||||||
|
|
||||||
|
vertex_declaration& add_attribute(
|
||||||
|
str_view name,
|
||||||
|
std::size_t rows,
|
||||||
|
std::size_t columns,
|
||||||
|
attribute_type type,
|
||||||
|
bool normalized) noexcept;
|
||||||
|
|
||||||
|
const attribute_info& attribute(std::size_t i) const noexcept;
|
||||||
|
std::size_t attribute_count() const noexcept;
|
||||||
|
std::size_t vertex_size() const noexcept;
|
||||||
|
private:
|
||||||
|
array<attribute_info, max_attribute_count> attributes_;
|
||||||
|
std::size_t attribute_count_ = 0;
|
||||||
|
std::size_t vertex_size_ = 0;
|
||||||
|
};
|
||||||
|
|
||||||
|
bool operator==(
|
||||||
|
const vertex_declaration& l,
|
||||||
|
const vertex_declaration& r) noexcept;
|
||||||
|
bool operator!=(
|
||||||
|
const vertex_declaration& l,
|
||||||
|
const vertex_declaration& r) noexcept;
|
||||||
|
bool operator==(
|
||||||
|
const vertex_declaration::attribute_info& l,
|
||||||
|
const vertex_declaration::attribute_info& r) noexcept;
|
||||||
|
bool operator!=(
|
||||||
|
const vertex_declaration::attribute_info& l,
|
||||||
|
const vertex_declaration::attribute_info& r) noexcept;
|
||||||
|
|
||||||
//
|
//
|
||||||
// shader
|
// shader
|
||||||
//
|
//
|
||||||
@@ -31,9 +158,9 @@ namespace e2d
|
|||||||
class internal_state;
|
class internal_state;
|
||||||
using internal_state_uptr = std::unique_ptr<internal_state>;
|
using internal_state_uptr = std::unique_ptr<internal_state>;
|
||||||
public:
|
public:
|
||||||
enum class uniform_type {
|
enum class uniform_type : u8 {
|
||||||
i,
|
signed_integer,
|
||||||
f,
|
floating_point,
|
||||||
|
|
||||||
v2i,
|
v2i,
|
||||||
v3i,
|
v3i,
|
||||||
@@ -47,9 +174,10 @@ namespace e2d
|
|||||||
m3f,
|
m3f,
|
||||||
m4f,
|
m4f,
|
||||||
|
|
||||||
s2d
|
sampler_2d,
|
||||||
|
sampler_cube
|
||||||
};
|
};
|
||||||
enum class attribute_type {
|
enum class attribute_type : u8 {
|
||||||
f,
|
f,
|
||||||
|
|
||||||
v2f,
|
v2f,
|
||||||
@@ -61,8 +189,11 @@ namespace e2d
|
|||||||
m4f
|
m4f
|
||||||
};
|
};
|
||||||
public:
|
public:
|
||||||
shader(internal_state_uptr);
|
explicit shader(internal_state_uptr);
|
||||||
~shader() noexcept;
|
~shader() noexcept;
|
||||||
|
const vertex_declaration& decl() const noexcept;
|
||||||
|
void set_uniform(str_view name, i32 value) const noexcept;
|
||||||
|
void set_uniform(str_view name, f32 value) const noexcept;
|
||||||
private:
|
private:
|
||||||
internal_state_uptr state_;
|
internal_state_uptr state_;
|
||||||
};
|
};
|
||||||
@@ -78,17 +209,17 @@ namespace e2d
|
|||||||
class internal_state;
|
class internal_state;
|
||||||
using internal_state_uptr = std::unique_ptr<internal_state>;
|
using internal_state_uptr = std::unique_ptr<internal_state>;
|
||||||
public:
|
public:
|
||||||
enum class wrap {
|
enum class wrap : u8 {
|
||||||
clamp,
|
clamp,
|
||||||
repeat,
|
repeat,
|
||||||
mirror
|
mirror
|
||||||
};
|
};
|
||||||
enum class filter {
|
enum class filter : u8 {
|
||||||
linear,
|
linear,
|
||||||
nearest
|
nearest
|
||||||
};
|
};
|
||||||
public:
|
public:
|
||||||
texture(internal_state_uptr);
|
explicit texture(internal_state_uptr);
|
||||||
~texture() noexcept;
|
~texture() noexcept;
|
||||||
|
|
||||||
void set_wrap(wrap u, wrap v) noexcept;
|
void set_wrap(wrap u, wrap v) noexcept;
|
||||||
@@ -108,16 +239,19 @@ namespace e2d
|
|||||||
class internal_state;
|
class internal_state;
|
||||||
using internal_state_uptr = std::unique_ptr<internal_state>;
|
using internal_state_uptr = std::unique_ptr<internal_state>;
|
||||||
public:
|
public:
|
||||||
enum class usage {
|
enum class usage : u8 {
|
||||||
static_draw,
|
static_draw,
|
||||||
stream_draw,
|
stream_draw,
|
||||||
dynamic_draw
|
dynamic_draw
|
||||||
};
|
};
|
||||||
public:
|
public:
|
||||||
index_buffer(internal_state_uptr);
|
explicit index_buffer(internal_state_uptr);
|
||||||
~index_buffer() noexcept;
|
~index_buffer() noexcept;
|
||||||
void update(const u16* indices, std::size_t count, std::size_t offset) noexcept;
|
void update(const buffer& indices, std::size_t offset) noexcept;
|
||||||
std::size_t count() const noexcept;
|
const index_declaration& decl() const noexcept;
|
||||||
|
usage buffer_usage() const noexcept;
|
||||||
|
std::size_t buffer_size() const noexcept;
|
||||||
|
std::size_t index_count() const noexcept;
|
||||||
private:
|
private:
|
||||||
internal_state_uptr state_;
|
internal_state_uptr state_;
|
||||||
};
|
};
|
||||||
@@ -133,16 +267,19 @@ namespace e2d
|
|||||||
class internal_state;
|
class internal_state;
|
||||||
using internal_state_uptr = std::unique_ptr<internal_state>;
|
using internal_state_uptr = std::unique_ptr<internal_state>;
|
||||||
public:
|
public:
|
||||||
enum class usage {
|
enum class usage : u8{
|
||||||
static_draw,
|
static_draw,
|
||||||
stream_draw,
|
stream_draw,
|
||||||
dynamic_draw
|
dynamic_draw
|
||||||
};
|
};
|
||||||
public:
|
public:
|
||||||
vertex_buffer(internal_state_uptr);
|
explicit vertex_buffer(internal_state_uptr);
|
||||||
~vertex_buffer() noexcept;
|
~vertex_buffer() noexcept;
|
||||||
void update(const vertex* vertices, std::size_t count, std::size_t offset) noexcept;
|
void update(const buffer& vertices, std::size_t offset) noexcept;
|
||||||
std::size_t count() const noexcept;
|
const vertex_declaration& decl() const noexcept;
|
||||||
|
usage buffer_usage() const noexcept;
|
||||||
|
std::size_t buffer_size() const noexcept;
|
||||||
|
std::size_t vertex_count() const noexcept;
|
||||||
private:
|
private:
|
||||||
internal_state_uptr state_;
|
internal_state_uptr state_;
|
||||||
};
|
};
|
||||||
@@ -154,18 +291,20 @@ namespace e2d
|
|||||||
|
|
||||||
class render final : public module<render> {
|
class render final : public module<render> {
|
||||||
public:
|
public:
|
||||||
enum class state {
|
enum class state : u8 {
|
||||||
blend,
|
blend,
|
||||||
cull_face,
|
cull_face,
|
||||||
depth_test,
|
depth_test,
|
||||||
stencil_test
|
stencil_test
|
||||||
};
|
};
|
||||||
enum class cull_face {
|
|
||||||
|
enum class cull_face : u8 {
|
||||||
front,
|
front,
|
||||||
back,
|
back,
|
||||||
front_back
|
front_back
|
||||||
};
|
};
|
||||||
enum class blend_func {
|
|
||||||
|
enum class blend_func : u8 {
|
||||||
zero,
|
zero,
|
||||||
one,
|
one,
|
||||||
src_color,
|
src_color,
|
||||||
@@ -182,12 +321,14 @@ namespace e2d
|
|||||||
one_minus_constant_alpha,
|
one_minus_constant_alpha,
|
||||||
src_alpha_saturate
|
src_alpha_saturate
|
||||||
};
|
};
|
||||||
enum class blend_equation {
|
|
||||||
|
enum class blend_equation : u8 {
|
||||||
add,
|
add,
|
||||||
subtract,
|
subtract,
|
||||||
reverse_subtract
|
reverse_subtract
|
||||||
};
|
};
|
||||||
enum class depth_func {
|
|
||||||
|
enum class depth_func : u8 {
|
||||||
never,
|
never,
|
||||||
less,
|
less,
|
||||||
lequal,
|
lequal,
|
||||||
@@ -197,7 +338,8 @@ namespace e2d
|
|||||||
notequal,
|
notequal,
|
||||||
always
|
always
|
||||||
};
|
};
|
||||||
enum class stencil_func {
|
|
||||||
|
enum class stencil_func : u8 {
|
||||||
never,
|
never,
|
||||||
less,
|
less,
|
||||||
lequal,
|
lequal,
|
||||||
@@ -207,7 +349,8 @@ namespace e2d
|
|||||||
notequal,
|
notequal,
|
||||||
always
|
always
|
||||||
};
|
};
|
||||||
enum class stencil_op {
|
|
||||||
|
enum class stencil_op : u8 {
|
||||||
keep,
|
keep,
|
||||||
zero,
|
zero,
|
||||||
replace,
|
replace,
|
||||||
@@ -217,13 +360,20 @@ namespace e2d
|
|||||||
decr_wrap,
|
decr_wrap,
|
||||||
invert
|
invert
|
||||||
};
|
};
|
||||||
|
|
||||||
|
enum class topology : u8 {
|
||||||
|
triangles,
|
||||||
|
triangles_fan,
|
||||||
|
triangles_strip
|
||||||
|
};
|
||||||
public:
|
public:
|
||||||
render(debug& d, window& w);
|
render(debug& d, window& w);
|
||||||
~render() noexcept;
|
~render() noexcept final;
|
||||||
|
|
||||||
shader_ptr create_shader(
|
shader_ptr create_shader(
|
||||||
input_stream_uptr vertex,
|
input_stream_uptr vertex,
|
||||||
input_stream_uptr fragment);
|
input_stream_uptr fragment,
|
||||||
|
const vertex_declaration& decl);
|
||||||
|
|
||||||
texture_ptr create_texture(
|
texture_ptr create_texture(
|
||||||
const image& image);
|
const image& image);
|
||||||
@@ -233,22 +383,27 @@ namespace e2d
|
|||||||
image_data_format format);
|
image_data_format format);
|
||||||
|
|
||||||
index_buffer_ptr create_index_buffer(
|
index_buffer_ptr create_index_buffer(
|
||||||
const u16* indices,
|
const buffer& indices,
|
||||||
std::size_t count,
|
const index_declaration& decl,
|
||||||
index_buffer::usage usage);
|
enum index_buffer::usage usage);
|
||||||
|
|
||||||
vertex_buffer_ptr create_vertex_buffer(
|
vertex_buffer_ptr create_vertex_buffer(
|
||||||
const vertex* vertices,
|
const buffer& vertices,
|
||||||
std::size_t count,
|
const vertex_declaration& decl,
|
||||||
vertex_buffer::usage usage);
|
enum vertex_buffer::usage usage);
|
||||||
|
|
||||||
void clear(bool color, bool depth, bool stencil) noexcept;
|
void clear(
|
||||||
|
bool color,
|
||||||
|
bool depth,
|
||||||
|
bool stencil) noexcept;
|
||||||
|
|
||||||
void draw(
|
void draw(
|
||||||
|
topology tp,
|
||||||
const shader_ptr& ps,
|
const shader_ptr& ps,
|
||||||
const index_buffer_ptr& ib,
|
const index_buffer_ptr& ib,
|
||||||
const vertex_buffer_ptr& vb) noexcept;
|
const vertex_buffer_ptr& vb) noexcept;
|
||||||
|
|
||||||
|
void set_model(const m4f& model) noexcept;
|
||||||
void set_view(const m4f& view) noexcept;
|
void set_view(const m4f& view) noexcept;
|
||||||
void set_projection(const m4f& projection) noexcept;
|
void set_projection(const m4f& projection) noexcept;
|
||||||
void set_viewport(u32 x, u32 y, u32 w, u32 h) noexcept;
|
void set_viewport(u32 x, u32 y, u32 w, u32 h) noexcept;
|
||||||
@@ -278,3 +433,6 @@ namespace e2d
|
|||||||
std::unique_ptr<internal_state> state_;
|
std::unique_ptr<internal_state> state_;
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#include "render.inl"
|
||||||
|
#endif
|
||||||
|
|||||||
74
headers/enduro2d/core/render.inl
Normal file
74
headers/enduro2d/core/render.inl
Normal file
@@ -0,0 +1,74 @@
|
|||||||
|
/*******************************************************************************
|
||||||
|
* This file is part of the "Enduro2D"
|
||||||
|
* For conditions of distribution and use, see copyright notice in LICENSE.md
|
||||||
|
* Copyright (C) 2018 Matvey Cherevko
|
||||||
|
******************************************************************************/
|
||||||
|
|
||||||
|
#ifndef E2D_INCLUDE_GUARD_8247225BE32B4135BDAECEEE88535A86
|
||||||
|
#define E2D_INCLUDE_GUARD_8247225BE32B4135BDAECEEE88535A86
|
||||||
|
#pragma once
|
||||||
|
|
||||||
|
#include "_core.hpp"
|
||||||
|
#include "render.hpp"
|
||||||
|
|
||||||
|
namespace e2d
|
||||||
|
{
|
||||||
|
template < typename T >
|
||||||
|
vertex_declaration& vertex_declaration::add_attribute(str_view name) noexcept {
|
||||||
|
E2D_UNUSED(name);
|
||||||
|
static_assert(sizeof(T) == 0, "not implemented for this type");
|
||||||
|
}
|
||||||
|
|
||||||
|
#define DEFINE_ADD_ATTRIBUTE_SPECIALIZATION(t, rows, columns, type)\
|
||||||
|
template <>\
|
||||||
|
inline vertex_declaration& vertex_declaration::add_attribute<t>(str_view name) noexcept {\
|
||||||
|
return add_attribute(name, (rows), (columns), attribute_type::type, false);\
|
||||||
|
}
|
||||||
|
|
||||||
|
DEFINE_ADD_ATTRIBUTE_SPECIALIZATION(i8, 1, 1, signed_byte)
|
||||||
|
DEFINE_ADD_ATTRIBUTE_SPECIALIZATION(vec2<i8>, 1, 2, signed_byte)
|
||||||
|
DEFINE_ADD_ATTRIBUTE_SPECIALIZATION(vec3<i8>, 1, 3, signed_byte)
|
||||||
|
DEFINE_ADD_ATTRIBUTE_SPECIALIZATION(vec4<i8>, 1, 4, signed_byte)
|
||||||
|
DEFINE_ADD_ATTRIBUTE_SPECIALIZATION(mat2<i8>, 2, 2, signed_byte)
|
||||||
|
DEFINE_ADD_ATTRIBUTE_SPECIALIZATION(mat3<i8>, 3, 3, signed_byte)
|
||||||
|
DEFINE_ADD_ATTRIBUTE_SPECIALIZATION(mat4<i8>, 4, 4, signed_byte)
|
||||||
|
|
||||||
|
DEFINE_ADD_ATTRIBUTE_SPECIALIZATION(u8, 1, 1, unsigned_byte)
|
||||||
|
DEFINE_ADD_ATTRIBUTE_SPECIALIZATION(vec2<u8>, 1, 2, unsigned_byte)
|
||||||
|
DEFINE_ADD_ATTRIBUTE_SPECIALIZATION(vec3<u8>, 1, 3, unsigned_byte)
|
||||||
|
DEFINE_ADD_ATTRIBUTE_SPECIALIZATION(vec4<u8>, 1, 4, unsigned_byte)
|
||||||
|
DEFINE_ADD_ATTRIBUTE_SPECIALIZATION(mat2<u8>, 2, 2, unsigned_byte)
|
||||||
|
DEFINE_ADD_ATTRIBUTE_SPECIALIZATION(mat3<u8>, 3, 3, unsigned_byte)
|
||||||
|
DEFINE_ADD_ATTRIBUTE_SPECIALIZATION(mat4<u8>, 4, 4, unsigned_byte)
|
||||||
|
|
||||||
|
DEFINE_ADD_ATTRIBUTE_SPECIALIZATION(i16, 1, 1, signed_short)
|
||||||
|
DEFINE_ADD_ATTRIBUTE_SPECIALIZATION(vec2<i16>, 1, 2, signed_short)
|
||||||
|
DEFINE_ADD_ATTRIBUTE_SPECIALIZATION(vec3<i16>, 1, 3, signed_short)
|
||||||
|
DEFINE_ADD_ATTRIBUTE_SPECIALIZATION(vec4<i16>, 1, 4, signed_short)
|
||||||
|
DEFINE_ADD_ATTRIBUTE_SPECIALIZATION(mat2<i16>, 2, 2, signed_short)
|
||||||
|
DEFINE_ADD_ATTRIBUTE_SPECIALIZATION(mat3<i16>, 3, 3, signed_short)
|
||||||
|
DEFINE_ADD_ATTRIBUTE_SPECIALIZATION(mat4<i16>, 4, 4, signed_short)
|
||||||
|
|
||||||
|
DEFINE_ADD_ATTRIBUTE_SPECIALIZATION(u16, 1, 1, unsigned_short)
|
||||||
|
DEFINE_ADD_ATTRIBUTE_SPECIALIZATION(vec2<u16>, 1, 2, unsigned_short)
|
||||||
|
DEFINE_ADD_ATTRIBUTE_SPECIALIZATION(vec3<u16>, 1, 3, unsigned_short)
|
||||||
|
DEFINE_ADD_ATTRIBUTE_SPECIALIZATION(vec4<u16>, 1, 4, unsigned_short)
|
||||||
|
DEFINE_ADD_ATTRIBUTE_SPECIALIZATION(mat2<u16>, 2, 2, unsigned_short)
|
||||||
|
DEFINE_ADD_ATTRIBUTE_SPECIALIZATION(mat3<u16>, 3, 3, unsigned_short)
|
||||||
|
DEFINE_ADD_ATTRIBUTE_SPECIALIZATION(mat4<u16>, 4, 4, unsigned_short)
|
||||||
|
|
||||||
|
DEFINE_ADD_ATTRIBUTE_SPECIALIZATION(f32, 1, 1, floating_point)
|
||||||
|
DEFINE_ADD_ATTRIBUTE_SPECIALIZATION(vec2<f32>, 1, 2, floating_point)
|
||||||
|
DEFINE_ADD_ATTRIBUTE_SPECIALIZATION(vec3<f32>, 1, 3, floating_point)
|
||||||
|
DEFINE_ADD_ATTRIBUTE_SPECIALIZATION(vec4<f32>, 1, 4, floating_point)
|
||||||
|
DEFINE_ADD_ATTRIBUTE_SPECIALIZATION(mat2<f32>, 2, 2, floating_point)
|
||||||
|
DEFINE_ADD_ATTRIBUTE_SPECIALIZATION(mat3<f32>, 3, 3, floating_point)
|
||||||
|
DEFINE_ADD_ATTRIBUTE_SPECIALIZATION(mat4<f32>, 4, 4, floating_point)
|
||||||
|
|
||||||
|
DEFINE_ADD_ATTRIBUTE_SPECIALIZATION(color, 1, 4, floating_point)
|
||||||
|
DEFINE_ADD_ATTRIBUTE_SPECIALIZATION(color32, 1, 4, unsigned_byte)
|
||||||
|
|
||||||
|
#undef DEFINE_ADD_ATTRIBUTE_SPECIALIZATION
|
||||||
|
}
|
||||||
|
|
||||||
|
#endif
|
||||||
@@ -10,69 +10,88 @@ using namespace e2d;
|
|||||||
namespace
|
namespace
|
||||||
{
|
{
|
||||||
const char* vs_source_cstr =
|
const char* vs_source_cstr =
|
||||||
"#version 120 \n"
|
"#version 120 \n"
|
||||||
" \n"
|
" \n"
|
||||||
"attribute vec3 in_pos; \n"
|
"attribute vec3 a_position; \n"
|
||||||
"attribute vec2 in_uv0; \n"
|
"attribute vec4 a_color; \n"
|
||||||
"attribute vec2 in_uv1; \n"
|
" \n"
|
||||||
"attribute vec4 in_color; \n"
|
"uniform float u_time = 0.0; \n"
|
||||||
" \n"
|
" \n"
|
||||||
"varying vec2 uv0; \n"
|
"varying vec4 color; \n"
|
||||||
"varying vec2 uv1; \n"
|
" \n"
|
||||||
"varying vec4 color; \n"
|
"void main(){ \n"
|
||||||
" \n"
|
" color = a_color; \n"
|
||||||
"void main(){ \n"
|
" \n"
|
||||||
" uv0 = in_uv0; \n"
|
" float s = 0.7 + 0.3 * (cos(u_time * 0.003) + 1); \n"
|
||||||
" uv1 = in_uv1; \n"
|
" gl_Position = vec4(a_position * s, 1.0); \n"
|
||||||
" color = in_color; \n"
|
|
||||||
" gl_Position = vec4(in_pos, 1.0); \n"
|
|
||||||
"}";
|
"}";
|
||||||
|
|
||||||
const char* fs_source_cstr =
|
const char* fs_source_cstr =
|
||||||
"#version 120 \n"
|
"#version 120 \n"
|
||||||
" \n"
|
" \n"
|
||||||
"varying vec2 uv0; \n"
|
"varying vec4 color; \n"
|
||||||
"varying vec2 uv1; \n"
|
" \n"
|
||||||
"varying vec4 color; \n"
|
"void main(){ \n"
|
||||||
" \n"
|
" gl_FragColor = color; \n"
|
||||||
"void main(){ \n"
|
|
||||||
" gl_FragColor = color; \n"
|
|
||||||
"}";
|
"}";
|
||||||
|
|
||||||
u16 indices[] = {
|
struct vertex {
|
||||||
|
v3f position;
|
||||||
|
color32 color;
|
||||||
|
};
|
||||||
|
|
||||||
|
u8 indices[] = {
|
||||||
0, 1, 2, 2, 1, 3};
|
0, 1, 2, 2, 1, 3};
|
||||||
|
|
||||||
const vertex vertices[] = {
|
const vertex vertices[] = {
|
||||||
{{-0.5f, 0.5f, 0.0f}, {{0.f, 0.f}, {0.f, 0.f}}, {0xFF, 0x00, 0x00, 0xFF}},
|
{{-0.5f, 0.5f, 0.0f}, color32::red()},
|
||||||
{{-0.5f, -0.5f, 0.0f}, {{0.f, 0.f}, {0.f, 0.f}}, {0x00, 0xFF, 0x00, 0xFF}},
|
{{-0.5f, -0.5f, 0.0f}, color32::green()},
|
||||||
{{ 0.5f, 0.5f, 0.0f}, {{0.f, 0.f}, {0.f, 0.f}}, {0x00, 0x00, 0xFF, 0xFF}},
|
{{ 0.5f, 0.5f, 0.0f}, color32::blue()},
|
||||||
{{ 0.5f, -0.5f, 0.0f}, {{0.f, 0.f}, {0.f, 0.f}}, {0xFF, 0xFF, 0xFF, 0xFF}}};
|
{{ 0.5f, -0.5f, 0.0f}, color32::white()}};
|
||||||
}
|
}
|
||||||
|
|
||||||
int e2d_main() {
|
int e2d_main() {
|
||||||
modules::initialize<debug>();
|
modules::initialize<debug>()
|
||||||
|
.register_sink<debug_console_sink>();
|
||||||
modules::initialize<input>();
|
modules::initialize<input>();
|
||||||
modules::initialize<window>(v2u{640, 480}, "Enduro2D", false);
|
modules::initialize<window>(v2u{640, 480}, "Enduro2D", false)
|
||||||
|
.register_event_listener<window_input_source>(the<input>());
|
||||||
modules::initialize<render>(the<debug>(), the<window>());
|
modules::initialize<render>(the<debug>(), the<window>());
|
||||||
|
|
||||||
the<debug>().register_sink<debug_console_sink>();
|
auto index_decl = index_declaration(
|
||||||
the<window>().register_event_listener<window_input_source>(the<input>());
|
index_declaration::index_type::unsigned_byte);
|
||||||
|
|
||||||
|
auto vertex_decl = vertex_declaration()
|
||||||
|
.add_attribute<v3f>("a_position")
|
||||||
|
.add_attribute<color32>("a_color").normalized();
|
||||||
|
|
||||||
const auto ps = the<render>().create_shader(
|
const auto ps = the<render>().create_shader(
|
||||||
make_memory_stream(buffer(vs_source_cstr, std::strlen(vs_source_cstr))),
|
make_memory_stream(buffer(vs_source_cstr, std::strlen(vs_source_cstr))),
|
||||||
make_memory_stream(buffer(fs_source_cstr, std::strlen(fs_source_cstr))));
|
make_memory_stream(buffer(fs_source_cstr, std::strlen(fs_source_cstr))),
|
||||||
|
vertex_decl);
|
||||||
|
|
||||||
const auto ib = the<render>().create_index_buffer(
|
const auto ib = the<render>().create_index_buffer(
|
||||||
indices, E2D_COUNTOF(indices), index_buffer::usage::static_draw);
|
buffer(indices, E2D_COUNTOF(indices) * sizeof(indices[0])),
|
||||||
|
index_decl,
|
||||||
|
index_buffer::usage::static_draw);
|
||||||
|
|
||||||
const auto vb = the<render>().create_vertex_buffer(
|
const auto vb = the<render>().create_vertex_buffer(
|
||||||
vertices, E2D_COUNTOF(vertices), vertex_buffer::usage::static_draw);
|
buffer(vertices, E2D_COUNTOF(vertices) * sizeof(vertices[0])),
|
||||||
|
vertex_decl,
|
||||||
|
vertex_buffer::usage::static_draw);
|
||||||
|
|
||||||
|
const auto begin_time = time::now_ms();
|
||||||
|
|
||||||
const keyboard& k = the<input>().keyboard();
|
const keyboard& k = the<input>().keyboard();
|
||||||
while ( !the<window>().should_close() && !k.is_key_just_released(keyboard_key::escape) ) {
|
while ( !the<window>().should_close() && !k.is_key_just_released(keyboard_key::escape) ) {
|
||||||
the<render>().set_clear_color({1.f, 0.4f, 0.f});
|
the<render>().set_clear_color({1.f, 0.4f, 0.f, 1.f});
|
||||||
the<render>().clear(true, true, true);
|
the<render>().clear(true, true, true);
|
||||||
the<render>().draw(ps, ib, vb);
|
|
||||||
|
f32 t = (time::now_ms() - begin_time).cast_to<f32>().value;
|
||||||
|
ps->set_uniform("u_time", t);
|
||||||
|
{
|
||||||
|
the<render>().draw(render::topology::triangles, ps, ib, vb);
|
||||||
|
}
|
||||||
the<window>().swap_buffers(true);
|
the<window>().swap_buffers(true);
|
||||||
the<input>().frame_tick();
|
the<input>().frame_tick();
|
||||||
window::poll_events();
|
window::poll_events();
|
||||||
|
|||||||
@@ -5,3 +5,202 @@
|
|||||||
******************************************************************************/
|
******************************************************************************/
|
||||||
|
|
||||||
#include "render_impl/render.hpp"
|
#include "render_impl/render.hpp"
|
||||||
|
|
||||||
|
namespace
|
||||||
|
{
|
||||||
|
using namespace e2d;
|
||||||
|
|
||||||
|
std::size_t index_element_size(index_declaration::index_type it) noexcept {
|
||||||
|
#define DEFINE_CASE(x,y) case index_declaration::index_type::x: return y;
|
||||||
|
switch ( it ) {
|
||||||
|
DEFINE_CASE(unsigned_byte, sizeof(u8));
|
||||||
|
DEFINE_CASE(unsigned_short, sizeof(u16));
|
||||||
|
default:
|
||||||
|
E2D_ASSERT_MSG(false, "unexpected index type");
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
#undef DEFINE_CASE
|
||||||
|
}
|
||||||
|
|
||||||
|
std::size_t attribute_element_size(vertex_declaration::attribute_type at) noexcept {
|
||||||
|
#define DEFINE_CASE(x,y) case vertex_declaration::attribute_type::x: return y;
|
||||||
|
switch ( at ) {
|
||||||
|
DEFINE_CASE(signed_byte, sizeof(u8));
|
||||||
|
DEFINE_CASE(unsigned_byte, sizeof(u8));
|
||||||
|
DEFINE_CASE(signed_short, sizeof(u16));
|
||||||
|
DEFINE_CASE(unsigned_short, sizeof(u16));
|
||||||
|
DEFINE_CASE(floating_point, sizeof(u32));
|
||||||
|
default:
|
||||||
|
E2D_ASSERT_MSG(false, "unexpected attribute type");
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
#undef DEFINE_CASE
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
namespace e2d
|
||||||
|
{
|
||||||
|
//
|
||||||
|
// index_declaration::index_info
|
||||||
|
//
|
||||||
|
|
||||||
|
index_declaration::index_info::index_info(index_type ntype) noexcept
|
||||||
|
: type(ntype) {}
|
||||||
|
|
||||||
|
//
|
||||||
|
// index_declaration
|
||||||
|
//
|
||||||
|
|
||||||
|
index_declaration::index_declaration() noexcept = default;
|
||||||
|
index_declaration::~index_declaration() noexcept = default;
|
||||||
|
|
||||||
|
index_declaration::index_declaration(index_type type) noexcept
|
||||||
|
: index_(type) {}
|
||||||
|
|
||||||
|
const index_declaration::index_info& index_declaration::index() const noexcept {
|
||||||
|
return index_;
|
||||||
|
}
|
||||||
|
|
||||||
|
std::size_t index_declaration::index_size() const noexcept {
|
||||||
|
return index_element_size(index_.type);
|
||||||
|
}
|
||||||
|
|
||||||
|
bool operator==(const index_declaration& l, const index_declaration& r) noexcept {
|
||||||
|
return l.index_size() == r.index_size()
|
||||||
|
&& l.index() == r.index();
|
||||||
|
}
|
||||||
|
|
||||||
|
bool operator!=(const index_declaration& l, const index_declaration& r) noexcept {
|
||||||
|
return !(l == r);
|
||||||
|
}
|
||||||
|
|
||||||
|
bool operator==(
|
||||||
|
const index_declaration::index_info& l,
|
||||||
|
const index_declaration::index_info& r) noexcept
|
||||||
|
{
|
||||||
|
return l.type == r.type;
|
||||||
|
}
|
||||||
|
|
||||||
|
bool operator!=(
|
||||||
|
const index_declaration::index_info& l,
|
||||||
|
const index_declaration::index_info& r) noexcept
|
||||||
|
{
|
||||||
|
return !(l == r);
|
||||||
|
}
|
||||||
|
|
||||||
|
//
|
||||||
|
// vertex_declaration::attribute_info
|
||||||
|
//
|
||||||
|
|
||||||
|
vertex_declaration::attribute_info::attribute_info(
|
||||||
|
str_view nname,
|
||||||
|
std::size_t nrows,
|
||||||
|
std::size_t ncolumns,
|
||||||
|
std::size_t nstride,
|
||||||
|
attribute_type ntype,
|
||||||
|
bool nnormalized)
|
||||||
|
: rows(nrows)
|
||||||
|
, columns(ncolumns)
|
||||||
|
, stride(nstride)
|
||||||
|
, type(ntype)
|
||||||
|
, normalized(nnormalized) {
|
||||||
|
bool name_format_success = strings::format_nothrow(
|
||||||
|
name, E2D_COUNTOF(name), nullptr, "%0", nname);
|
||||||
|
E2D_UNUSED(name_format_success);
|
||||||
|
E2D_ASSERT(name_format_success);
|
||||||
|
}
|
||||||
|
|
||||||
|
std::size_t vertex_declaration::attribute_info::row_size() const noexcept {
|
||||||
|
return attribute_element_size(type) * columns;
|
||||||
|
}
|
||||||
|
|
||||||
|
//
|
||||||
|
// vertex_declaration
|
||||||
|
//
|
||||||
|
|
||||||
|
vertex_declaration::vertex_declaration() noexcept = default;
|
||||||
|
vertex_declaration::~vertex_declaration() noexcept = default;
|
||||||
|
|
||||||
|
vertex_declaration& vertex_declaration::normalized() noexcept {
|
||||||
|
E2D_ASSERT(attribute_count_ > 0);
|
||||||
|
attributes_[attribute_count_ - 1].normalized = true;
|
||||||
|
return *this;
|
||||||
|
}
|
||||||
|
|
||||||
|
vertex_declaration& vertex_declaration::skip_bytes(std::size_t bytes) noexcept {
|
||||||
|
vertex_size_ += bytes;
|
||||||
|
return *this;
|
||||||
|
}
|
||||||
|
|
||||||
|
vertex_declaration& vertex_declaration::add_attribute(
|
||||||
|
str_view name,
|
||||||
|
std::size_t rows,
|
||||||
|
std::size_t columns,
|
||||||
|
attribute_type type,
|
||||||
|
bool normalized) noexcept
|
||||||
|
{
|
||||||
|
E2D_ASSERT(attribute_count_ < attributes_.size());
|
||||||
|
const std::size_t stride = vertex_size_;
|
||||||
|
attributes_[attribute_count_] = attribute_info(
|
||||||
|
name,
|
||||||
|
rows,
|
||||||
|
columns,
|
||||||
|
stride,
|
||||||
|
type,
|
||||||
|
normalized);
|
||||||
|
vertex_size_ += attribute_element_size(type) * rows * columns;
|
||||||
|
++attribute_count_;
|
||||||
|
return *this;
|
||||||
|
}
|
||||||
|
|
||||||
|
const vertex_declaration::attribute_info& vertex_declaration::attribute(std::size_t i) const noexcept {
|
||||||
|
E2D_ASSERT(i < attribute_count_);
|
||||||
|
return attributes_[i];
|
||||||
|
}
|
||||||
|
|
||||||
|
std::size_t vertex_declaration::attribute_count() const noexcept {
|
||||||
|
return attribute_count_;
|
||||||
|
}
|
||||||
|
|
||||||
|
std::size_t vertex_declaration::vertex_size() const noexcept {
|
||||||
|
return vertex_size_;
|
||||||
|
}
|
||||||
|
|
||||||
|
bool operator==(const vertex_declaration& l, const vertex_declaration& r) noexcept {
|
||||||
|
if ( l.vertex_size() != r.vertex_size() ) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
if ( l.attribute_count() != r.attribute_count() ) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
for ( std::size_t i = 0, e = l.attribute_count(); i < e; ++i ) {
|
||||||
|
if ( l.attribute(i) != r.attribute(i) ) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
bool operator!=(const vertex_declaration& l, const vertex_declaration& r) noexcept {
|
||||||
|
return !(l == r);
|
||||||
|
}
|
||||||
|
|
||||||
|
bool operator==(
|
||||||
|
const vertex_declaration::attribute_info& l,
|
||||||
|
const vertex_declaration::attribute_info& r) noexcept
|
||||||
|
{
|
||||||
|
return !std::strcmp(l.name, r.name)
|
||||||
|
&& l.rows == r.rows
|
||||||
|
&& l.columns == r.columns
|
||||||
|
&& l.stride == r.stride
|
||||||
|
&& l.type == r.type
|
||||||
|
&& l.normalized == r.normalized;
|
||||||
|
}
|
||||||
|
|
||||||
|
bool operator!=(
|
||||||
|
const vertex_declaration::attribute_info& l,
|
||||||
|
const vertex_declaration::attribute_info& r) noexcept
|
||||||
|
{
|
||||||
|
return !(l == r);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|||||||
File diff suppressed because it is too large
Load Diff
@@ -8,4 +8,82 @@
|
|||||||
using namespace e2d;
|
using namespace e2d;
|
||||||
|
|
||||||
TEST_CASE("render"){
|
TEST_CASE("render"){
|
||||||
|
SECTION("index_declaration"){
|
||||||
|
index_declaration id;
|
||||||
|
REQUIRE(id.index().type == index_declaration::index_type::unsigned_short);
|
||||||
|
REQUIRE(id.index_size() == 2);
|
||||||
|
|
||||||
|
index_declaration id2(index_declaration::index_type::unsigned_short);
|
||||||
|
REQUIRE(id2.index().type == index_declaration::index_type::unsigned_short);
|
||||||
|
REQUIRE(id2.index_size() == 2);
|
||||||
|
|
||||||
|
index_declaration id3(index_declaration::index_type::unsigned_byte);
|
||||||
|
REQUIRE(id3.index().type == index_declaration::index_type::unsigned_byte);
|
||||||
|
REQUIRE(id3.index_size() == 1);
|
||||||
|
|
||||||
|
REQUIRE(id == id2);
|
||||||
|
REQUIRE_FALSE(id == id3);
|
||||||
|
|
||||||
|
REQUIRE_FALSE(id != id2);
|
||||||
|
REQUIRE(id != id3);
|
||||||
|
|
||||||
|
index_declaration id4 = id;
|
||||||
|
REQUIRE(id4 == id2);
|
||||||
|
id4 = id3;
|
||||||
|
REQUIRE(id4 != id2);
|
||||||
|
REQUIRE(id4 == id3);
|
||||||
|
}
|
||||||
|
SECTION("vertex_declaration"){
|
||||||
|
vertex_declaration vd;
|
||||||
|
REQUIRE(vd.attribute_count() == 0);
|
||||||
|
REQUIRE(vd.vertex_size() == 0);
|
||||||
|
|
||||||
|
REQUIRE(&vd == &vd.add_attribute<v2f>("hello"));
|
||||||
|
REQUIRE(vd.attribute_count() == 1);
|
||||||
|
REQUIRE(vd.vertex_size() == 8);
|
||||||
|
|
||||||
|
vertex_declaration::attribute_info ai = vd.attribute(0);
|
||||||
|
REQUIRE(!std::strcmp(ai.name, "hello"));
|
||||||
|
REQUIRE(ai.columns == 2);
|
||||||
|
REQUIRE(ai.stride == 0);
|
||||||
|
REQUIRE(ai.type == vertex_declaration::attribute_type::floating_point);
|
||||||
|
REQUIRE_FALSE(ai.normalized);
|
||||||
|
|
||||||
|
REQUIRE(&vd == &vd.skip_bytes(4));
|
||||||
|
REQUIRE(vd.vertex_size() == 12);
|
||||||
|
|
||||||
|
REQUIRE(&vd == &vd.add_attribute<u16>("world").normalized());
|
||||||
|
REQUIRE(vd.attribute_count() == 2);
|
||||||
|
REQUIRE(vd.vertex_size() == 14);
|
||||||
|
|
||||||
|
vertex_declaration::attribute_info ai2 = vd.attribute(1);
|
||||||
|
REQUIRE(!std::strcmp(ai2.name, "world"));
|
||||||
|
REQUIRE(ai2.columns == 1);
|
||||||
|
REQUIRE(ai2.stride == 12);
|
||||||
|
REQUIRE(ai2.type == vertex_declaration::attribute_type::unsigned_short);
|
||||||
|
REQUIRE(ai2.normalized);
|
||||||
|
|
||||||
|
auto vd2 = vertex_declaration()
|
||||||
|
.add_attribute("hello", 1, 2, vertex_declaration::attribute_type::floating_point, false)
|
||||||
|
.skip_bytes(4)
|
||||||
|
.add_attribute("world", 1, 1, vertex_declaration::attribute_type::unsigned_short, true);
|
||||||
|
REQUIRE(vd == vd2);
|
||||||
|
REQUIRE_FALSE(vd != vd2);
|
||||||
|
|
||||||
|
auto vd3 = vertex_declaration()
|
||||||
|
.add_attribute<v2f>("hello")
|
||||||
|
.add_attribute<v2f>("world");
|
||||||
|
REQUIRE_FALSE(vd == vd3);
|
||||||
|
REQUIRE(vd != vd3);
|
||||||
|
|
||||||
|
REQUIRE(vd3.vertex_size() == 16);
|
||||||
|
vd3.skip_bytes(4);
|
||||||
|
REQUIRE(vd3.vertex_size() == 20);
|
||||||
|
|
||||||
|
vertex_declaration vd4 = vd2;
|
||||||
|
REQUIRE(vd4 == vd);
|
||||||
|
vd4 = vd3;
|
||||||
|
REQUIRE(vd4 != vd);
|
||||||
|
REQUIRE(vd4 == vd3);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
Reference in New Issue
Block a user