Allow per-context transformations (#9)

This commit is contained in:
Kevin Harrison 2016-12-29 23:17:13 -05:00
parent 8b5482e74f
commit 26f05c82e4
6 changed files with 377 additions and 95 deletions

View file

@ -1,3 +1,5 @@
-- Demonstrate a number of custom drawing functions.
local img = love.graphics.newImage 'skin/button.png'
return function (ui)

View file

@ -7,52 +7,61 @@ local draw = require 'draw'
local overview = require 'overview'
local style = require 'style'
local skin = require 'skin'
local transform = require 'transform'
local ui
local ui1, ui2
function love.load()
ui = nuklear.init()
ui1, ui2 = nuklear.newUI(), nuklear.newUI()
end
function love.update(dt)
ui:frameBegin()
calculator(ui)
style(ui)
overview(ui)
draw(ui)
skin(ui)
ui:frameEnd()
ui1:frameBegin()
calculator(ui1)
style(ui1)
overview(ui1)
draw(ui1)
skin(ui1)
ui1:frameEnd()
ui2:frameBegin()
transform(ui2)
ui2:frameEnd()
end
function love.draw()
ui:draw()
ui1:draw()
ui2:draw()
love.graphics.print("Current FPS: "..tostring(love.timer.getFPS( )), 10, 10)
end
local function input(name, ...)
return ui2[name](ui2, ...) or ui1[name](ui1, ...)
end
function love.keypressed(key, scancode, isrepeat)
ui:keypressed(key, scancode, isrepeat)
input('keypressed', key, scancode, isrepeat)
end
function love.keyreleased(key, scancode)
ui:keyreleased(key, scancode)
input('keyreleased', key, scancode)
end
function love.mousepressed(x, y, button, istouch)
ui:mousepressed(x, y, button, istouch)
input('mousepressed', x, y, button, istouch)
end
function love.mousereleased(x, y, button, istouch)
ui:mousereleased(x, y, button, istouch)
input('mousereleased', x, y, button, istouch)
end
function love.mousemoved(x, y, dx, dy, istouch)
ui:mousemoved(x, y, dx, dy, istouch)
input('mousemoved', x, y, dx, dy, istouch)
end
function love.textinput(text)
ui:textinput(text)
input('textinput', text)
end
function love.wheelmoved(x, y)
ui:wheelmoved(x, y)
input('wheelmoved', x, y)
end

View file

@ -24,7 +24,7 @@ return function (ui)
ui:menuEnd()
end
ui:menubarEnd()
ui:layoutRow('dynamic', 400, 3)
ui:layoutRow('dynamic', 375, 3)
if ui:groupBegin('Group 1', 'border') then
ui:layoutRow('dynamic', 30, 1)
ui:label('Left label')

View file

@ -1,3 +1,5 @@
-- Basic skinning example.
local windowHeader = love.graphics.newImage 'skin/window_header.png'
local checkboxSkin = love.graphics.newImage 'skin/checkbox_false.png'
local checkboxCheck = love.graphics.newImage 'skin/checkbox_true.png'

14
example/transform.lua Normal file
View file

@ -0,0 +1,14 @@
-- Apply transformations to a basic UI.
return function(ui)
local t = love.timer.getTime()
ui:translate(350 + 100 * math.cos(t / 4), 350 + 100 * math.sin(t / 4))
ui:rotate(t / 8)
ui:scale(1 + math.sin(t / 4) / 2, 1 + math.cos(t / 4) / 2)
ui:shear(math.cos(t / 8) / 4, math.sin(t / 8) / 4)
if ui:windowBegin('Transform', 0, 0, 200, 200, 'border', 'title') then
ui:layoutRow('dynamic', 150, 1)
ui:label('You can apply transformations to the UI using ui:rotate, ui:scale, ui:shear, and ui:translate.', 'wrap')
end
ui:windowEnd()
end

View file

@ -4,6 +4,7 @@
* adapted to LOVE in 2016 by Kevin Harrison
*/
#include <math.h>
#include <stdio.h>
#include <string.h>
@ -38,18 +39,22 @@
#define NK_LOVE_COMBOBOX_MAX_ITEMS 1024
#define NK_LOVE_MAX_FONTS 1024
#define NK_LOVE_MAX_RATIOS 1024
#define NK_LOVE_GRADIENT_RESOLUTION 32
static lua_State *L;
static char *edit_buffer;
static const char **combobox_items;
static float *points;
struct nk_love_context {
static struct nk_love_context {
struct nk_context nkctx;
struct nk_user_font *fonts;
int font_count;
float *layout_ratios;
int layout_ratio_count;
float T[9];
float Ti[9];
int transform_allowed;
} *context;
static void nk_love_assert(int pass, const char *msg)
@ -101,9 +106,17 @@ static struct nk_love_context *nk_love_checkcontext(int index)
static void nk_love_assert_context(int index)
{
struct nk_love_context *ctx = nk_love_checkcontext(index);
ctx->transform_allowed = 0;
nk_love_assert(ctx == context, "%s: UI calls must reside between ui:frameBegin and ui:frameEnd");
}
static void nk_love_assert_transform(void)
{
struct nk_love_context *ctx = nk_love_checkcontext(1);
nk_love_assert(ctx == context && ctx->transform_allowed,
"%s: UI transformations must occur directly after ui:frameBegin");
}
static void nk_love_pushregistry(const char *name)
{
lua_getfield(L, LUA_REGISTRYINDEX, "nuklear");
@ -240,6 +253,21 @@ static struct nk_color nk_love_checkcolor(int index)
return color;
}
static void nk_love_color(int r, int g, int b, int a, char *color_string)
{
r = NK_CLAMP(0, r, 255);
g = NK_CLAMP(0, g, 255);
b = NK_CLAMP(0, b, 255);
a = NK_CLAMP(0, a, 255);
const char *format_string;
if (a < 255) {
format_string = "#%02x%02x%02x%02x";
} else {
format_string = "#%02x%02x%02x";
}
sprintf(color_string, format_string, r, g, b, a);
}
static nk_flags nk_love_parse_window_flags(int flags_begin)
{
int argc = lua_gettop(L);
@ -490,6 +518,15 @@ static int nk_love_checkboolean(lua_State *L, int index)
return lua_toboolean(L, index);
}
static void nk_love_transform(float *T, int *x, int *y)
{
float rx, ry;
rx = *x * T[0] + *y * T[3] + T[6];
ry = *x * T[1] + *y * T[4] + T[7];
*x = (int) rx;
*y = (int) ry;
}
static void nk_love_configureGraphics(int line_thickness, struct nk_color col)
{
lua_getglobal(L, "love");
@ -530,10 +567,19 @@ static void nk_love_scissor(int x, int y, int w, int h)
lua_getglobal(L, "love");
lua_getfield(L, -1, "graphics");
lua_getfield(L, -1, "setScissor");
lua_pushnumber(L, x);
lua_pushnumber(L, y);
lua_pushnumber(L, w);
lua_pushnumber(L, h);
int x1 = x, y1 = y, x2 = x + w, y2 = y, x3 = x, y3 = y + h, x4 = x + w, y4 = y + h;
nk_love_transform(context->T, &x1, &y1);
nk_love_transform(context->T, &x2, &y2);
nk_love_transform(context->T, &x3, &y3);
nk_love_transform(context->T, &x4, &y4);
int left = NK_MIN(NK_MIN(x1, x2), NK_MIN(x3, x4));
int top = NK_MIN(NK_MIN(y1, y2), NK_MIN(y3, y4));
int right = NK_MAX(NK_MAX(x1, x2), NK_MAX(x3, x4));
int bottom = NK_MAX(NK_MAX(y1, y2), NK_MAX(y3, y4));
lua_pushnumber(L, left);
lua_pushnumber(L, top);
lua_pushnumber(L, right - left);
lua_pushnumber(L, bottom - top);
lua_call(L, 4, 0);
lua_pop(L, 2);
}
@ -727,59 +773,57 @@ static void interpolate_color(struct nk_color c1, struct nk_color c2,
}
static void nk_love_draw_rect_multi_color(int x, int y, unsigned int w,
unsigned int h, struct nk_color left, struct nk_color top,
struct nk_color right, struct nk_color bottom)
unsigned int h, struct nk_color top_left, struct nk_color top_right,
struct nk_color bottom_left, struct nk_color bottom_right)
{
lua_getglobal(L, "love");
lua_getfield(L, -1, "graphics");
lua_getfield(L, -1, "push");
lua_pushstring(L, "all");
lua_call(L, 1, 0);
lua_getfield(L, -1, "setColor");
lua_pushnumber(L, 255);
lua_pushnumber(L, 255);
lua_pushnumber(L, 255);
lua_call(L, 3, 0);
lua_getfield(L, -1, "setPointSize");
lua_pushnumber(L, 1);
lua_call(L, 1, 0);
lua_pop(L, 2);
struct nk_color X1, X2, Y;
float fraction_x, fraction_y;
int i,j;
lua_getfield(L, -1, "points");
lua_createtable(L, w * h, 0);
for (j = 0; j < h; j++) {
fraction_y = ((float)j) / h;
for (i = 0; i < w; i++) {
fraction_x = ((float)i) / w;
interpolate_color(left, top, &X1, fraction_x);
interpolate_color(right, bottom, &X2, fraction_x);
interpolate_color(X1, X2, &Y, fraction_y);
lua_createtable(L, 6, 0);
lua_pushnumber(L, x + i);
lua_rawseti(L, -2, 1);
lua_pushnumber(L, y + j);
lua_rawseti(L, -2, 2);
lua_pushnumber(L, Y.r);
lua_rawseti(L, -2, 3);
lua_pushnumber(L, Y.g);
lua_rawseti(L, -2, 4);
lua_pushnumber(L, Y.b);
lua_rawseti(L, -2, 5);
lua_pushnumber(L, Y.a);
lua_rawseti(L, -2, 6);
lua_rawseti(L, -2, i + j * w + 1);
lua_getfield(L, LUA_REGISTRYINDEX, "nuklear");
lua_getfield(L, -1, "gradientData");
int row, col;
for (row = 0; row < NK_LOVE_GRADIENT_RESOLUTION; ++row) {
float row_ratio = (float) row / NK_LOVE_GRADIENT_RESOLUTION;
struct nk_color left, right;
interpolate_color(top_left, bottom_left, &left, row_ratio);
interpolate_color(top_right, bottom_right, &right, row_ratio);
for (col = 0; col < NK_LOVE_GRADIENT_RESOLUTION; ++col) {
float col_ratio = (float) col / NK_LOVE_GRADIENT_RESOLUTION;
struct nk_color pixel;
interpolate_color(left, right, &pixel, col_ratio);
lua_getfield(L, -1, "setPixel");
lua_pushvalue(L, -2);
lua_pushnumber(L, col);
lua_pushnumber(L, row);
lua_pushnumber(L, pixel.r);
lua_pushnumber(L, pixel.g);
lua_pushnumber(L, pixel.b);
lua_pushnumber(L, pixel.a);
lua_call(L, 7, 0);
}
}
lua_pop(L, 1);
lua_getfield(L, -1, "gradient");
lua_getfield(L, -1, "refresh");
lua_pushvalue(L, -2);
lua_call(L, 1, 0);
lua_getfield(L, -1, "pop");
lua_call(L, 0, 0);
lua_getglobal(L, "love");
lua_getfield(L, -1, "graphics");
lua_getfield(L, -1, "draw");
lua_replace(L, -5);
lua_pop(L, 2);
lua_pushnumber(L, x);
lua_pushnumber(L, y);
lua_pushnumber(L, 0);
lua_pushnumber(L, (float) w / NK_LOVE_GRADIENT_RESOLUTION);
lua_pushnumber(L, (float) h / NK_LOVE_GRADIENT_RESOLUTION);
lua_call(L, 6, 0);
}
static void nk_love_draw_image(int x, int y, unsigned int w, unsigned int h,
@ -941,25 +985,29 @@ static int nk_love_keyevent(struct nk_context *ctx, const char *key,
return nk_love_is_active(ctx);
}
static int nk_love_clickevent(struct nk_context *ctx, int x, int y,
static int nk_love_clickevent(struct nk_love_context *ctx, int x, int y,
int button, int istouch, int down)
{
nk_love_transform(ctx->Ti, &x, &y);
struct nk_context *nkctx = &ctx->nkctx;
if (button == 1)
nk_input_button(ctx, NK_BUTTON_LEFT, x, y, down);
nk_input_button(nkctx, NK_BUTTON_LEFT, x, y, down);
else if (button == 3)
nk_input_button(ctx, NK_BUTTON_MIDDLE, x, y, down);
nk_input_button(nkctx, NK_BUTTON_MIDDLE, x, y, down);
else if (button == 2)
nk_input_button(ctx, NK_BUTTON_RIGHT, x, y, down);
nk_input_button(nkctx, NK_BUTTON_RIGHT, x, y, down);
else
return 0;
return nk_window_is_any_hovered(ctx);
return nk_window_is_any_hovered(nkctx);
}
static int nk_love_mousemoved_event(struct nk_context *ctx, int x, int y,
static int nk_love_mousemoved_event(struct nk_love_context *ctx, int x, int y,
int dx, int dy, int istouch)
{
nk_input_motion(ctx, x, y);
return nk_window_is_any_hovered(ctx);
nk_love_transform(ctx->Ti, &x, &y);
struct nk_context *nkctx = &ctx->nkctx;
nk_input_motion(nkctx, x, y);
return nk_window_is_any_hovered(nkctx);
}
static int nk_love_textinput_event(struct nk_context *ctx, const char *text)
@ -984,7 +1032,7 @@ static int nk_love_wheelmoved_event(struct nk_context *ctx, int x, int y)
* ===============================================================
*/
static int nk_love_init(lua_State *L)
static int nk_love_new_ui(lua_State *L)
{
nk_love_assert_argc(lua_gettop(L) == 0);
lua_getfield(L, LUA_REGISTRYINDEX, "nuklear");
@ -1022,7 +1070,7 @@ static int nk_love_init(lua_State *L)
return 1;
}
static int nk_love_shutdown(lua_State *luaState)
static int nk_love_destroy(lua_State *luaState)
{
nk_love_assert_argc(lua_gettop(L) == 1);
struct nk_love_context *ctx = nk_love_checkcontext(1);
@ -1062,7 +1110,7 @@ static int nk_love_keyreleased(lua_State *L)
static int nk_love_mousepressed(lua_State *L)
{
nk_love_assert_argc(lua_gettop(L) == 5);
struct nk_context *ctx = &nk_love_checkcontext(1)->nkctx;
struct nk_love_context *ctx = nk_love_checkcontext(1);
int x = luaL_checkint(L, 2);
int y = luaL_checkint(L, 3);
int button = luaL_checkint(L, 4);
@ -1075,7 +1123,7 @@ static int nk_love_mousepressed(lua_State *L)
static int nk_love_mousereleased(lua_State *L)
{
nk_love_assert_argc(lua_gettop(L) == 5);
struct nk_context *ctx = &nk_love_checkcontext(1)->nkctx;
struct nk_love_context *ctx = nk_love_checkcontext(1);
int x = luaL_checkint(L, 2);
int y = luaL_checkint(L, 3);
int button = luaL_checkint(L, 4);
@ -1088,7 +1136,7 @@ static int nk_love_mousereleased(lua_State *L)
static int nk_love_mousemoved(lua_State *L)
{
nk_love_assert_argc(lua_gettop(L) == 6);
struct nk_context *ctx = &nk_love_checkcontext(1)->nkctx;
struct nk_love_context *ctx = nk_love_checkcontext(1);
int x = luaL_checkint(L, 2);
int y = luaL_checkint(L, 3);
int dx = luaL_checkint(L, 4);
@ -1135,6 +1183,21 @@ static int nk_love_draw(lua_State *L)
lua_getfield(L, -1, "origin");
lua_call(L, 0, 0);
nk_love_pushregistry("transform");
size_t transform_count = lua_objlen(L, -1);
size_t i, j;
for (i = 1; i <= transform_count; ++i) {
lua_rawgeti(L, -1, i);
lua_rawgeti(L, -1, 1);
lua_gettable(L, -4);
size_t transform_size = lua_objlen(L, -2);
for (j = 2; j <= transform_size; ++j)
lua_rawgeti(L, -j, j);
lua_call(L, transform_size - 1, 0);
lua_pop(L, 1);
}
lua_pop(L, 1);
const struct nk_command *cmd;
nk_foreach(cmd, &context->nkctx)
{
@ -1167,7 +1230,7 @@ static int nk_love_draw(lua_State *L)
nk_love_draw_circle(c->x, c->y, c->w, c->h, -1, c->color);
} break;
case NK_COMMAND_TRIANGLE: {
const struct nk_command_triangle*t = (const struct nk_command_triangle*)cmd;
const struct nk_command_triangle *t = (const struct nk_command_triangle*)cmd;
nk_love_draw_triangle(t->a.x, t->a.y, t->b.x, t->b.y,
t->c.x, t->c.y, t->line_thickness, t->color);
} break;
@ -1200,7 +1263,7 @@ static int nk_love_draw(lua_State *L)
} break;
case NK_COMMAND_RECT_MULTI_COLOR: {
const struct nk_command_rect_multi_color *r = (const struct nk_command_rect_multi_color *)cmd;
nk_love_draw_rect_multi_color(r->x, r->y, r->w, r->h, r->left, r->top, r->right, r->bottom);
nk_love_draw_rect_multi_color(r->x, r->y, r->w, r->h, r->left, r->top, r->bottom, r->right);
} break;
case NK_COMMAND_IMAGE: {
const struct nk_command_image *i = (const struct nk_command_image *)cmd;
@ -1223,6 +1286,7 @@ static int nk_love_draw(lua_State *L)
lua_call(L, 0, 0);
lua_pop(L, 2);
nk_clear(&context->nkctx);
context = NULL;
return 0;
}
@ -1358,6 +1422,7 @@ static void nk_love_preserve_all(void)
static int nk_love_frame_begin(lua_State *L)
{
nk_love_assert_argc(lua_gettop(L) == 1);
nk_love_assert(context == NULL, "%s: missing ui:frameEnd for previous frame");
context = nk_love_checkcontext(1);
nk_input_end(&context->nkctx);
lua_getglobal(L, "love");
@ -1390,7 +1455,13 @@ static int nk_love_frame_begin(lua_State *L)
lua_pop(L, 1);
context->nkctx.stacks.fonts.elements[i].old_value = &context->fonts[context->font_count++];
}
lua_pop(L, 1);
context->layout_ratio_count = 0;
for (i = 0; i < 9; ++i)
context->T[i] = context->Ti[i] = (i % 3 == i / 3);
context->transform_allowed = 1;
lua_newtable(L);
lua_setfield(L, -2, "transform");
return 0;
}
@ -1403,6 +1474,183 @@ static int nk_love_frame_end(lua_State *L)
return 0;
}
/*
cos -sin 0 | cos sin 0
sin cos 0 | -sin cos 0
0 0 1 | 0 0 1
*/
static int nk_love_rotate(lua_State *L)
{
nk_love_assert_argc(lua_gettop(L) == 2);
nk_love_assert_transform();
float angle = luaL_checknumber(L, 2);
nk_love_pushregistry("transform");
size_t len = lua_objlen(L, -1);
lua_newtable(L);
lua_pushstring(L, "rotate");
lua_rawseti(L, -2, 1);
lua_pushnumber(L, angle);
lua_rawseti(L, -2, 2);
lua_rawseti(L, -2, len + 1);
float *T = context->T, *Ti = context->Ti;
float c = cosf(angle);
float s = sinf(angle);
int i;
float R[9];
R[0] = T[0] * c + T[3] * s;
R[1] = T[1] * c + T[4] * s;
R[2] = T[2] * c + T[5] * s;
R[3] = T[0] * -s + T[3] * c;
R[4] = T[1] * -s + T[4] * c;
R[5] = T[2] * -s + T[5] * c;
R[6] = T[6];
R[7] = T[7];
R[8] = T[8];
for (i = 0; i < 9; ++i)
T[i] = R[i];
R[0] = c * Ti[0] + s * Ti[1];
R[1] = -s * Ti[0] + c * Ti[1];
R[2] = Ti[2];
R[3] = c * Ti[3] + s * Ti[4];
R[4] = -s * Ti[3] + c * Ti[4];
R[5] = Ti[5];
R[6] = c * Ti[6] + s * Ti[7];
R[7] = -s * Ti[6] + c * Ti[7];
R[8] = Ti[8];
for (i = 0; i < 9; ++i)
Ti[i] = R[i];
return 0;
}
/*
sx 0 0 | 1/sx 0 0
0 sy 0 | 0 1/sy 0
0 0 1 | 0 0 1
*/
static int nk_love_scale(lua_State *L)
{
nk_love_assert_argc(lua_gettop(L) >= 2 && lua_gettop(L) <= 3);
nk_love_assert_transform();
float sx = luaL_checknumber(L, 2);
float sy = luaL_optnumber(L, 3, sx);
nk_love_pushregistry("transform");
size_t len = lua_objlen(L, -1);
lua_newtable(L);
lua_pushstring(L, "scale");
lua_rawseti(L, -2, 1);
lua_pushnumber(L, sx);
lua_rawseti(L, -2, 2);
lua_pushnumber(L, sy);
lua_rawseti(L, -2, 3);
lua_rawseti(L, -2, len + 1);
float *T = context->T, *Ti = context->Ti;
T[0] *= sx;
T[1] *= sx;
T[2] *= sx;
T[3] *= sy;
T[4] *= sy;
T[5] *= sy;
Ti[0] /= sx;
Ti[1] /= sy;
Ti[3] /= sx;
Ti[4] /= sy;
Ti[6] /= sx;
Ti[7] /= sy;
return 0;
}
/*
1 kx 0 | 1/(1-kx*ky) kx/(kx*ky-1) 0
ky 1 0 | ky/(kx*ky-1) 1/(1-kx*ky) 0
0 0 1 | 0 0 1
*/
static int nk_love_shear(lua_State *L)
{
nk_love_assert_argc(lua_gettop(L) == 3);
nk_love_assert_transform();
float kx = luaL_checknumber(L, 2);
float ky = luaL_checknumber(L, 3);
nk_love_pushregistry("transform");
size_t len = lua_objlen(L, -1);
lua_newtable(L);
lua_pushstring(L, "shear");
lua_rawseti(L, -2, 1);
lua_pushnumber(L, kx);
lua_rawseti(L, -2, 2);
lua_pushnumber(L, ky);
lua_rawseti(L, -2, 3);
lua_rawseti(L, -2, len + 1);
float *T = context->T, *Ti = context->Ti;
float R[9];
R[0] = T[0] + T[3] * ky;
R[1] = T[1] + T[4] * ky;
R[2] = T[2] + T[5] * ky;
R[3] = T[0] * kx + T[3];
R[4] = T[1] * kx + T[4];
R[5] = T[2] * kx + T[5];
R[6] = T[6];
R[7] = T[7];
R[8] = T[8];
int i;
for (i = 0; i < 9; ++i)
T[i] = R[i];
float a = 1.0f / (1 - kx * ky);
float b = 1.0f / (kx * ky - 1);
R[0] = a * Ti[0] + kx * b * Ti[1];
R[1] = ky * b * Ti[0] + a * Ti[1];
R[2] = Ti[2];
R[3] = a * Ti[3] + kx * b * Ti[4];
R[4] = ky * b * Ti[3] + a * Ti[4];
R[5] = Ti[5];
R[6] = a * Ti[6] + kx * b * Ti[7];
R[7] = ky * b * Ti[6] + a * Ti[7];
R[8] = Ti[8];
for (i = 0; i < 9; ++i)
Ti[i] = R[i];
return 0;
}
/*
1 0 dx | 1 0 -dx
0 1 dy | 0 1 -dy
0 0 1 | 0 0 1
*/
static int nk_love_translate(lua_State *L)
{
nk_love_assert_argc(lua_gettop(L) == 3);
nk_love_assert_transform();
float dx = luaL_checknumber(L, 2);
float dy = luaL_checknumber(L, 3);
nk_love_pushregistry("transform");
size_t len = lua_objlen(L, -1);
lua_newtable(L);
lua_pushstring(L, "translate");
lua_rawseti(L, -2, 1);
lua_pushnumber(L, dx);
lua_rawseti(L, -2, 2);
lua_pushnumber(L, dy);
lua_rawseti(L, -2, 3);
lua_rawseti(L, -2, len + 1);
float *T = context->T, *Ti = context->Ti;
float R[9];
T[6] += T[0] * dx + T[3] * dy;
T[7] += T[1] * dx + T[4] * dy;
T[8] += T[2] * dx + T[5] * dy;
R[0] = Ti[0] - dx * Ti[2];
R[1] = Ti[1] - dy * Ti[2];
R[2] = Ti[2];
R[3] = Ti[3] - dx * Ti[5];
R[4] = Ti[4] - dy * Ti[5];
R[5] = Ti[5];
R[6] = Ti[6] - dx * Ti[8];
R[7] = Ti[7] - dy * Ti[8];
R[8] = Ti[8];
int i;
for (i = 0; i < 9; ++i)
Ti[i] = R[i];
return 0;
}
static int nk_love_window_begin(lua_State *L)
{
nk_love_assert_argc(lua_gettop(L) >= 1);
@ -1877,21 +2125,6 @@ static int nk_love_tree_pop(lua_State *L)
return 0;
}
static void nk_love_color(int r, int g, int b, int a, char *color_string)
{
r = NK_CLAMP(0, r, 255);
g = NK_CLAMP(0, g, 255);
b = NK_CLAMP(0, b, 255);
a = NK_CLAMP(0, a, 255);
const char *format_string;
if (a < 255) {
format_string = "#%02x%02x%02x%02x";
} else {
format_string = "#%02x%02x%02x";
}
sprintf(color_string, format_string, r, g, b, a);
}
static int nk_love_color_rgba(lua_State *L)
{
int argc = lua_gettop(L);
@ -3606,6 +3839,23 @@ LUALIB_API int luaopen_nuklear(lua_State *luaState)
lua_newtable(L);
lua_pushvalue(L, -1);
lua_setfield(L, LUA_REGISTRYINDEX, "nuklear");
lua_getglobal(L, "love");
nk_love_assert(lua_istable(L, -1), "LOVE-Nuklear requires LOVE environment");
lua_getfield(L, -1, "image");
lua_getfield(L, -1, "newImageData");
lua_pushnumber(L, NK_LOVE_GRADIENT_RESOLUTION);
lua_pushnumber(L, NK_LOVE_GRADIENT_RESOLUTION);
lua_call(L, 2, 1);
lua_getfield(L, -3, "graphics");
lua_getfield(L, -1, "newImage");
lua_pushvalue(L, -3);
lua_call(L, 1, 1);
lua_setfield(L, -6, "gradient");
lua_pop(L, 1);
lua_setfield(L, -4, "gradientData");
lua_pop(L, 2);
lua_newtable(L);
lua_pushvalue(L, -1);
lua_setfield(L, -3, "methods");
@ -3623,6 +3873,11 @@ LUALIB_API int luaopen_nuklear(lua_State *luaState)
NK_LOVE_REGISTER("frameBegin", nk_love_frame_begin);
NK_LOVE_REGISTER("frameEnd", nk_love_frame_end);
NK_LOVE_REGISTER("rotate", nk_love_rotate);
NK_LOVE_REGISTER("scale", nk_love_scale);
NK_LOVE_REGISTER("shear", nk_love_shear);
NK_LOVE_REGISTER("translate", nk_love_translate);
NK_LOVE_REGISTER("windowBegin", nk_love_window_begin);
NK_LOVE_REGISTER("windowEnd", nk_love_window_end);
NK_LOVE_REGISTER("windowGetBounds", nk_love_window_get_bounds);
@ -3741,12 +3996,12 @@ LUALIB_API int luaopen_nuklear(lua_State *luaState)
lua_newtable(L);
lua_pushvalue(L, -1);
lua_setfield(L, -4, "metatable");
NK_LOVE_REGISTER("__gc", nk_love_shutdown);
NK_LOVE_REGISTER("__gc", nk_love_destroy);
lua_pushvalue(L, -2);
lua_setfield(L, -2, "__index");
lua_newtable(L);
NK_LOVE_REGISTER("init", nk_love_init);
NK_LOVE_REGISTER("newUI", nk_love_new_ui);
NK_LOVE_REGISTER("colorRGBA", nk_love_color_rgba);
NK_LOVE_REGISTER("colorHSVA", nk_love_color_hsva);
NK_LOVE_REGISTER("colorParseRGBA", nk_love_color_parse_rgba);