[prev in list] [next in list] [prev in thread] [next in thread]
List: bzflag-commits
Subject: SF.net SVN: bzflag:[19555] trunk/bzflag/src/lua
From: trepan () users ! sourceforge ! net
Date: 2009-03-31 0:58:23
Message-ID: E1LoSJ5-00071K-E1 () 74yxhf1 ! ch3 ! sourceforge ! com
[Download RAW message or body]
Revision: 19555
http://bzflag.svn.sourceforge.net/bzflag/?rev=19555&view=rev
Author: trepan
Date: 2009-03-31 00:58:23 +0000 (Tue, 31 Mar 2009)
Log Message:
-----------
* implemented the lua gl.TexSubImage() call-out
Modified Paths:
--------------
trunk/bzflag/src/lua/LuaTextures.cxx
trunk/bzflag/src/lua/LuaTextures.h
Modified: trunk/bzflag/src/lua/LuaTextures.cxx
===================================================================
--- trunk/bzflag/src/lua/LuaTextures.cxx 2009-03-30 23:40:20 UTC (rev 19554)
+++ trunk/bzflag/src/lua/LuaTextures.cxx 2009-03-31 00:58:23 UTC (rev 19555)
@@ -7,21 +7,27 @@
// system headers
#include <new>
#include <string.h>
+#include <sstream>
#include <string>
using std::string;
// common headers
#include "bzfgl.h"
#include "bzfio.h"
+#include "BzVFS.h"
#include "OpenGLGState.h"
#include "OpenGLTexture.h"
#include "OpenGLPassState.h"
#include "TextureManager.h"
#include "StateDatabase.h"
+// mediafile headers
+#include "../mediafile/PNGImageFile.h"
+
// local headers
#include "LuaInclude.h"
#include "LuaUtils.h"
+#include "LuaHandle.h"
#include "LuaHashString.h"
#include "LuaGLBuffers.h"
@@ -40,6 +46,164 @@
//============================================================================//
//============================================================================//
//
+// TextureData helper class
+//
+
+class TextureData {
+ public:
+ TextureData()
+ : xsize(0)
+ , ysize(0)
+ , format(GL_RGBA)
+ , type(GL_UNSIGNED_BYTE)
+ , data(NULL)
+ , ownData(false)
+ {}
+
+ ~TextureData() {
+ if (ownData) {
+ delete[] data;
+ }
+ }
+
+ bool Parse(lua_State* L, int index) {
+ const int table = (index > 0) ? index : lua_gettop(L) + index + 1;
+ if (!lua_istable(L, table)) {
+ return false;
+ }
+
+ // image data source
+ if (GetString(L, table, "image")) {
+ size_t inLen;
+ const char* inData = lua_tolstring(L, -1, &inLen);
+ lua_pop(L, 1);
+ const string imageData(inData, inLen);
+
+ return ReadPNGData(imageData);
+ }
+
+ // fileName data source
+ if (GetString(L, table, "file")) {
+ const string fileName = lua_tostring(L, -1);
+ lua_pop(L, 1);
+
+ const LuaHandle* lh = L2H(L);
+ const string modes = lh->GetFSRead();
+
+ string imageData;
+ if (!bzVFS.readFile(fileName, modes, imageData)) {
+ return false;
+ }
+
+ return ReadPNGData(imageData);
+ }
+
+ // fallback to raw binary data
+ if (!GetString(L, table, "data")) {
+ return false;
+ }
+ size_t len;
+ data = (char*)(lua_tolstring(L, -1, &len));
+ lua_pop(L, 1);
+
+ if (GetNumber(L, table, "xsize")) {
+ xsize = (GLint)lua_toint(L, -1); lua_pop(L, 1);
+ }
+ if (GetNumber(L, table, "ysize")) {
+ ysize = (GLint)lua_toint(L, -1); lua_pop(L, 1);
+ }
+ if (GetNumber(L, table, "format")) {
+ format = (GLenum)lua_toint(L, -1); lua_pop(L, 1);
+ }
+ if (GetNumber(L, table, "type")) {
+ type = (GLenum)lua_toint(L, -1); lua_pop(L, 1);
+ }
+
+ // check the dimensions
+ if ((xsize <= 0) || (ysize <= 0)) {
+ return false;
+ }
+
+ const int pixelSize = LuaTextureMgr::GetPixelSize(format, type);
+ const int bytes = (pixelSize * xsize * ysize);
+ if (len != (size_t)bytes) {
+ return false;
+ }
+
+ return true;
+ }
+
+ private:
+ bool GetNumber(lua_State* L, int index, const char* name) {
+ lua_getfield(L, index, name);
+ if (!lua_israwnumber(L, -1)) {
+ lua_pop(L, 1);
+ return false;
+ }
+ return true;
+ }
+
+ bool GetString(lua_State* L, int index, const char* name) {
+ lua_getfield(L, index, name);
+ if (!lua_israwstring(L, -1)) {
+ lua_pop(L, 1);
+ return false;
+ }
+ return true;
+ }
+
+ private:
+ bool ReadPNGData(const string& pngData) {
+ std::istringstream iss(pngData);
+ PNGImageFile image(&iss);
+ if (!image.isOpen()) {
+ return false;
+ }
+
+ type = GL_UNSIGNED_BYTE;
+ xsize = (GLint)image.getWidth();
+ ysize = (GLint)image.getHeight();
+
+ // set the data format based on the number of channels
+ const int channels = image.getNumChannels();
+ switch (channels) {
+ case 1: { format = GL_LUMINANCE; break; }
+ case 2: { format = GL_LUMINANCE_ALPHA; break; }
+ case 3: { format = GL_RGB; break; }
+ case 4: { format = GL_RGBA; break; }
+ default: {
+ return false;
+ }
+ }
+
+ const int bufSize = (xsize * ysize * channels);
+ data = new char[bufSize];
+ if (!image.read(data)) {
+ delete[] data;
+ data = NULL;
+ return false;
+ }
+
+ ownData = true;
+
+ return true;
+ }
+
+ public:
+ GLsizei xsize;
+ GLsizei ysize;
+ GLenum format;
+ GLenum type;
+ char* data;
+
+ private:
+ bool ownData;
+};
+
+
+//============================================================================//
+//============================================================================//
+//
// LuaTexture
//
@@ -591,6 +755,7 @@
PUSH_LUA_CFUNC(L, MultiTexGen);
}
+ PUSH_LUA_CFUNC(L, TexSubImage);
PUSH_LUA_CFUNC(L, CopyToTexture);
if (glGenerateMipmapEXT) {
@@ -905,45 +1070,59 @@
array[i] = luaL_checkfloat(L, i + 4);
}
- const GLenum texTarget = texture->GetTarget();
+ if (!OpenGLPassState::PushAttrib(GL_TEXTURE_BIT)) {
+ return 0; // exceeded the attrib stack depth
+ }
- GLuint oldTexID;
- glGetIntegerv(texTarget, (GLint*)&oldTexID);
-
if (!texture->Bind()) {
+ OpenGLPassState::PopAttrib();
return 0;
}
glTexParameterfv(target, pname, array);
- glBindTexture(texTarget, oldTexID);
+ OpenGLPassState::PopAttrib();
return 0;
}
-int LuaTextureMgr::GenerateMipMap(lua_State* L)
+int LuaTextureMgr::TexSubImage(lua_State* L)
{
- //LuaOpenGL::CheckDrawingEnabled(L, __FUNCTION__);
-
const LuaTexture* texture = CheckLuaTexture(L, 1);
if (!texture->IsWritable()) {
return 0;
}
- const GLenum texTarget = texture->GetTarget();
- GLuint oldTexID;
- glGetIntegerv(texTarget, (GLint*)&oldTexID);
+ TextureData texData;
+ if (!texData.Parse(L, 2)) {
+ return 0;
+ }
+ const GLenum target = (GLenum)luaL_optint(L, 3, texture->GetTarget());
+ const GLint level = (GLint) luaL_optint(L, 4, 0);
+ const GLint x = (GLint) luaL_optint(L, 5, 0);
+ const GLint y = (GLint) luaL_optint(L, 6, 0);
+
+ if (!OpenGLPassState::PushAttrib(GL_TEXTURE_BIT)) {
+ return 0; // exceeded the attrib stack depth
+ }
+
if (!texture->Bind()) {
- return 0;
+ OpenGLPassState::PopAttrib();
+ lua_pushboolean(L, false);
+ return 1;
}
- glGenerateMipmapEXT(texTarget);
+ glGetError(); // clear the error
+ glTexSubImage2D(target, level, x, y,
+ texData.xsize, texData.ysize,
+ texData.format, texData.type, texData.data);
+ lua_pushboolean(L, glGetError() == GL_NO_ERROR);
- glBindTexture(texTarget, oldTexID);
+ OpenGLPassState::PopAttrib();
- return 0;
+ return 1;
}
@@ -957,10 +1136,12 @@
}
const GLenum texTarget = texture->GetTarget();
- GLuint oldTexID;
- glGetIntegerv(texTarget, (GLint*)&oldTexID);
+ if (!OpenGLPassState::PushAttrib(GL_TEXTURE_BIT)) {
+ return 0; // exceeded the attrib stack depth
+ }
if (!texture->Bind()) {
+ OpenGLPassState::PopAttrib();
lua_pushboolean(L, false);
return 1;
}
@@ -978,12 +1159,42 @@
glCopyTexSubImage2D(target, level, xoff, yoff, x, y, w, h);
lua_pushboolean(L, glGetError() == GL_NO_ERROR);
- glBindTexture(target, oldTexID);
+ OpenGLPassState::PopAttrib();
return 1;
}
+int LuaTextureMgr::GenerateMipMap(lua_State* L)
+{
+ //LuaOpenGL::CheckDrawingEnabled(L, __FUNCTION__);
+
+ const LuaTexture* texture = CheckLuaTexture(L, 1);
+ if (!texture->IsWritable()) {
+ return 0;
+ }
+
+ const GLenum texTarget = (GLenum)luaL_optint(L, 2, texture->GetTarget());
+
+ if (!OpenGLPassState::PushAttrib(GL_TEXTURE_BIT)) {
+ return 0; // exceeded the attrib stack depth
+ }
+
+ if (!texture->Bind()) {
+ OpenGLPassState::PopAttrib();
+ lua_pushboolean(L, false);
+ return 1;
+ }
+
+ glGenerateMipmapEXT(texTarget);
+
+ OpenGLPassState::PopAttrib();
+
+ lua_pushboolean(L, true);
+ return 1;
+}
+
+
int LuaTextureMgr::ActiveTexture(lua_State* L)
{
LuaOpenGL::CheckDrawingEnabled(L, __FUNCTION__);
Modified: trunk/bzflag/src/lua/LuaTextures.h
===================================================================
--- trunk/bzflag/src/lua/LuaTextures.h 2009-03-30 23:40:20 UTC (rev 19554)
+++ trunk/bzflag/src/lua/LuaTextures.h 2009-03-31 00:58:23 UTC (rev 19555)
@@ -95,10 +95,10 @@
static int MultiTexEnv(lua_State* L);
static int MultiTexGen(lua_State* L);
+ static int TexSubImage(lua_State* L);
+
static int CopyToTexture(lua_State* L);
- static int TexSubImage2D(lua_State* L);
-
static int GenerateMipMap(lua_State* L);
static int TexBuffer(lua_State* L);
This was sent by the SourceForge.net collaborative development platform, the world's \
largest Open Source development site.
------------------------------------------------------------------------------
_______________________________________________
BZFlag-commits mailing list
BZFlag-commits@lists.SourceForge.net
https://lists.SourceForge.net/lists/listinfo/bzflag-commits
irc: #BZFlag @ irc.freenode.net
[prev in list] [next in list] [prev in thread] [next in thread]
Configure |
About |
News |
Add a list |
Sponsored by KoreLogic