diff options
Diffstat (limited to 'src/engine/client')
| -rw-r--r-- | src/engine/client/ec_gfx.c | 49 | ||||
| -rw-r--r-- | src/engine/client/ec_ui.c | 271 | ||||
| -rw-r--r-- | src/engine/client/ec_ui.h | 48 |
3 files changed, 233 insertions, 135 deletions
diff --git a/src/engine/client/ec_gfx.c b/src/engine/client/ec_gfx.c index 70712ded..a87818bc 100644 --- a/src/engine/client/ec_gfx.c +++ b/src/engine/client/ec_gfx.c @@ -18,6 +18,8 @@ #define GL_COMPRESSED_RGB_ARB 0x84ED #define GL_COMPRESSED_RGBA_ARB 0x84EE +#define TEXTURE_MAX_ANISOTROPY_EXT 0x84FE + enum { DRAWING_QUADS=1, @@ -612,8 +614,31 @@ void gfx_screenshot() do_screenshot = 1; } +static int64 next_frame = 0; +static int record = 0; + void gfx_swap() { + if(record) + { + int w = screen_width; + int h = screen_height; + unsigned char *pixel_data = (unsigned char *)mem_alloc(w*(h+1)*3, 1); + /*unsigned char *temp_row = pixel_data+w*h*3;*/ + glReadPixels(0,0, w, h, GL_RGB, GL_UNSIGNED_BYTE, pixel_data); + + /* clean up */ + mem_free(pixel_data); + + if(next_frame) + next_frame += time_freq()/30; + else + next_frame = time_get() + time_freq()/30; + + while(time_get() < next_frame) + (void)0; + } + if(do_screenshot) { /* fetch image data */ @@ -642,8 +667,8 @@ void gfx_swap() for(; index < 1000; index++) { IOHANDLE io; - sprintf(filename, "screenshots/screenshot%04d.png", index); - engine_savepath(filename, wholepath, sizeof(wholepath)); + sprintf(wholepath, "/home/kma/Desktop/prq/blogimg/editor/screenshot%04d.png", index); + /*engine_savepath(filename, wholepath, sizeof(wholepath));*/ io = io_open(wholepath, IOFLAG_READ); if(io) @@ -783,6 +808,26 @@ void gfx_quads_setsubset(float tl_u, float tl_v, float br_u, float br_v) texture[3].v = br_v; } +void gfx_quads_setsubset_free( + float x0, float y0, + float x1, float y1, + float x2, float y2, + float x3, float y3) +{ + texture[0].u = x0; + texture[0].v = y0; + + texture[1].u = x1; + texture[1].v = y1; + + texture[2].u = x2; + texture[2].v = y2; + + texture[3].u = x3; + texture[3].v = y3; +} + + static void rotate(VEC3 *center, VEC3 *point) { float x = point->x - center->x; diff --git a/src/engine/client/ec_ui.c b/src/engine/client/ec_ui.c index 5ba9c0d9..3ce40f9c 100644 --- a/src/engine/client/ec_ui.c +++ b/src/engine/client/ec_ui.c @@ -24,12 +24,14 @@ static const void *becomming_hot_item = 0; static float mouse_x, mouse_y; /* in gui space */ static float mouse_wx, mouse_wy; /* in world space */ static unsigned mouse_buttons = 0; +static unsigned last_mouse_buttons = 0; float ui_mouse_x() { return mouse_x; } float ui_mouse_y() { return mouse_y; } float ui_mouse_world_x() { return mouse_wx; } float ui_mouse_world_y() { return mouse_wy; } int ui_mouse_button(int index) { return (mouse_buttons>>index)&1; } +int ui_mouse_button_clicked(int index) { return ui_mouse_button(index) && !((last_mouse_buttons>>index)&1) ; } void ui_set_hot_item(const void *id) { becomming_hot_item = id; } void ui_set_active_item(const void *id) { active_item = id; if (id) last_active_item = id; } @@ -44,6 +46,7 @@ int ui_update(float mx, float my, float mwx, float mwy, int buttons) mouse_y = my; mouse_wx = mwx; mouse_wy = mwy; + last_mouse_buttons = mouse_buttons; mouse_buttons = buttons; hot_item = becomming_hot_item; if(active_item) @@ -52,226 +55,238 @@ int ui_update(float mx, float my, float mwx, float mwy, int buttons) return 0; } -int ui_mouse_inside(float x, float y, float w, float h) +int ui_mouse_inside(const RECT *r) { - if(mouse_x >= x && mouse_x <= x+w && mouse_y >= y && mouse_y <= y+h) + if(mouse_x >= r->x && mouse_x <= r->x+r->w && mouse_y >= r->y && mouse_y <= r->y+r->h) return 1; return 0; } -void ui_do_image(int texture, float x, float y, float w, float h) -{ - gfx_blend_normal(); - gfx_texture_set(texture); - gfx_quads_begin(); - gfx_setcolor(1,1,1,1); - gfx_quads_setsubset( - 0.0f, /* startx */ - 0.0f, /* starty */ - 1.0f, /* endx */ - 1.0f); /* endy */ - gfx_quads_drawTL(x,y,w,h); - gfx_quads_end(); -} +static RECT screen = { 0.0f, 0.0f, 848.0f, 480.0f }; -void ui_do_label(float x, float y, const char *text, float size) +RECT *ui_screen() { - gfx_blend_normal(); - gfx_texture_set(current_font->font_texture); - gfx_pretty_text(x, y, size, text, -1); -} + float aspect = gfx_screenaspect(); + float w, h; -int ui_do_button(const void *id, const char *text, int checked, float x, float y, float w, float h, draw_button_callback draw_func, void *extra) -{ - /* logic */ - int r = 0; - int inside = ui_mouse_inside(x,y,w,h); + h = 600; + w = aspect*h; - if(ui_active_item() == id) - { - if(!ui_mouse_button(0)) - { - if(inside) - r = 1; - ui_set_active_item(0); - } - } - else if(ui_hot_item() == id) - { - if(ui_mouse_button(0)) - ui_set_active_item(id); - } - - if(inside) - ui_set_hot_item(id); + screen.w = w; + screen.h = h; - draw_func(id, text, checked, x, y, w, h, extra); - return r; + return &screen; } -static float scale = 1.0f; -#define MEMORY_SIZE 10*1024 -static struct rect memory[MEMORY_SIZE]; -static int memory_used = 0; -static struct rect screen = { 0.0f, 0.0f, 848.0f, 480.0f }; - -void ui_foreach_rect(rect_fun fun) +void ui_set_scale(float s) { - int hrm; - for (hrm = 0; hrm < memory_used; hrm++) - fun(&memory[hrm]); + config.ui_scale = (int)(s*100.0f); } -static void add_rect(struct rect *r) +float ui_scale() { - if (memory_used < MEMORY_SIZE) - memory[memory_used++] = *r; - else - dbg_msg("ui", "rect memory full."); + return config.ui_scale/100.0f; } -struct rect *ui_screen() +void ui_clip_enable(const RECT *r) { - if (config.debug) - { - memory_used = 0; - } - - return &screen; + float xscale = gfx_screenwidth()/ui_screen()->w; + float yscale = gfx_screenheight()/ui_screen()->h; + gfx_clip_enable((int)(r->x*xscale), (int)(r->y*yscale), (int)(r->w*xscale), (int)(r->h*yscale)); } -void ui_scale(float s) +void ui_clip_disable() { - scale = s; + gfx_clip_disable(); } -void ui_hsplit_t(const struct rect *original, int pixels, struct rect *top, struct rect *bottom) +void ui_hsplit_t(const RECT *original, float cut, RECT *top, RECT *bottom) { - struct rect r = *original; - pixels *= scale; + RECT r = *original; + cut *= ui_scale(); if (top) { top->x = r.x; top->y = r.y; top->w = r.w; - top->h = pixels; + top->h = cut; } if (bottom) { bottom->x = r.x; - bottom->y = r.y + pixels; + bottom->y = r.y + cut; bottom->w = r.w; - bottom->h = r.h - pixels; - } - - if (config.debug) - { - if (top) - add_rect(top); - if (bottom) - add_rect(bottom); + bottom->h = r.h - cut; } } -void ui_hsplit_b(const struct rect *original, int pixels, struct rect *top, struct rect *bottom) +void ui_hsplit_b(const RECT *original, float cut, RECT *top, RECT *bottom) { - struct rect r = *original; - pixels *= scale; + RECT r = *original; + cut *= ui_scale(); if (top) { top->x = r.x; top->y = r.y; top->w = r.w; - top->h = r.h - pixels; + top->h = r.h - cut; } if (bottom) { bottom->x = r.x; - bottom->y = r.y + r.h - pixels; + bottom->y = r.y + r.h - cut; bottom->w = r.w; - bottom->h = pixels; - } - - if (config.debug) - { - if (top) - add_rect(top); - if (bottom) - add_rect(bottom); + bottom->h = cut; } } -void ui_vsplit_l(const struct rect *original, int pixels, struct rect *left, struct rect *right) + +void ui_vsplit_mid(const RECT *original, RECT *left, RECT *right) { - struct rect r = *original; - pixels *= scale; + RECT r = *original; + float cut = r.w/2; if (left) { left->x = r.x; left->y = r.y; - left->w = pixels; + left->w = cut; left->h = r.h; } if (right) { - right->x = r.x + pixels; + right->x = r.x + cut; right->y = r.y; - right->w = r.w - pixels; + right->w = r.w - cut; right->h = r.h; } +} + +void ui_vsplit_l(const RECT *original, float cut, RECT *left, RECT *right) +{ + RECT r = *original; + cut *= ui_scale(); + + if (left) + { + left->x = r.x; + left->y = r.y; + left->w = cut; + left->h = r.h; + } - if (config.debug) + if (right) { - if (left) - add_rect(left); - if (right) - add_rect(right); + right->x = r.x + cut; + right->y = r.y; + right->w = r.w - cut; + right->h = r.h; } } -void ui_vsplit_r(const struct rect *original, int pixels, struct rect *left, struct rect *right) +void ui_vsplit_r(const RECT *original, float cut, RECT *left, RECT *right) { - struct rect r = *original; - pixels *= scale; + RECT r = *original; + cut *= ui_scale(); if (left) { left->x = r.x; left->y = r.y; - left->w = r.w - pixels; + left->w = r.w - cut; left->h = r.h; } if (right) { - right->x = r.x + r.w - pixels; + right->x = r.x + r.w - cut; right->y = r.y; - right->w = pixels; + right->w = cut; right->h = r.h; } +} - if (config.debug) - { - if (left) - add_rect(left); - if (right) - add_rect(right); - } +void ui_margin(const RECT *original, float cut, RECT *other_rect) +{ + RECT r = *original; + cut *= ui_scale(); + + other_rect->x = r.x + cut; + other_rect->y = r.y + cut; + other_rect->w = r.w - 2*cut; + other_rect->h = r.h - 2*cut; +} + +void ui_vmargin(const RECT *original, float cut, RECT *other_rect) +{ + RECT r = *original; + cut *= ui_scale(); + + other_rect->x = r.x + cut; + other_rect->y = r.y; + other_rect->w = r.w - 2*cut; + other_rect->h = r.h; } -void ui_margin(const struct rect *original, int pixels, struct rect *other_rect) +void ui_hmargin(const RECT *original, float cut, RECT *other_rect) { - struct rect r = *original; - pixels *= scale; + RECT r = *original; + cut *= ui_scale(); - other_rect->x = r.x + pixels; - other_rect->y = r.y + pixels; - other_rect->w = r.w - 2*pixels; - other_rect->h = r.h - 2*pixels; + other_rect->x = r.x; + other_rect->y = r.y + cut; + other_rect->w = r.w; + other_rect->h = r.h - 2*cut; +} + +int ui_do_button(const void *id, const char *text, int checked, const RECT *r, ui_draw_button_func draw_func, const void *extra) +{ + /* logic */ + int ret = 0; + int inside = ui_mouse_inside(r); + + if(ui_active_item() == id) + { + if(!ui_mouse_button(0)) + { + if(inside && checked >= 0) + ret = 1; + ui_set_active_item(0); + } + } + else if(ui_hot_item() == id) + { + if(ui_mouse_button(0)) + ui_set_active_item(id); + } + + if(inside) + ui_set_hot_item(id); + + if(draw_func) + draw_func(id, text, checked, r, extra); + return ret; +} + +void ui_do_label(const RECT *r, const char *text, float size, int align, int max_width) +{ + gfx_blend_normal(); + size *= ui_scale(); + if(align == 0) + { + float tw = gfx_pretty_text_width(size, text, max_width); + gfx_pretty_text(r->x + r->w/2-tw/2, r->y, size, text, max_width); + } + else if(align < 0) + gfx_pretty_text(r->x, r->y, size, text, max_width); + else if(align > 0) + { + float tw = gfx_pretty_text_width(size, text, max_width); + gfx_pretty_text(r->x + r->w-tw, r->y, size, text, max_width); + } } diff --git a/src/engine/client/ec_ui.h b/src/engine/client/ec_ui.h index 15c63b90..83dbe37d 100644 --- a/src/engine/client/ec_ui.h +++ b/src/engine/client/ec_ui.h @@ -6,6 +6,28 @@ extern "C" { #endif + + +typedef struct +{ + float x, y, w, h; +} RECT; + +enum +{ + CORNER_TL=1, + CORNER_TR=2, + CORNER_BL=4, + CORNER_BR=8, + + CORNER_T=CORNER_TL|CORNER_TR, + CORNER_B=CORNER_BL|CORNER_BR, + CORNER_R=CORNER_TR|CORNER_BR, + CORNER_L=CORNER_TL|CORNER_BL, + + CORNER_ALL=CORNER_T|CORNER_B +}; + int ui_update(float mx, float my, float mwx, float mwy, int buttons); float ui_mouse_x(); @@ -13,6 +35,7 @@ float ui_mouse_y(); float ui_mouse_world_x(); float ui_mouse_world_y(); int ui_mouse_button(int index); +int ui_mouse_button_clicked(int index); void ui_set_hot_item(const void *id); void ui_set_active_item(const void *id); @@ -21,13 +44,28 @@ const void *ui_hot_item(); const void *ui_active_item(); const void *ui_last_active_item(); -int ui_mouse_inside(float x, float y, float w, float h); +int ui_mouse_inside(const RECT *r); + +RECT *ui_screen(); +void ui_set_scale(float s); +float ui_scale(); +void ui_clip_enable(const RECT *r); +void ui_clip_disable(); + +void ui_hsplit_t(const RECT *original, float cut, RECT *top, RECT *bottom); +void ui_hsplit_b(const RECT *original, float cut, RECT *top, RECT *bottom); +void ui_vsplit_mid(const RECT *original, RECT *left, RECT *right); +void ui_vsplit_l(const RECT *original, float cut, RECT *left, RECT *right); +void ui_vsplit_r(const RECT *original, float cut, RECT *left, RECT *right); + +void ui_margin(const RECT *original, float cut, RECT *other_rect); +void ui_vmargin(const RECT *original, float cut, RECT *other_rect); +void ui_hmargin(const RECT *original, float cut, RECT *other_rect); -typedef void (*draw_button_callback)(const void *id, const char *text, int checked, float x, float y, float w, float h, void *extra); +typedef void (*ui_draw_button_func)(const void *id, const char *text, int checked, const RECT *r, const void *extra); +int ui_do_button(const void *id, const char *text, int checked, const RECT *r, ui_draw_button_func draw_func, const void *extra); +void ui_do_label(const RECT *r, const char *text, float size, int align, int max_width); -void ui_do_image(int texture, float x, float y, float w, float h); -void ui_do_label(float x, float y, const char *text, float size); -int ui_do_button(const void *id, const char *text, int checked, float x, float y, float w, float h, draw_button_callback draw_func, void *extra); #ifdef __cplusplus } |