aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorGravatar Chris Xiong <chirs241097@gmail.com> 2016-01-25 23:01:59 +0800
committerGravatar Chris Xiong <chirs241097@gmail.com> 2016-01-25 23:01:59 +0800
commit841465ea45e56bf2f294b5cb934e5ff955c72401 (patch)
tree6ea71790c1b1c8458cdf6b2b751788ecd32943bf
parent1d64816653b5d1835dd60762c2bc64f000d88fa5 (diff)
downloadSMELT-841465ea45e56bf2f294b5cb934e5ff955c72401.tar.xz
Texture options.
Add smHandler* version of event handlers.
-rw-r--r--doc/SMELTdoc34
-rw-r--r--include/smelt.hpp17
-rw-r--r--smelt/sdl/gfx_sdl.cpp52
-rw-r--r--smelt/sdl/smelt_internal.hpp8
-rw-r--r--smelt/sdl/sys_sdl.cpp19
5 files changed, 116 insertions, 14 deletions
diff --git a/doc/SMELTdoc b/doc/SMELTdoc
index 4bbc7a3..f106e63 100644
--- a/doc/SMELTdoc
+++ b/doc/SMELTdoc
@@ -36,6 +36,8 @@ SMINP_*: Key modifiers. They can be or'd together.
SMKST_*: Key states.
SMK_*: Keys.
+TPOT_*, TFLT_*: Texture Options.
+
Sturctures=====================================================================
smInpEvent: Input event structure.
-chcode: Char code.
@@ -97,20 +99,34 @@ proper occasion.
This function requires the UpdateFunc set and the initialization of the SMELT
interface.
-void smUpdateFunc(smHook func) [core]
+void smUpdateFunc(smHook func) [core]
+void smUpdateFunc(smHandler* h) [core]
Sets the update function.
The update function returns bool and takes no parameters.
If the update function returns true, the main loop will break, otherwise
the main loop runs perpetually.
The update function is called every frame.
+If both the handler and the hook are set, the hook will be executed first.
-void smUnFocFunc(smHook func) [core]
-Sets the unfocus function.
+void smUnFocFunc(smHook func) [core]
+void smUnFocFunc(smHandler* h) [core]
+Sets the unfocus event handler.
The unfocus function is called when the application window loses focus.
+If both the handler and the hook are set, the hook will be executed first.
-void smFocFunc(smHook func) [core]
-Sets the focus function.
+void smFocFunc(smHook func) [core]
+void smFocFunc(smHandler* h) [core]
+Sets the focus event handler.
The focus functions is called when the application window gains focus.
+If both the handler and the hook are set, the hook will be executed first.
+
+void smQuitFunc(smHook func) [core]
+void smQuitFunc(smHandler* h) [core]
+Sets the quit event handler.
+Called when the user send a quit request to the application (e.g. by pressing
+the close button).
+If the handler/hook returns true, the quit request will be rejected and the
+application will keep running.
void smWinTitle(const char* title) [core]
Sets the application window title.
@@ -378,6 +394,14 @@ mipmapping doesn't work in OpenGL versions.
void smTextureFree(SMTEX tex) [core/GFX]
Release the texture from memory.
+void smTextureOpt(int potopt=TPOT_NONPOT,int filter=TFLT_LINEAR) [core/GFX]
+Sets texture options.
+TPOT_POT: textures dimensions are resized to the minimal power of two value.
+TPOT_NONPOT: use textures whose dimensions are not power of two directly.
+Please note that only power-of-two textures supports texture repeating.
+TFLT_LINEAR: use the linear filter for texture scaling.
+TFLT_NEAREST: use the nearest filter for texture scaling.
+
int smTextureGetWidth(SMTEX tex,bool original=false) [core/GFX]
Gets the width of the texture.
If original==false and the texture is resized, the function will return the
diff --git a/include/smelt.hpp b/include/smelt.hpp
index 4651814..bba4ff5 100644
--- a/include/smelt.hpp
+++ b/include/smelt.hpp
@@ -71,6 +71,7 @@ typedef size_t SMCHN;//Audio channel Handle
//callback function pointer
typedef bool (*smHook)();
+//Wrapper abstract class for a function that can hook into SMELT
class smHandler
{
public: virtual bool handlerFunc()=0;
@@ -87,6 +88,13 @@ class smHandler
#define PRIM_TRIANGLES 3
#define PRIM_QUADS 4
+//Texture Options
+#define TPOT_NONPOT 0
+#define TPOT_POT 1
+
+#define TFLT_LINEAR 0
+#define TFLT_NEAREST 1
+
//Texture Region structure
struct smTexRect
{
@@ -171,6 +179,11 @@ public:
* It returns true when you want to terminate the main loop.
*/
virtual void smUpdateFunc(smHook func)=0;
+ /**
+ * Sets the update function via a smHandler class.
+ * Update function is called every frame.
+ * It returns true when you want to terminate the main loop.
+ */
virtual void smUpdateFunc(smHandler* h)=0;
/**
* Sets the focus lost function.
@@ -179,6 +192,7 @@ public:
* The return value of the focus lost function has no effect.
*/
virtual void smUnFocFunc(smHook func)=0;
+ virtual void smUnFocFunc(smHandler* h)=0;
/**
* Sets the focus gain function.
* Focus gain function is called when the application window gains
@@ -186,6 +200,7 @@ public:
* The return value of the focus gain function has no effect.
*/
virtual void smFocFunc(smHook func)=0;
+ virtual void smFocFunc(smHandler* h)=0;
/**
* Sets the quit function.
* Quit function is called when the user attempts to close the
@@ -194,6 +209,7 @@ public:
* Otherwise the main loop will break.
*/
virtual void smQuitFunc(smHook func)=0;
+ virtual void smQuitFunc(smHandler* h)=0;
/**
* Sets the window title of the application window.
* The default window title is "untitled".
@@ -352,6 +368,7 @@ public:
virtual SMTEX smTextureLoad(const char *path)=0;
virtual SMTEX smTextureLoadFromMemory(const char *ptr,DWORD size)=0;
virtual void smTextureFree(SMTEX tex)=0;
+ virtual void smTextureOpt(int potopt=TPOT_NONPOT,int filter=TFLT_LINEAR)=0;
virtual int smTextureGetWidth(SMTEX tex,bool original=false)=0;
virtual int smTextureGetHeight(SMTEX tex,bool original=false)=0;
virtual DWORD* smTextureLock(SMTEX tex,int l,int t,int w,int h,bool ro=true)=0;
diff --git a/smelt/sdl/gfx_sdl.cpp b/smelt/sdl/gfx_sdl.cpp
index 47b6999..4e80a38 100644
--- a/smelt/sdl/gfx_sdl.cpp
+++ b/smelt/sdl/gfx_sdl.cpp
@@ -343,6 +343,45 @@ void SMELT_IMPL::smTextureFree(SMTEX tex)
delete ptex;
}
}
+void SMELT_IMPL::smTextureOpt(int potopt,int filter)
+{
+ batchOGL();
+ if(potopt==TPOT_NONPOT)
+ {
+ if(pOpenGLDevice->have_GL_ARB_texture_rectangle)
+ pOpenGLDevice->TextureTarget=GL_TEXTURE_RECTANGLE_ARB;
+ else if(pOpenGLDevice->have_GL_ARB_texture_non_power_of_two)
+ pOpenGLDevice->TextureTarget=GL_TEXTURE_2D;
+ else pOpenGLDevice->TextureTarget=GL_TEXTURE_2D;
+ pOpenGLDevice->glDisable(GL_TEXTURE_2D);
+ if(pOpenGLDevice->have_GL_ARB_texture_rectangle)pOpenGLDevice->glDisable(GL_TEXTURE_RECTANGLE_ARB);
+ pOpenGLDevice->glEnable(pOpenGLDevice->TextureTarget);
+ pOpenGLDevice->glTexParameteri(pOpenGLDevice->TextureTarget,GL_TEXTURE_WRAP_S,GL_CLAMP_TO_EDGE);
+ pOpenGLDevice->glTexParameteri(pOpenGLDevice->TextureTarget,GL_TEXTURE_WRAP_T,GL_CLAMP_TO_EDGE);
+ pOpenGLDevice->glTexParameteri(pOpenGLDevice->TextureTarget,GL_TEXTURE_WRAP_R,GL_CLAMP_TO_EDGE);
+ }
+ if(potopt==TPOT_POT)
+ {
+ pOpenGLDevice->TextureTarget=GL_TEXTURE_2D;
+ pOpenGLDevice->glDisable(GL_TEXTURE_2D);
+ if(pOpenGLDevice->have_GL_ARB_texture_rectangle)pOpenGLDevice->glDisable(GL_TEXTURE_RECTANGLE_ARB);
+ pOpenGLDevice->glEnable(pOpenGLDevice->TextureTarget);
+ pOpenGLDevice->glTexParameteri(pOpenGLDevice->TextureTarget,GL_TEXTURE_WRAP_S,GL_REPEAT);
+ pOpenGLDevice->glTexParameteri(pOpenGLDevice->TextureTarget,GL_TEXTURE_WRAP_T,GL_REPEAT);
+ pOpenGLDevice->glTexParameteri(pOpenGLDevice->TextureTarget,GL_TEXTURE_WRAP_R,GL_REPEAT);
+ }
+ filtermode=filter;
+ if(filter==TFLT_NEAREST)
+ {
+ pOpenGLDevice->glTexParameteri(pOpenGLDevice->TextureTarget,GL_TEXTURE_MIN_FILTER,GL_NEAREST);
+ pOpenGLDevice->glTexParameteri(pOpenGLDevice->TextureTarget,GL_TEXTURE_MAG_FILTER,GL_NEAREST);
+ }
+ if(filter==TFLT_LINEAR)
+ {
+ pOpenGLDevice->glTexParameteri(pOpenGLDevice->TextureTarget,GL_TEXTURE_MIN_FILTER,GL_LINEAR);
+ pOpenGLDevice->glTexParameteri(pOpenGLDevice->TextureTarget,GL_TEXTURE_MAG_FILTER,GL_LINEAR);
+ }
+}
int SMELT_IMPL::smTextureGetWidth(SMTEX tex,bool original)
{
if(original)
@@ -594,8 +633,16 @@ void SMELT_IMPL::batchOGL(bool endScene)
float twm=1.,thm=1.;
if(primTex)
{
- pOpenGLDevice->glTexParameteri(pOpenGLDevice->TextureTarget,GL_TEXTURE_MIN_FILTER,GL_LINEAR);
- pOpenGLDevice->glTexParameteri(pOpenGLDevice->TextureTarget,GL_TEXTURE_MAG_FILTER,GL_LINEAR);
+ if(filtermode==TFLT_NEAREST)
+ {
+ pOpenGLDevice->glTexParameteri(pOpenGLDevice->TextureTarget,GL_TEXTURE_MIN_FILTER,GL_NEAREST);
+ pOpenGLDevice->glTexParameteri(pOpenGLDevice->TextureTarget,GL_TEXTURE_MAG_FILTER,GL_NEAREST);
+ }
+ if(filtermode==TFLT_LINEAR)
+ {
+ pOpenGLDevice->glTexParameteri(pOpenGLDevice->TextureTarget,GL_TEXTURE_MIN_FILTER,GL_LINEAR);
+ pOpenGLDevice->glTexParameteri(pOpenGLDevice->TextureTarget,GL_TEXTURE_MAG_FILTER,GL_LINEAR);
+ }
glTexture *ptex=(glTexture*)primTex;
if(pOpenGLDevice->TextureTarget==GL_TEXTURE_RECTANGLE_ARB)
{twm=ptex->rw;thm=ptex->rh;}
@@ -881,6 +928,7 @@ bool SMELT_IMPL::confOGL()
pOpenGLDevice->glEnable(GL_ALPHA_TEST);
pOpenGLDevice->glAlphaFunc(GL_GEQUAL,1.0f/255.0f);
pOpenGLDevice->glTexEnvi(GL_TEXTURE_ENV,GL_TEXTURE_ENV_MODE,GL_MODULATE);
+ filtermode=TFLT_LINEAR;
pOpenGLDevice->glTexParameteri(pOpenGLDevice->TextureTarget,GL_TEXTURE_MIN_FILTER,GL_LINEAR);
pOpenGLDevice->glTexParameteri(pOpenGLDevice->TextureTarget,GL_TEXTURE_MAG_FILTER,GL_LINEAR);
//GL_REPEAT doesn't work with non-pot textures...
diff --git a/smelt/sdl/smelt_internal.hpp b/smelt/sdl/smelt_internal.hpp
index c3cfa89..6d9e04f 100644
--- a/smelt/sdl/smelt_internal.hpp
+++ b/smelt/sdl/smelt_internal.hpp
@@ -91,8 +91,11 @@ public:
virtual void smUpdateFunc(smHook func);
virtual void smUpdateFunc(smHandler* h);
virtual void smUnFocFunc(smHook func);
+ virtual void smUnFocFunc(smHandler* h);
virtual void smFocFunc(smHook func);
+ virtual void smFocFunc(smHandler* h);
virtual void smQuitFunc(smHook func);
+ virtual void smQuitFunc(smHandler* h);
virtual void smWinTitle(const char* title);
virtual bool smIsActive();
virtual void smNoSuspend(bool para);
@@ -159,6 +162,7 @@ public:
virtual SMTEX smTextureLoad(const char *path);
virtual SMTEX smTextureLoadFromMemory(const char *ptr,DWORD size);
virtual void smTextureFree(SMTEX tex);
+ virtual void smTextureOpt(int potopt=TPOT_NONPOT,int filter=TFLT_LINEAR);
virtual int smTextureGetWidth(SMTEX tex,bool original=false);
virtual int smTextureGetHeight(SMTEX tex,bool original=false);
virtual DWORD* smTextureLock(SMTEX tex,int l,int t,int w,int h,bool ro=true);
@@ -175,7 +179,7 @@ public:
bool (*pUnFocFunc)();
bool (*pFocFunc)();
bool (*pQuitFunc)();
- smHandler *updateHandler;
+ smHandler *updateHandler,*unFocHandler,*focHandler,*quitHandler;
const char *Icon;
char winTitle[256];
int scrw,scrh;
@@ -195,7 +199,7 @@ public:
TRenderTargetList *curTarget;
TTextureList *textures;
bool tdmode;
- int primcnt,primType,primBlend;
+ int primcnt,primType,primBlend,filtermode;
SMTEX primTex;
bool zbufenabled;
bool checkGLExtension(const char *extlist,const char *ext);
diff --git a/smelt/sdl/sys_sdl.cpp b/smelt/sdl/sys_sdl.cpp
index 675d88f..427b1bf 100644
--- a/smelt/sdl/sys_sdl.cpp
+++ b/smelt/sdl/sys_sdl.cpp
@@ -182,8 +182,11 @@ void SMELT_IMPL::smMainLoop()
void SMELT_IMPL::smUpdateFunc(smHook func){pUpdateFunc=func;}
void SMELT_IMPL::smUpdateFunc(smHandler* h){updateHandler=h;}
void SMELT_IMPL::smUnFocFunc(smHook func){pUnFocFunc=func;}
+void SMELT_IMPL::smUnFocFunc(smHandler* h){unFocHandler=h;}
void SMELT_IMPL::smFocFunc(smHook func){pFocFunc=func;}
+void SMELT_IMPL::smFocFunc(smHandler* h){focHandler=h;}
void SMELT_IMPL::smQuitFunc(smHook func){pQuitFunc=func;}
+void SMELT_IMPL::smQuitFunc(smHandler* h){quitHandler=h;}
void SMELT_IMPL::smWinTitle(const char *title){strcpy(winTitle,title);}
bool SMELT_IMPL::smIsActive(){return Active;}
void SMELT_IMPL::smNoSuspend(bool para){noSuspend=para;}
@@ -250,7 +253,8 @@ float SMELT_IMPL::smGetTime(){return timeS;}
SMELT_IMPL::SMELT_IMPL()
{
hwnd=NULL;Active=false;memset(curError,0,sizeof(curError));
- pUpdateFunc=pUnFocFunc=pFocFunc=pQuitFunc=NULL;updateHandler=NULL;
+ pUpdateFunc=pUnFocFunc=pFocFunc=pQuitFunc=NULL;
+ updateHandler=unFocHandler=focHandler=quitHandler=NULL;
Icon=NULL;strcpy(winTitle,"untitled");scrw=dispw=800;scrh=disph=600;
windowed=vsync=false;memset(logFile,0,sizeof(logFile));
limfps=0;hideMouse=true;noSuspend=false;
@@ -263,8 +267,8 @@ SMELT_IMPL::SMELT_IMPL()
void SMELT_IMPL::focusChange(bool actif)
{
Active=actif;
- if(actif)pFocFunc?pFocFunc():0;
- else pUnFocFunc?pUnFocFunc():0;
+ if(actif){pFocFunc?pFocFunc():0;focHandler?focHandler->handlerFunc():0;}
+ else {pUnFocFunc?pUnFocFunc():0;unFocHandler?unFocHandler->handlerFunc():0;};
}
bool SMELT_IMPL::procSDLEvent(const SDL_Event &e)
{
@@ -291,8 +295,13 @@ bool SMELT_IMPL::procSDLEvent(const SDL_Event &e)
}
break;
case SDL_QUIT:
- if(pSM->pQuitFunc&&!pSM->pQuitFunc())break;
- return false;
+ {
+ bool accepted=true;
+ if(pSM->pQuitFunc&&pSM->pQuitFunc())accepted=false;
+ if(pSM->quitHandler&&quitHandler->handlerFunc())accepted=false;
+ if(accepted)return false;
+ }
+ break;
case SDL_KEYDOWN:
keymods=(SDL_Keymod)e.key.keysym.mod;
if((keymods&KMOD_ALT)&&((e.key.keysym.sym==SDLK_RETURN)||(e.key.keysym.sym==SDLK_KP_ENTER)))