added shader attributes and added vertex buffer loading
parent
3951babc93
commit
aeea0eadc9
|
@ -575,8 +575,8 @@ struct gs_device {
|
|||
gs_texture *curTextures[GS_MAX_TEXTURES];
|
||||
gs_sampler_state *curSamplers[GS_MAX_TEXTURES];
|
||||
gs_vertex_buffer *curVertexBuffer;
|
||||
gs_vertex_shader *curVertexShader;
|
||||
gs_index_buffer *curIndexBuffer;
|
||||
gs_vertex_shader *curVertexShader;
|
||||
gs_pixel_shader *curPixelShader;
|
||||
gs_swap_chain *curSwapChain;
|
||||
|
||||
|
|
|
@ -60,10 +60,6 @@ EXPORT enum gs_texture_type device_gettexturetype(device_t device,
|
|||
EXPORT void device_load_vertexbuffer(device_t device, vertbuffer_t vertbuffer);
|
||||
EXPORT void device_load_indexbuffer(device_t device, indexbuffer_t indexbuffer);
|
||||
EXPORT void device_load_texture(device_t device, texture_t tex, int unit);
|
||||
EXPORT void device_load_cubetexture(device_t device, texture_t cubetex,
|
||||
int unit);
|
||||
EXPORT void device_load_volumetexture(device_t device, texture_t voltex,
|
||||
int unit);
|
||||
EXPORT void device_load_samplerstate(device_t device,
|
||||
samplerstate_t samplerstate, int unit);
|
||||
EXPORT void device_load_vertexshader(device_t device, shader_t vertshader);
|
||||
|
|
|
@ -108,13 +108,69 @@ static inline void gl_add_samplers(struct gs_shader *shader,
|
|||
struct gl_shader_parser *glsp)
|
||||
{
|
||||
size_t i;
|
||||
|
||||
for (i = 0; i < glsp->parser.samplers.num; i++) {
|
||||
struct shader_sampler *sampler = glsp->parser.samplers.array+i;
|
||||
gl_add_sampler(shader, sampler);
|
||||
}
|
||||
}
|
||||
|
||||
static void get_attrib_type(const char *mapping, enum attrib_type *type,
|
||||
size_t *index)
|
||||
{
|
||||
if (strcmp(mapping, "POSITION") == 0) {
|
||||
*type = ATTRIB_POSITION;
|
||||
|
||||
} else if (strcmp(mapping, "NORMAL") == 0) {
|
||||
*type = ATTRIB_NORMAL;
|
||||
|
||||
} else if (strcmp(mapping, "TANGENT") == 0) {
|
||||
*type = ATTRIB_TANGENT;
|
||||
|
||||
} else if (strcmp(mapping, "COLOR") == 0) {
|
||||
*type = ATTRIB_COLOR;
|
||||
|
||||
} else if (astrcmp_n(mapping, "TEXCOORD", 8) == 0) {
|
||||
*type = ATTRIB_TEXCOORD;
|
||||
*index = (*(mapping+8)) - '0';
|
||||
return;
|
||||
|
||||
} else if (strcmp(mapping, "TARGET") == 0) {
|
||||
*type = ATTRIB_TARGET;
|
||||
}
|
||||
|
||||
*index = 0;
|
||||
}
|
||||
|
||||
static inline bool gl_add_attrib(struct gs_shader *shader,
|
||||
struct gl_parser_attrib *pa)
|
||||
{
|
||||
struct shader_attrib attrib = {0};
|
||||
get_attrib_type(pa->mapping, &attrib.type, &attrib.index);
|
||||
|
||||
attrib.attrib = glGetAttribLocation(shader->program, pa->name.array);
|
||||
if (!gl_success("glGetAttribLocation"))
|
||||
return false;
|
||||
|
||||
if (attrib.attrib == -1)
|
||||
return false;
|
||||
|
||||
da_push_back(shader->attribs, &attrib);
|
||||
return true;
|
||||
}
|
||||
|
||||
static inline bool gl_add_attribs(struct gs_shader *shader,
|
||||
struct gl_shader_parser *glsp)
|
||||
{
|
||||
size_t i;
|
||||
for (i = 0; i < glsp->attribs.num; i++) {
|
||||
struct gl_parser_attrib *pa = glsp->attribs.array+i;
|
||||
if (!gl_add_attrib(shader, pa))
|
||||
return false;
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
static bool gl_shader_init(struct gs_shader *shader,
|
||||
struct gl_shader_parser *glsp,
|
||||
const char *file, char **error_string)
|
||||
|
@ -140,6 +196,8 @@ static bool gl_shader_init(struct gs_shader *shader,
|
|||
|
||||
if (success)
|
||||
success = gl_add_params(shader, glsp);
|
||||
if (success)
|
||||
success = gl_add_attribs(shader, glsp);
|
||||
if (success)
|
||||
gl_add_samplers(shader, glsp);
|
||||
|
||||
|
@ -176,14 +234,22 @@ shader_t device_create_vertexshader(device_t device,
|
|||
const char *shader, const char *file,
|
||||
char **error_string)
|
||||
{
|
||||
return shader_create(device, SHADER_VERTEX, shader, file, error_string);
|
||||
struct gs_shader *ptr;
|
||||
ptr = shader_create(device, SHADER_VERTEX, shader, file, error_string);
|
||||
if (!ptr)
|
||||
blog(LOG_ERROR, "device_create_vertexshader (GL) failed");
|
||||
return ptr;
|
||||
}
|
||||
|
||||
shader_t device_create_pixelshader(device_t device,
|
||||
const char *shader, const char *file,
|
||||
char **error_string)
|
||||
{
|
||||
return shader_create(device, SHADER_PIXEL, shader, file, error_string);
|
||||
struct gs_shader *ptr;
|
||||
ptr = shader_create(device, SHADER_PIXEL, shader, file, error_string);
|
||||
if (!ptr)
|
||||
blog(LOG_ERROR, "device_create_pixelshader (GL) failed");
|
||||
return ptr;
|
||||
}
|
||||
|
||||
void shader_destroy(shader_t shader)
|
||||
|
|
|
@ -146,17 +146,24 @@ static void gl_write_storage_var(struct gl_shader_parser *glsp,
|
|||
if (st) {
|
||||
gl_unwrap_storage_struct(glsp, st, var->name, storage, prefix);
|
||||
} else {
|
||||
struct gl_parser_attrib attrib = {0};
|
||||
|
||||
if (storage) {
|
||||
dstr_cat(&glsp->gl_string, storage);
|
||||
dstr_cat(&glsp->gl_string, " ");
|
||||
}
|
||||
|
||||
if (prefix)
|
||||
dstr_cat(&attrib.name, prefix);
|
||||
dstr_cat(&attrib.name, var->name);
|
||||
|
||||
gl_write_type(glsp, var->type);
|
||||
dstr_cat(&glsp->gl_string, " ");
|
||||
if (prefix)
|
||||
dstr_cat(&glsp->gl_string, prefix);
|
||||
dstr_cat(&glsp->gl_string, var->name);
|
||||
dstr_cat_dstr(&glsp->gl_string, &attrib.name);
|
||||
dstr_cat(&glsp->gl_string, ";\n");
|
||||
|
||||
attrib.mapping = var->mapping;
|
||||
da_push_back(glsp->attribs, &attrib);
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
@ -27,21 +27,40 @@
|
|||
#include "util/dstr.h"
|
||||
#include "graphics/shader-parser.h"
|
||||
|
||||
struct gl_shader_parser {
|
||||
struct dstr gl_string;
|
||||
struct shader_parser parser;
|
||||
struct gl_parser_attrib {
|
||||
struct dstr name;
|
||||
const char *mapping;
|
||||
};
|
||||
|
||||
DARRAY(uint32_t) texture_samplers;
|
||||
static inline gl_parser_attrib_free(struct gl_parser_attrib *attr)
|
||||
{
|
||||
dstr_free(&attr->name);
|
||||
}
|
||||
|
||||
struct gl_shader_parser {
|
||||
struct shader_parser parser;
|
||||
struct dstr gl_string;
|
||||
|
||||
DARRAY(uint32_t) texture_samplers;
|
||||
DARRAY(struct gl_parser_attrib) attribs;
|
||||
};
|
||||
|
||||
static inline void gl_shader_parser_init(struct gl_shader_parser *glsp)
|
||||
{
|
||||
shader_parser_init(&glsp->parser);
|
||||
dstr_init(&glsp->gl_string);
|
||||
da_init(glsp->texture_samplers);
|
||||
da_init(glsp->attribs);
|
||||
}
|
||||
|
||||
static inline void gl_shader_parser_free(struct gl_shader_parser *glsp)
|
||||
{
|
||||
size_t i;
|
||||
for (i = 0; i < glsp->attribs.num; i++)
|
||||
gl_parser_attrib_free(glsp->attribs.array+i);
|
||||
|
||||
da_free(glsp->attribs);
|
||||
da_free(glsp->texture_samplers);
|
||||
dstr_free(&glsp->gl_string);
|
||||
shader_parser_free(&glsp->parser);
|
||||
}
|
||||
|
|
|
@ -115,10 +115,7 @@ samplerstate_t device_create_samplerstate(device_t device,
|
|||
enum gs_texture_type device_gettexturetype(device_t device,
|
||||
texture_t texture)
|
||||
{
|
||||
}
|
||||
|
||||
void device_load_vertexbuffer(device_t device, vertbuffer_t vertbuffer)
|
||||
{
|
||||
return texture->type;
|
||||
}
|
||||
|
||||
void device_load_indexbuffer(device_t device, indexbuffer_t indexbuffer)
|
||||
|
@ -129,16 +126,6 @@ void device_load_texture(device_t device, texture_t tex, int unit)
|
|||
{
|
||||
}
|
||||
|
||||
void device_load_cubetexture(device_t device, texture_t cubetex,
|
||||
int unit)
|
||||
{
|
||||
}
|
||||
|
||||
void device_load_volumetexture(device_t device, texture_t voltex,
|
||||
int unit)
|
||||
{
|
||||
}
|
||||
|
||||
void device_load_samplerstate(device_t device,
|
||||
samplerstate_t samplerstate, int unit)
|
||||
{
|
||||
|
@ -331,22 +318,31 @@ void swapchain_destroy(swapchain_t swapchain)
|
|||
|
||||
void volumetexture_destroy(texture_t voltex)
|
||||
{
|
||||
/* TODO */
|
||||
}
|
||||
|
||||
uint32_t volumetexture_getwidth(texture_t voltex)
|
||||
{
|
||||
/* TODO */
|
||||
return 0;
|
||||
}
|
||||
|
||||
uint32_t volumetexture_getheight(texture_t voltex)
|
||||
{
|
||||
/* TODO */
|
||||
return 0;
|
||||
}
|
||||
|
||||
uint32_t volumetexture_getdepth(texture_t voltex)
|
||||
{
|
||||
/* TODO */
|
||||
return 0;
|
||||
}
|
||||
|
||||
enum gs_color_format volumetexture_getcolorformat(texture_t voltex)
|
||||
{
|
||||
/* TODO */
|
||||
return GS_UNKNOWN;
|
||||
}
|
||||
|
||||
void samplerstate_destroy(samplerstate_t samplerstate)
|
||||
|
|
|
@ -185,37 +185,54 @@ extern void convert_sampler_info(struct gs_sampler_state *sampler,
|
|||
struct gs_sampler_info *info);
|
||||
|
||||
struct gs_sampler_state {
|
||||
GLint min_filter;
|
||||
GLint mag_filter;
|
||||
GLint address_u;
|
||||
GLint address_v;
|
||||
GLint address_w;
|
||||
GLint max_anisotropy;
|
||||
GLint min_filter;
|
||||
GLint mag_filter;
|
||||
GLint address_u;
|
||||
GLint address_v;
|
||||
GLint address_w;
|
||||
GLint max_anisotropy;
|
||||
};
|
||||
|
||||
struct shader_param {
|
||||
char *name;
|
||||
enum shader_param_type type;
|
||||
GLint param;
|
||||
GLint texture_id;
|
||||
size_t sampler_id;
|
||||
int array_count;
|
||||
|
||||
struct gs_texture *texture;
|
||||
char *name;
|
||||
GLint param;
|
||||
GLint texture_id;
|
||||
size_t sampler_id;
|
||||
int array_count;
|
||||
|
||||
DARRAY(uint8_t) cur_value;
|
||||
DARRAY(uint8_t) def_value;
|
||||
bool changed;
|
||||
struct gs_texture *texture;
|
||||
|
||||
DARRAY(uint8_t) cur_value;
|
||||
DARRAY(uint8_t) def_value;
|
||||
bool changed;
|
||||
};
|
||||
|
||||
enum attrib_type {
|
||||
ATTRIB_POSITION,
|
||||
ATTRIB_NORMAL,
|
||||
ATTRIB_TANGENT,
|
||||
ATTRIB_COLOR,
|
||||
ATTRIB_TEXCOORD,
|
||||
ATTRIB_TARGET
|
||||
};
|
||||
|
||||
struct shader_attrib {
|
||||
GLint attrib;
|
||||
size_t index;
|
||||
enum attrib_type type;
|
||||
};
|
||||
|
||||
struct gs_shader {
|
||||
device_t device;
|
||||
enum shader_type type;
|
||||
GLuint program;
|
||||
device_t device;
|
||||
enum shader_type type;
|
||||
GLuint program;
|
||||
|
||||
struct shader_param *viewproj;
|
||||
struct shader_param *world;
|
||||
struct shader_param *viewproj;
|
||||
struct shader_param *world;
|
||||
|
||||
DARRAY(struct shader_attrib) attribs;
|
||||
DARRAY(struct gs_sampler_state) samplers;
|
||||
DARRAY(struct shader_param) params;
|
||||
};
|
||||
|
@ -226,6 +243,7 @@ struct gs_vertex_buffer {
|
|||
GLuint tangent_buffer;
|
||||
GLuint color_buffer;
|
||||
DARRAY(GLuint) uv_buffers;
|
||||
DARRAY(size_t) uv_sizes;
|
||||
|
||||
device_t device;
|
||||
bool dynamic;
|
||||
|
@ -233,15 +251,15 @@ struct gs_vertex_buffer {
|
|||
};
|
||||
|
||||
struct gs_index_buffer {
|
||||
GLuint buffer;
|
||||
enum gs_index_type type;
|
||||
GLuint gl_type;
|
||||
GLuint buffer;
|
||||
enum gs_index_type type;
|
||||
GLuint gl_type;
|
||||
|
||||
device_t device;
|
||||
void *data;
|
||||
size_t num;
|
||||
size_t size;
|
||||
bool dynamic;
|
||||
device_t device;
|
||||
void *data;
|
||||
size_t num;
|
||||
size_t size;
|
||||
bool dynamic;
|
||||
};
|
||||
|
||||
struct gs_texture {
|
||||
|
@ -302,11 +320,16 @@ struct gs_device {
|
|||
struct gl_platform *plat;
|
||||
enum copy_type copy_type;
|
||||
|
||||
struct gs_texture *cur_render_texture;
|
||||
texture_t cur_render_target;
|
||||
zstencil_t cur_zstencil_buffer;
|
||||
int cur_render_side;
|
||||
struct gs_texture *cur_textures[GS_MAX_TEXTURES];
|
||||
struct gs_sampler *cur_samplers[GS_MAX_TEXTURES];
|
||||
struct gs_swap_chain *cur_swap;
|
||||
texture_t cur_textures[GS_MAX_TEXTURES];
|
||||
samplerstate_t cur_samplers[GS_MAX_TEXTURES];
|
||||
vertbuffer_t cur_vertex_buffer;
|
||||
indexbuffer_t cur_index_buffer;
|
||||
shader_t cur_vertex_shader;
|
||||
shader_t cur_pixel_shader;
|
||||
swapchain_t cur_swap;
|
||||
};
|
||||
|
||||
extern struct gl_platform *gl_platform_create(device_t device,
|
||||
|
|
|
@ -50,6 +50,7 @@ static bool init_vb(struct gs_vertex_buffer *vb)
|
|||
}
|
||||
|
||||
da_reserve(vb->uv_buffers, vb->data->num_tex);
|
||||
da_reserve(vb->uv_sizes, vb->data->num_tex);
|
||||
|
||||
for (i = 0; i < vb->data->num_tex; i++) {
|
||||
GLuint tex_buffer;
|
||||
|
@ -61,6 +62,7 @@ static bool init_vb(struct gs_vertex_buffer *vb)
|
|||
return false;
|
||||
|
||||
da_push_back(vb->uv_buffers, &tex_buffer);
|
||||
da_push_back(vb->uv_sizes, &tv->width);
|
||||
}
|
||||
|
||||
if (!vb->dynamic) {
|
||||
|
@ -109,6 +111,7 @@ void vertexbuffer_destroy(vertbuffer_t vb)
|
|||
gl_delete_buffers((GLsizei)vb->uv_buffers.num,
|
||||
vb->uv_buffers.array);
|
||||
|
||||
da_free(vb->uv_sizes);
|
||||
da_free(vb->uv_buffers);
|
||||
vbdata_destroy(vb->data);
|
||||
|
||||
|
@ -170,3 +173,83 @@ struct vb_data *vertexbuffer_getdata(vertbuffer_t vb)
|
|||
{
|
||||
return vb->data;
|
||||
}
|
||||
|
||||
static inline GLuint get_vb_buffer(struct gs_vertex_buffer *vb,
|
||||
enum attrib_type type, size_t index, GLint *width,
|
||||
GLenum *gl_type)
|
||||
{
|
||||
*gl_type = GL_FLOAT;
|
||||
*width = 4;
|
||||
|
||||
if (type == ATTRIB_POSITION) {
|
||||
return vb->vertex_buffer;
|
||||
} else if (type == ATTRIB_NORMAL) {
|
||||
return vb->normal_buffer;
|
||||
} else if (type == ATTRIB_TANGENT) {
|
||||
return vb->tangent_buffer;
|
||||
} else if (type == ATTRIB_COLOR) {
|
||||
*gl_type = GL_UNSIGNED_BYTE;
|
||||
return vb->color_buffer;
|
||||
} else if (type == ATTRIB_TEXCOORD) {
|
||||
if (vb->uv_buffers.num <= index)
|
||||
return 0;
|
||||
|
||||
*width = (GLint)vb->uv_sizes.array[index];
|
||||
return vb->uv_buffers.array[index];
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
static bool load_vb_buffer(struct gs_shader *shader,
|
||||
struct shader_attrib *attrib,
|
||||
struct gs_vertex_buffer *vb)
|
||||
{
|
||||
GLenum type;
|
||||
GLint width;
|
||||
GLuint buffer;
|
||||
bool success = true;
|
||||
|
||||
buffer = get_vb_buffer(vb, attrib->type, attrib->index, &width, &type);
|
||||
if (!buffer) {
|
||||
blog(LOG_ERROR, "Vertex buffer does not have the required "
|
||||
"inputs for vertex shader");
|
||||
return false;
|
||||
}
|
||||
|
||||
if (!gl_bind_buffer(GL_ARRAY_BUFFER, buffer))
|
||||
return false;
|
||||
|
||||
glVertexAttribPointer(attrib->attrib, width, type, GL_TRUE, 0, 0);
|
||||
if (!gl_success("glVertexAttribPointer"))
|
||||
success = false;
|
||||
|
||||
gl_bind_buffer(GL_ARRAY_BUFFER, 0);
|
||||
return success;
|
||||
}
|
||||
|
||||
static inline bool load_vb_buffers(struct gs_shader *shader,
|
||||
struct gs_vertex_buffer *vb)
|
||||
{
|
||||
size_t i;
|
||||
for (i = 0; i < shader->attribs.num; i++) {
|
||||
struct shader_attrib *attrib = shader->attribs.array+i;
|
||||
if (!load_vb_buffer(shader, attrib, vb))
|
||||
return false;
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
void device_load_vertexbuffer(device_t device, vertbuffer_t vb)
|
||||
{
|
||||
if (device->cur_vertex_buffer == vb)
|
||||
return;
|
||||
|
||||
device->cur_vertex_buffer = vb;
|
||||
if (!device->cur_vertex_shader)
|
||||
return;
|
||||
|
||||
if (!load_vb_buffers(device->cur_vertex_shader, vb))
|
||||
blog(LOG_ERROR, "device_load_vertexbuffer (GL) failed");
|
||||
}
|
||||
|
|
Loading…
Reference in New Issue