2 Copyright (c)2006-2008 - Brett Lajzer
4 See LICENSE for license information.
12 #include <SDL/SDL_image.h>
17 //loads an SDL_Surface into a texture and returns the handle
18 GLuint
surfaceToTexture(lua_State
*L
, SDL_Surface
*s
){
19 GLenum texture_format
;
22 if (s
->format
->BytesPerPixel
== 4){
23 if (s
->format
->Rmask
== 0x000000ff)
24 texture_format
= GL_RGBA
;
26 texture_format
= GL_BGRA
;
27 } else if (s
->format
->BytesPerPixel
== 3){
28 if (s
->format
->Rmask
== 0x000000ff)
29 texture_format
= GL_RGB
;
31 texture_format
= GL_BGR
;
33 return luaL_error(L
, "ERROR: Can't create texture from image.");
36 glGenTextures(1, &tex
);
37 glBindTexture(GL_TEXTURE_RECTANGLE_ARB
, tex
);
38 glTexParameteri(GL_TEXTURE_RECTANGLE_ARB
, GL_TEXTURE_MIN_FILTER
, GL_LINEAR
);
39 glTexParameteri(GL_TEXTURE_RECTANGLE_ARB
, GL_TEXTURE_MAG_FILTER
, GL_LINEAR
);
40 glTexImage2D(GL_TEXTURE_RECTANGLE_ARB
, 0, s
->format
->BytesPerPixel
, s
->w
, s
->h
, 0, texture_format
, GL_UNSIGNED_BYTE
, s
->pixels
);
46 //function for loading a surface from many different formats
47 int l_getimage(lua_State
*L
){
48 std::string
filename(luaL_checkstring(L
,1));
49 std::map
<std::string
, GLSurface
*>::iterator im
= image_store
.find(filename
);
51 //search for the image in the store, if not found, load it
52 if(im
== image_store
.end()){
53 SDL_Surface
*temp
= IMG_Load(filename
.c_str());
56 return luaL_error(L
, "ERROR: Can't find image file: \"%s\".", filename
.c_str());
59 GLuint texture
= surfaceToTexture(L
, temp
);
61 GLSurface
*surf
= new GLSurface(texture
, temp
->w
, temp
->h
);
62 image_store
[filename
] = surf
;
63 lua_pushlightuserdata(L
, surf
);
64 lua_pushinteger(L
, (lua_Integer
)temp
->w
);
65 lua_pushinteger(L
, (lua_Integer
)temp
->h
);
67 SDL_FreeSurface(temp
);
69 lua_pushlightuserdata(L
, im
->second
);
70 lua_pushinteger(L
, (lua_Integer
)im
->second
->w
);
71 lua_pushinteger(L
, (lua_Integer
)im
->second
->h
);
76 //forces an image to be unloaded from memory
77 int l_releaseimage(lua_State
*L
){
78 std::string
filename(luaL_checkstring(L
,1));
79 std::map
<std::string
, GLSurface
*>::iterator im
= image_store
.find(filename
);
81 if(im
!= image_store
.end()){
82 glDeleteTextures(1, &(im
->second
->texture
));
84 image_store
.erase(im
);
91 //function for updating the display surface
92 int l_flip(lua_State
*L
){
98 //function for simple displaying of images (non-animated)
99 int l_display(lua_State
*L
){
100 GLSurface
*tex
= (GLSurface
*)lua_touserdata(L
,1);
102 float x
= (float)lua_tonumber(L
,2);
103 float y
= (float)lua_tonumber(L
,3);
104 double rot
= lua_tonumber(L
,4);
105 double scale_x
= lua_tonumber(L
,5);
106 double scale_y
= lua_tonumber(L
,6);
109 return luaL_error(L
, "ERROR: Can't draw. Image is null.");
112 float w_half
= tex
->w
/2.0;
113 float h_half
= tex
->h
/2.0;
116 glTranslatef(x
+ w_half
, y
+ h_half
, 0.0f
);
117 glScalef(scale_x
, scale_y
, 1.0f
);
118 glRotatef(rot
, 0.0f
, 0.0f
, -1.0f
);
120 glBindTexture(GL_TEXTURE_RECTANGLE_ARB
, tex
->texture
);
123 // Top-left vertex (corner)
125 glVertex2f(-w_half
, -h_half
);
127 // Bottom-left vertex (corner)
128 glTexCoord2i(0, tex
->h
);
129 glVertex2f(-w_half
, h_half
);
131 // Bottom-right vertex (corner)
132 glTexCoord2i(tex
->w
, tex
->h
);
133 glVertex2f(w_half
, h_half
);
135 // Top-right vertex (corner)
136 glTexCoord2i(tex
->w
, 0);
137 glVertex2f(w_half
, -h_half
);
146 //function for displaying a frame of an animation
147 //frames are laid out horizontally
149 int l_displayframe(lua_State
*L
){
150 GLSurface
*tex
= (GLSurface
*)lua_touserdata(L
,1);
151 float x
= (float)lua_tonumber(L
,2);
152 float y
= (float)lua_tonumber(L
,3);
153 int numframes
= lua_tointeger(L
,4);
154 int frame
= lua_tointeger(L
,5);
155 double rot
= lua_tonumber(L
,6);
156 double scale_x
= lua_tonumber(L
,7);
157 double scale_y
= lua_tonumber(L
,8);
160 return luaL_error(L
, "ERROR: Can't draw. Image is null.");
163 int width
= tex
->w
/numframes
;
164 int frame_offset
= frame
* width
;
166 float w_half
= width
/2.0;
167 float h_half
= tex
->h
/2.0;
170 glTranslatef(x
+ w_half
, y
+ h_half
, 0.0f
);
171 glScalef(scale_x
, scale_y
, 1.0f
);
172 glRotatef(rot
, 0.0f
, 0.0f
, -1.0f
);
174 glBindTexture(GL_TEXTURE_RECTANGLE_ARB
, tex
->texture
);
177 // Top-left vertex (corner)
178 glTexCoord2i(frame_offset
, 0);
179 glVertex2f(-w_half
, -h_half
);
181 // Bottom-left vertex (corner)
182 glTexCoord2i(frame_offset
, tex
->h
);
183 glVertex2f(-w_half
, h_half
);
185 // Bottom-right vertex (corner)
186 glTexCoord2i(frame_offset
+ width
, tex
->h
);
187 glVertex2f(w_half
, h_half
);
189 // Top-right vertex (corner)
190 glTexCoord2i(frame_offset
+ width
, 0);
191 glVertex2f(w_half
, -h_half
);
201 int l_show_cursor(lua_State
*L
){
202 bool show
= lua_toboolean(L
, 1);
204 SDL_ShowCursor((show
? SDL_ENABLE
: SDL_DISABLE
));
210 //fills screen with a color
211 int l_fill_screen(lua_State
*L
){
212 glClearColor(lua_tointeger(L
,1)/255.0, lua_tointeger(L
,2)/255.0, lua_tointeger(L
,3)/255.0, 0.0f
);
213 glClear(GL_COLOR_BUFFER_BIT
);
218 //free surface interface
219 int l_delete_image(lua_State
*L
){
220 GLSurface
*tmp
= (GLSurface
*)lua_touserdata(L
,1);
223 return luaL_error(L
, "ERROR: Can't free. Image is null.");
226 glDeleteTextures(1, &(tmp
->texture
));