Aside from adding the new source files for libjpeg-turbo, added SLERP quaternion interpolation to libvitaboy Renderer.

The renderer is also making use of the new File::ReadFile() interface added to the FileHandler library.
This commit is contained in:
Fatbag 2012-02-22 16:25:23 -06:00
parent 7bf2669441
commit 83ad5d89d1
6 changed files with 815 additions and 865 deletions

View file

@ -1,6 +1,35 @@
cmake_minimum_required(VERSION 2.6)
project(FileHandler)
add_subdirectory(libexpat) add_subdirectory(libexpat)
add_subdirectory(libfar) add_subdirectory(libfar)
add_subdirectory(libpng) add_subdirectory(libpng)
add_subdirectory(utk) add_subdirectory(utk)
add_subdirectory(xa) add_subdirectory(xa)
add_subdirectory(zlib) add_subdirectory(zlib)
set(FILEHANDLER_SERIES 0)
set(FILEHANDLER_MAJOR 0)
set(FILEHANDLER_MINOR 0)
set(FILEHANDLER_SOURCES
File.cpp
)
include_directories(${CMAKE_SOURCE_DIR}/Libraries/FileHandler)
add_library(FileHandler_static STATIC ${FILEHANDLER_SOURCES})
set_target_properties(FileHandler_static PROPERTIES
OUTPUT_NAME "FileHandler${FILEHANDLER_SERIES}"
PREFIX ""
CLEAN_DIRECT_OUTPUT 1)
add_library(FileHandler_shared SHARED ${FILEHANDLER_SOURCES})
set_target_properties(FileHandler_shared PROPERTIES
OUTPUT_NAME "FileHandler${FILEHANDLER_SERIES}"
VERSION ${FILEHANDLER_SERIES}${FILEHANDLER_MAJOR}.${FILEHANDLER_MINOR}.0
SOVERSION ${FILEHANDLER_SERIES}${FILEHANDLER_MAJOR}
PREFIX ""
IMPORT_PREFIX ""
CLEAN_DIRECT_OUTPUT 1)
target_link_libraries(FileHandler_shared kernel32)

View file

@ -0,0 +1,59 @@
/*
libvitaboy - Copyright (c) 2012 Fatbag <X-Fi6@phppoll.org>
Permission to use, copy, modify, and/or distribute this software for any
purpose with or without fee is hereby granted, provided that the above
copyright notice and this permission notice appear in all copies.
THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
*/
#include <stdint.h>
#include <windows.h>
#include "FileHandler.hpp"
namespace File {
int Error = 0;
unsigned FileSize = 0;
uint8_t * ReadFile(const char * Filename){
HANDLE hFile = CreateFile(Filename, GENERIC_READ, FILE_SHARE_READ, NULL, OPEN_EXISTING, FILE_FLAG_SEQUENTIAL_SCAN, NULL);
if(hFile == INVALID_HANDLE_VALUE){
File::Error = (GetLastError() == ERROR_FILE_NOT_FOUND) ? FERR_NOT_FOUND : FERR_OPEN;
return NULL;
}
FileSize = GetFileSize(hFile, NULL);
if(FileSize == 0){
CloseHandle(hFile);
File::Error = FERR_BLANK;
return NULL;
}
uint8_t * InData = (uint8_t*) malloc(FileSize);
if(InData == NULL){
CloseHandle(hFile);
File::Error = FERR_MEMORY;
return NULL;
}
DWORD bytestransferred;
BOOL result = ::ReadFile(hFile, InData, FileSize, &bytestransferred, NULL);
CloseHandle(hFile);
if(!result || bytestransferred != FileSize){
free(InData);
File::Error = FERR_READ;
return NULL;
}
return InData;
}
}

View file

@ -0,0 +1,32 @@
/*
FileHandler - Copyright (c) 2012 Fatbag <X-Fi6@phppoll.org>
Permission to use, copy, modify, and/or distribute this software for any
purpose with or without fee is hereby granted, provided that the above
copyright notice and this permission notice appear in all copies.
THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
*/
enum FErr {
FERR_NOT_FOUND,
FERR_OPEN,
FERR_BLANK,
FERR_MEMORY,
FERR_READ
};
namespace File {
extern int Error;
extern unsigned FileSize;
uint8_t * ReadFile(const char * Filename);
}

View file

@ -15,6 +15,8 @@ if(WIN32)
set(LIBVITABOY_SOURCES ${LIBVITABOY_SOURCES} resource.rc) set(LIBVITABOY_SOURCES ${LIBVITABOY_SOURCES} resource.rc)
endif() endif()
include_directories(${CMAKE_SOURCE_DIR}/Libraries/FileHandler)
add_library(libvitaboy_static STATIC ${LIBVITABOY_SOURCES}) add_library(libvitaboy_static STATIC ${LIBVITABOY_SOURCES})
set_target_properties(libvitaboy_static PROPERTIES set_target_properties(libvitaboy_static PROPERTIES
OUTPUT_NAME "vitaboy" OUTPUT_NAME "vitaboy"
@ -34,4 +36,4 @@ add_executable(vbparse vbparse.cpp)
target_link_libraries(vbparse libvitaboy_static) target_link_libraries(vbparse libvitaboy_static)
add_executable(Renderer Renderer.cpp) add_executable(Renderer Renderer.cpp)
target_link_libraries(Renderer libvitaboy_shared "${CMAKE_SOURCE_DIR}/Libraries/libvitaboy/libSOIL.a" opengl32 glu32 winmm) target_link_libraries(Renderer libvitaboy_shared "${CMAKE_SOURCE_DIR}/Libraries/libvitaboy/libSOIL.a" FileHandler_shared opengl32 glu32 winmm)

View file

@ -33,7 +33,7 @@
* hand.jpg (pick one from ./avatardata/hands/textures/) * hand.jpg (pick one from ./avatardata/hands/textures/)
Animation: Animation:
* animation.anim (pick one from avatardata/animations) * animation.anim (pick one from ./avatardata/animations/)
==== Controls ==== ==== Controls ====
Arrow keys: Rotate the sim Arrow keys: Rotate the sim
@ -44,43 +44,44 @@
F11: Enter/leave fullscreen F11: Enter/leave fullscreen
*/ */
#include <windows.h> // Header File For Windows #include <windows.h>
#include <math.h> #include <math.h>
#include <gl\gl.h> // Header File For The OpenGL32 Library #include <gl\gl.h>
#include <gl\glu.h> // Header File For The GLu32 Library #include <gl\glu.h>
#include <gl\glext.h> #include <gl\glext.h>
#include <FileHandler.hpp>
#include "SOIL.h" #include "SOIL.h"
#include "libvitaboy.hpp" #include "libvitaboy.hpp"
HDC hDC=NULL; // Private GDI Device Context HDC hDC=NULL;
HGLRC hRC=NULL; // Permanent Rendering Context HGLRC hRC=NULL;
HWND hWnd=NULL; // Holds Our Window Handle HWND hWnd=NULL;
HINSTANCE hInstance; // Holds The Instance Of The Application HINSTANCE hInstance;
bool keys[256] = {0}; // Array Used For The Keyboard Routine bool keys[256] = {0};
bool active=true; // Window Active Flag Set To TRUE By Default bool active=true;
bool fullscreen=false; // Fullscreen Flag Set To Fullscreen Mode By Default bool fullscreen=false;
float zoom = -10; float zoom = -10;
struct CharacterPlacement_t { struct CharacterPlacement_t {
Vertex_t Translation; Vertex_t Translation;
Vertex_t Rotation; Vertex_t Rotation;
}; };
CharacterPlacement_t Character = {{0,-3,0}, {0,0,0}}; CharacterPlacement_t Character = {{0,-3,0}, {0,0,0}};
Skeleton_t Skeleton; Skeleton_t Skeleton;
unsigned TextureCount = 3; const unsigned TextureCount = 3;
GLuint texture[3]; GLuint texture[3];
enum { Texture_Body, Texture_Head, Texture_Hand }; enum { Texture_Body, Texture_Head, Texture_Hand };
const char* TexturePaths[] = {"body.jpg", "head.jpg", "hand.jpg"}; const char* const TexturePaths[] = {"body.jpg", "head.jpg", "hand.jpg"};
unsigned MeshCount = 4; const unsigned MeshCount = 4;
Mesh_t Meshes[4]; Mesh_t Meshes[4];
enum { Mesh_Body, Mesh_Head, Mesh_LHand, Mesh_RHand }; enum { Mesh_Body, Mesh_Head, Mesh_LHand, Mesh_RHand };
unsigned Mesh_UseTexture[] = { Texture_Body, Texture_Head, Texture_Hand, Texture_Hand }; const char* const MeshPaths[] = {"body.mesh", "head.mesh", "lhand.mesh", "rhand.mesh" };
const char* MeshActivate[] = {NULL, "HEAD", "L_HAND", "R_HAND"}; const unsigned Mesh_UseTexture[] = { Texture_Body, Texture_Head, Texture_Hand, Texture_Hand };
const char* const MeshActivate[] = {NULL, "HEAD", "L_HAND", "R_HAND"};
Animation_t Animation; Animation_t Animation;
float AnimationTime = 0; float AnimationTime = 0;
@ -91,65 +92,59 @@ bool ShowSkeleton = true;
LARGE_INTEGER ClockFreq, PreviousTime; LARGE_INTEGER ClockFreq, PreviousTime;
float FramePeriod; float FramePeriod;
LRESULT CALLBACK WndProc(HWND, UINT, WPARAM, LPARAM); // Declaration For WndProc LRESULT CALLBACK WndProc(HWND, UINT, WPARAM, LPARAM);
int LoadGLTextures() // Load Bitmaps And Convert To Textures int LoadGLTextures()
{ {
for(int i=0; i<3; i++){ for(int i=0; i<3; i++){
/* load an image file directly as a new OpenGL texture */
texture[i] = SOIL_load_OGL_texture(TexturePaths[i], SOIL_LOAD_AUTO, SOIL_CREATE_NEW_ID, 0); texture[i] = SOIL_load_OGL_texture(TexturePaths[i], SOIL_LOAD_AUTO, SOIL_CREATE_NEW_ID, 0);
if(texture[i] == 0) if(texture[i] == 0)
return false; return false;
// Typical Texture Generation Using Data From The Bitmap
glBindTexture(GL_TEXTURE_2D, texture[i]); glBindTexture(GL_TEXTURE_2D, texture[i]);
glTexParameteri(GL_TEXTURE_2D,GL_TEXTURE_MIN_FILTER,GL_LINEAR); glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR);
glTexParameteri(GL_TEXTURE_2D,GL_TEXTURE_MAG_FILTER,GL_LINEAR); glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_REPEAT); glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_REPEAT);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_REPEAT); glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_REPEAT);
} }
return true; // Return Success return true;
} }
void ReSizeGLScene(GLsizei width, GLsizei height) // Resize And Initialize The GL Window void ResizeScene(GLsizei width, GLsizei height)
{ {
if (height==0) // Prevent A Divide By Zero By if(height==0) height++;
{
height=1; // Making Height Equal One
}
glViewport(0,0,width,height); // Reset The Current Viewport glViewport(0,0,width,height);
glMatrixMode(GL_PROJECTION); // Select The Projection Matrix glMatrixMode(GL_PROJECTION);
glLoadIdentity(); // Reset The Projection Matrix glLoadIdentity();
// Calculate The Aspect Ratio Of The Window // Calculate The Aspect Ratio Of The Window
gluPerspective(45.0f,(GLfloat)width/(GLfloat)height,0.1f,100.0f); gluPerspective(45.0f,(GLfloat)width/(GLfloat)height,0.1f,100.0f);
glMatrixMode(GL_MODELVIEW); // Select The Modelview Matrix glMatrixMode(GL_MODELVIEW);
glLoadIdentity(); // Reset The Modelview Matrix glLoadIdentity();
} }
int InitGL(void) // All Setup For OpenGL Goes Here int InitGL()
{ {
if (!LoadGLTextures()) // Jump To Texture Loading Routine ( NEW ) if(!LoadGLTextures())
{ return false;
return FALSE; // If Texture Didn't Load Return FALSE
}
glShadeModel(GL_SMOOTH); // Enable Smooth Shading glShadeModel(GL_SMOOTH);
glClearColor(0.0f, 0.0f, 0.0f, 0.5f); // Black Background glClearColor(0.0f, 0.0f, 0.0f, 1.0f);
glClearDepth(1.0f); // Depth Buffer Setup glClearDepth(1.0f);
glEnable(GL_DEPTH_TEST); // Enables Depth Testing glEnable(GL_DEPTH_TEST);
glEnable(GL_CULL_FACE); glEnable(GL_CULL_FACE);
glEnable(GL_RESCALE_NORMAL); glEnable(GL_RESCALE_NORMAL);
glDisable(GL_BLEND); glDisable(GL_BLEND);
glDepthFunc(GL_LEQUAL); // The Type Of Depth Testing To Do glDepthFunc(GL_LEQUAL);
glHint(GL_PERSPECTIVE_CORRECTION_HINT, GL_NICEST); // Really Nice Perspective Calculations glHint(GL_PERSPECTIVE_CORRECTION_HINT, GL_NICEST);
return TRUE; // Initialization Went OK return true;
} }
void TransformVertices(Bone_t& Bone){ void TransformVertices(Bone_t& Bone)
{
glTranslatef(Bone.Translation.x, Bone.Translation.y, Bone.Translation.z); glTranslatef(Bone.Translation.x, Bone.Translation.y, Bone.Translation.z);
float Matrix[16]; float Matrix[16];
FindQuaternionMatrix(Matrix, &Bone.Rotation); FindQuaternionMatrix(Matrix, &Bone.Rotation);
@ -172,56 +167,65 @@ void TransformVertices(Bone_t& Bone){
if(BoneIndex < Mesh.BindingCount){ if(BoneIndex < Mesh.BindingCount){
for(unsigned i=0; i<Mesh.BoneBindings[BoneIndex].FixedVertexCount; i++){ for(unsigned i=0; i<Mesh.BoneBindings[BoneIndex].FixedVertexCount; i++){
glTranslatef(Mesh.VertexData[Mesh.BoneBindings[BoneIndex].FirstFixedVertex + i].x, unsigned VertexIndex = Mesh.BoneBindings[BoneIndex].FirstFixedVertex + i;
Mesh.VertexData[Mesh.BoneBindings[BoneIndex].FirstFixedVertex + i].y, Vertex_t& RelativeVertex = Mesh.VertexData[VertexIndex];
Mesh.VertexData[Mesh.BoneBindings[BoneIndex].FirstFixedVertex + i].z); Vertex_t& AbsoluteVertex = Mesh.TransformedVertexData[VertexIndex];
glTranslatef(RelativeVertex.x, RelativeVertex.y, RelativeVertex.z);
glGetFloatv(GL_MODELVIEW_MATRIX, Matrix); glGetFloatv(GL_MODELVIEW_MATRIX, Matrix);
Mesh.TransformedVertexData[Mesh.BoneBindings[BoneIndex].FirstFixedVertex + i].x = Matrix[12]; AbsoluteVertex.x = Matrix[12];
Mesh.TransformedVertexData[Mesh.BoneBindings[BoneIndex].FirstFixedVertex + i].y = Matrix[13]; AbsoluteVertex.y = Matrix[13];
Mesh.TransformedVertexData[Mesh.BoneBindings[BoneIndex].FirstFixedVertex + i].z = Matrix[14]; AbsoluteVertex.z = Matrix[14];
glTranslatef(-Mesh.VertexData[Mesh.BoneBindings[BoneIndex].FirstFixedVertex + i].x, glTranslatef(-RelativeVertex.x, -RelativeVertex.y, -RelativeVertex.z);
-Mesh.VertexData[Mesh.BoneBindings[BoneIndex].FirstFixedVertex + i].y,
-Mesh.VertexData[Mesh.BoneBindings[BoneIndex].FirstFixedVertex + i].z);
} }
for(unsigned i=0; i<Mesh.BoneBindings[BoneIndex].BlendedVertexCount; i++){ for(unsigned i=0; i<Mesh.BoneBindings[BoneIndex].BlendedVertexCount; i++){
glTranslatef(Mesh.VertexData[Mesh.FixedVertexCount + Mesh.BoneBindings[BoneIndex].FirstBlendedVertex + i].x, unsigned VertexIndex = Mesh.FixedVertexCount + Mesh.BoneBindings[BoneIndex].FirstBlendedVertex + i;
Mesh.VertexData[Mesh.FixedVertexCount + Mesh.BoneBindings[BoneIndex].FirstBlendedVertex + i].y, Vertex_t& RelativeVertex = Mesh.VertexData[VertexIndex];
Mesh.VertexData[Mesh.FixedVertexCount + Mesh.BoneBindings[BoneIndex].FirstBlendedVertex + i].z); Vertex_t& AbsoluteVertex = Mesh.TransformedVertexData[VertexIndex];
glTranslatef(RelativeVertex.x, RelativeVertex.y, RelativeVertex.z);
glGetFloatv(GL_MODELVIEW_MATRIX, Matrix); glGetFloatv(GL_MODELVIEW_MATRIX, Matrix);
Mesh.TransformedVertexData[Mesh.FixedVertexCount + Mesh.BoneBindings[BoneIndex].FirstBlendedVertex + i].x = Matrix[12]; AbsoluteVertex.x = Matrix[12];
Mesh.TransformedVertexData[Mesh.FixedVertexCount + Mesh.BoneBindings[BoneIndex].FirstBlendedVertex + i].x = Matrix[13]; AbsoluteVertex.y = Matrix[13];
Mesh.TransformedVertexData[Mesh.FixedVertexCount + Mesh.BoneBindings[BoneIndex].FirstBlendedVertex + i].x = Matrix[14]; AbsoluteVertex.z = Matrix[14];
glTranslatef(-Mesh.VertexData[Mesh.FixedVertexCount + Mesh.BoneBindings[BoneIndex].FirstBlendedVertex + i].x, glTranslatef(-RelativeVertex.x, -RelativeVertex.y, -RelativeVertex.z);
-Mesh.VertexData[Mesh.FixedVertexCount + Mesh.BoneBindings[BoneIndex].FirstBlendedVertex + i].y,
-Mesh.VertexData[Mesh.FixedVertexCount + Mesh.BoneBindings[BoneIndex].FirstBlendedVertex + i].z);
} }
} }
if(Bone.ChildrenCount == 1){
TransformVertices(*Bone.Children[0]);
}else if(Bone.ChildrenCount > 1){
for(unsigned i=0; i<Bone.ChildrenCount; i++){ for(unsigned i=0; i<Bone.ChildrenCount; i++){
glPushMatrix(); glPushMatrix();
TransformVertices(*Bone.Children[i]); TransformVertices(*Bone.Children[i]);
glPopMatrix(); glPopMatrix();
} }
}
} }
void BlendVertices(){ void BlendVertices()
{
for(unsigned i=0; i<MeshCount; i++){ for(unsigned i=0; i<MeshCount; i++){
Mesh_t& Mesh = Meshes[i]; Mesh_t& Mesh = Meshes[i];
for(unsigned i=0; i<Mesh.BlendedVertexCount; i++){ for(unsigned i=0; i<Mesh.BlendedVertexCount; i++){
Mesh.TransformedVertexData[Mesh.FixedVertexCount + i].x = unsigned Weight = Mesh.BlendData[i].Weight;
Mesh.BlendData[i].Weight * Mesh.TransformedVertexData[Mesh.FixedVertexCount + i].x + Vertex_t& BlendedVertex = Mesh.TransformedVertexData[Mesh.FixedVertexCount + i];
(1-Mesh.BlendData[i].Weight) * Mesh.TransformedVertexData[Mesh.BlendData[i].OtherVertex].x; Vertex_t& FixedVertex = Mesh.TransformedVertexData[Mesh.FixedVertexCount + i];
Mesh.TransformedVertexData[Mesh.FixedVertexCount + i].y = BlendedVertex.x =
Mesh.BlendData[i].Weight * Mesh.TransformedVertexData[Mesh.FixedVertexCount + i].y + Weight * BlendedVertex.x +
(1-Mesh.BlendData[i].Weight) * Mesh.TransformedVertexData[Mesh.BlendData[i].OtherVertex].y; (1-Weight) * FixedVertex.x;
Mesh.TransformedVertexData[Mesh.FixedVertexCount + i].z = BlendedVertex.y =
Mesh.BlendData[i].Weight * Mesh.TransformedVertexData[Mesh.FixedVertexCount + i].z + Weight * BlendedVertex.y +
(1-Mesh.BlendData[i].Weight) * Mesh.TransformedVertexData[Mesh.BlendData[i].OtherVertex].z; (1-Weight) * FixedVertex.y;
BlendedVertex.z =
Weight * BlendedVertex.z +
(1-Weight) * FixedVertex.z;
} }
} }
} }
void DrawMeshes(){ void DrawMeshes()
{
glPointSize(2.0); glPointSize(2.0);
glColor3f(1.0, 1.0, 1.0); glColor3f(1.0, 1.0, 1.0);
glPushMatrix(); glPushMatrix();
@ -246,7 +250,8 @@ void DrawMeshes(){
glDisable(GL_TEXTURE_2D); glDisable(GL_TEXTURE_2D);
} }
void AdvanceFrame(Skeleton_t& Skeleton, Animation_t& Animation, float TimeDelta){ void AdvanceFrame(Skeleton_t& Skeleton, Animation_t& Animation, float TimeDelta)
{
float Duration = (float)Animation.Motions[0].FrameCount/30; float Duration = (float)Animation.Motions[0].FrameCount/30;
AnimationTime += TimeDelta; AnimationTime += TimeDelta;
while(AnimationTime >= Duration) AnimationTime -= Duration; while(AnimationTime >= Duration) AnimationTime -= Duration;
@ -299,7 +304,8 @@ void AdvanceFrame(Skeleton_t& Skeleton, Animation_t& Animation, float TimeDelta)
} }
} }
void DrawBonesSkeleton(Bone_t& Bone){ void DrawBonesSkeleton(Bone_t& Bone)
{
glPointSize(5.0); glPointSize(5.0);
glTranslatef(Bone.Translation.x, Bone.Translation.y, Bone.Translation.z); glTranslatef(Bone.Translation.x, Bone.Translation.y, Bone.Translation.z);
float RotationMatrix[16]; float RotationMatrix[16];
@ -314,22 +320,34 @@ void DrawBonesSkeleton(Bone_t& Bone){
glColor3f(0.0, 1.0, 0.0); glColor3f(0.0, 1.0, 0.0);
glBegin(GL_POINTS); glVertex3f(0, 0, 0); glEnd(); glBegin(GL_POINTS); glVertex3f(0, 0, 0); glEnd();
if(Bone.ChildrenCount == 1){
DrawBonesSkeleton(*Bone.Children[0]);
}else if(Bone.ChildrenCount > 1){
for(unsigned i=0; i<Bone.ChildrenCount; i++){ for(unsigned i=0; i<Bone.ChildrenCount; i++){
glPushMatrix(); glPushMatrix();
DrawBonesSkeleton(*Bone.Children[i]); DrawBonesSkeleton(*Bone.Children[i]);
glPopMatrix(); glPopMatrix();
} }
}
} }
int DrawGLScene(void) // Here's Where We Do All The Drawing void DrawSkeleton()
{ {
glPushMatrix();
DrawBonesSkeleton(Skeleton.Bones[0]);
glPopMatrix();
}
int DrawGLScene()
{
//Obtain the current time
LARGE_INTEGER CurrentTime; LARGE_INTEGER CurrentTime;
QueryPerformanceCounter(&CurrentTime); QueryPerformanceCounter(&CurrentTime);
float TimeDelta = (float)(CurrentTime.QuadPart-PreviousTime.QuadPart)/ClockFreq.QuadPart; float TimeDelta = (float)(CurrentTime.QuadPart-PreviousTime.QuadPart)/ClockFreq.QuadPart;
if(TimeDelta < 0) TimeDelta = 0; //Safe-guard in case of system delay if(TimeDelta < 0) TimeDelta = 0; //Safe-guard in case of system delay
PreviousTime = CurrentTime; PreviousTime = CurrentTime;
//Handle user interaction
if(keys['A']) /*{if(zoom <=-1.0f) zoom+=0.05f; }*/ zoom+=3*TimeDelta; if(keys['A']) /*{if(zoom <=-1.0f) zoom+=0.05f; }*/ zoom+=3*TimeDelta;
if(keys['S']) /*{if(zoom >=-10.0f) zoom-=0.05f; }*/ zoom-=3*TimeDelta; if(keys['S']) /*{if(zoom >=-10.0f) zoom-=0.05f; }*/ zoom-=3*TimeDelta;
if(keys[VK_UP]){ if((Character.Rotation.x-=60*TimeDelta) <=-360) Character.Rotation.x+=360; } if(keys[VK_UP]){ if((Character.Rotation.x-=60*TimeDelta) <=-360) Character.Rotation.x+=360; }
@ -344,7 +362,7 @@ int DrawGLScene(void) // Here's Where We Do All The Drawing
if(keys['L']){ Character.Translation.x+=3*TimeDelta; } if(keys['L']){ Character.Translation.x+=3*TimeDelta; }
if(keys['N']){ AdvanceFrame(Skeleton, Animation, TimeDelta); } if(keys['N']){ AdvanceFrame(Skeleton, Animation, TimeDelta); }
glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT); // Clear The Screen And The Depth Buffer glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT); //Clear the screen and the depth buffer
glLoadIdentity(); glLoadIdentity();
glTranslatef(Character.Translation.x, Character.Translation.y, zoom + Character.Translation.z); glTranslatef(Character.Translation.x, Character.Translation.y, zoom + Character.Translation.z);
@ -361,200 +379,160 @@ int DrawGLScene(void) // Here's Where We Do All The Drawing
if(ShowSkeleton){ if(ShowSkeleton){
glClear(GL_DEPTH_BUFFER_BIT); glClear(GL_DEPTH_BUFFER_BIT);
DrawBonesSkeleton(Skeleton.Bones[0]); DrawSkeleton();
} }
return TRUE; // Keep Going return true;
} }
void KillGLWindow(void) // Properly Kill The Window void KillGLWindow()
{ {
if (fullscreen) // Are We In Fullscreen Mode? if(fullscreen){
{ ChangeDisplaySettings(NULL, 0); //Reset to the desktop resolution
ChangeDisplaySettings(NULL,0); // If So Switch Back To The Desktop ShowCursor(true);
ShowCursor(TRUE); // Show Mouse Pointer
} }
if (hRC) // Do We Have A Rendering Context? if(hRC){
{ wglMakeCurrent(NULL, NULL);
if (!wglMakeCurrent(NULL,NULL)) // Are We Able To Release The DC And RC Contexts? wglDeleteContext(hRC);
{ hRC = NULL;
MessageBox(NULL,"Release Of DC And RC Failed.","SHUTDOWN ERROR",MB_OK | MB_ICONINFORMATION);
} }
if (!wglDeleteContext(hRC)) // Are We Able To Delete The RC? if(hDC){
{ ReleaseDC(hWnd,hDC);
MessageBox(NULL,"Release Rendering Context Failed.","SHUTDOWN ERROR",MB_OK | MB_ICONINFORMATION); hDC = NULL;
}
hRC=NULL; // Set RC To NULL
} }
if (hDC && !ReleaseDC(hWnd,hDC)) // Are We Able To Release The DC if(hWnd){
{ DestroyWindow(hWnd);
MessageBox(NULL,"Release Device Context Failed.","SHUTDOWN ERROR",MB_OK | MB_ICONINFORMATION); hWnd = NULL;
hDC=NULL; // Set DC To NULL
} }
if (hWnd && !DestroyWindow(hWnd)) // Are We Able To Destroy The Window? UnregisterClass("OpenGL", hInstance);
{ hInstance = NULL;
MessageBox(NULL,"Could Not Release hWnd.","SHUTDOWN ERROR",MB_OK | MB_ICONINFORMATION);
hWnd=NULL; // Set hWnd To NULL
}
if (!UnregisterClass("OpenGL",hInstance)) // Are We Able To Unregister Class
{
MessageBox(NULL,"Could Not Unregister Class.","SHUTDOWN ERROR",MB_OK | MB_ICONINFORMATION);
hInstance=NULL; // Set hInstance To NULL
}
} }
/* This Code Creates Our OpenGL Window. Parameters Are: *
* title - Title To Appear At The Top Of The Window *
* width - Width Of The GL Window Or Fullscreen Mode *
* height - Height Of The GL Window Or Fullscreen Mode *
* bits - Number Of Bits To Use For Color (8/16/24/32) *
* fullscreenflag - Use Fullscreen Mode (TRUE) Or Windowed Mode (FALSE) */
typedef bool (APIENTRY *PFNWGLSWAPINTERVALFARPROC)(int); typedef bool (APIENTRY *PFNWGLSWAPINTERVALFARPROC)(int);
BOOL CreateGLWindow(const char * title, int width, int height, int bits, bool fullscreenflag) BOOL CreateGLWindow(const char * title, int width, int height, int bits, bool fullscreenflag)
{ {
GLuint PixelFormat; // Holds The Results After Searching For A Match fullscreen = fullscreenflag;
WNDCLASS wc; // Windows Class Structure hInstance = GetModuleHandle(NULL);
DWORD dwExStyle; // Window Extended Style
DWORD dwStyle; // Window Style
fullscreen=fullscreenflag; // Set The Global Fullscreen Flag WNDCLASS wc = {
CS_HREDRAW | CS_VREDRAW | CS_OWNDC, //style
(WNDPROC) WndProc, //lpfnWndProc
0, //cbClsExtra
0, //cbWndExtra
hInstance, //hInstance
(HICON) LoadImage(NULL, IDI_WINLOGO, IMAGE_ICON, 0, 0, LR_SHARED), //hIcon
(HCURSOR) LoadImage(NULL, IDC_ARROW, IMAGE_CURSOR, 0, 0, LR_SHARED | LR_DEFAULTSIZE), //hCursor
NULL, //hbrBackground
NULL, //lpszMenuName
"OpenGL" //lpszClassName
};
hInstance = GetModuleHandle(NULL); // Grab An Instance For Our Window if(!RegisterClass(&wc)){
wc.style = CS_HREDRAW | CS_VREDRAW | CS_OWNDC; // Redraw On Size, And Own DC For Window. MessageBox(NULL, "Failed to registrer the window class.", NULL, MB_OK | MB_ICONERROR);
wc.lpfnWndProc = (WNDPROC) WndProc; // WndProc Handles Messages return false;
wc.cbClsExtra = 0; // No Extra Window Data
wc.cbWndExtra = 0; // No Extra Window Data
wc.hInstance = hInstance; // Set The Instance
wc.hIcon = LoadIcon(NULL, IDI_WINLOGO); // Load The Default Icon
wc.hCursor = LoadCursor(NULL, IDC_ARROW); // Load The Arrow Pointer
wc.hbrBackground = NULL; // No Background Required For GL
wc.lpszMenuName = NULL; // We Don't Want A Menu
wc.lpszClassName = "OpenGL"; // Set The Class Name
if (!RegisterClass(&wc)) // Attempt To Register The Window Class
{
MessageBox(NULL,"Failed To Register The Window Class.","ERROR",MB_OK|MB_ICONEXCLAMATION);
return FALSE; // Return FALSE
} }
if (fullscreen) // Attempt Fullscreen Mode? DWORD dwStyle, dwExStyle;
{
DEVMODE dmScreenSettings; // Device Mode if(fullscreen){
DEVMODE dmScreenSettings;
EnumDisplaySettings(NULL, ENUM_CURRENT_SETTINGS, &dmScreenSettings); EnumDisplaySettings(NULL, ENUM_CURRENT_SETTINGS, &dmScreenSettings);
width = dmScreenSettings.dmPelsWidth; width = dmScreenSettings.dmPelsWidth;
height = dmScreenSettings.dmPelsHeight; height = dmScreenSettings.dmPelsHeight;
bits = dmScreenSettings.dmBitsPerPel; bits = dmScreenSettings.dmBitsPerPel;
dwExStyle=WS_EX_APPWINDOW | WS_EX_TOPMOST; // Window Extended Style dwExStyle = WS_EX_APPWINDOW | WS_EX_TOPMOST;
dwStyle=WS_POPUP; // Windows Style dwStyle = WS_POPUP;
ShowCursor(FALSE); // Hide Mouse Pointer ShowCursor(false);
} }else{
else dwExStyle = WS_EX_APPWINDOW | WS_EX_WINDOWEDGE;
{ dwStyle = WS_OVERLAPPEDWINDOW;
dwExStyle=WS_EX_APPWINDOW | WS_EX_WINDOWEDGE; // Window Extended Style
dwStyle=WS_OVERLAPPEDWINDOW; // Windows Style
} }
RECT WindowRect; // Grabs Rectangle Upper Left / Lower Right Values RECT WindowRect;
WindowRect.left=(long)0; // Set Left Value To 0 WindowRect.left = 0;
WindowRect.right=(long)width; // Set Right Value To Requested Width WindowRect.right = width;
WindowRect.top=(long)0; // Set Top Value To 0 WindowRect.top = 0;
WindowRect.bottom=(long)height; // Set Bottom Value To Requested Height WindowRect.bottom = height;
AdjustWindowRectEx(&WindowRect, dwStyle, FALSE, dwExStyle); // Adjust Window To True Requested Size AdjustWindowRectEx(&WindowRect, dwStyle, false, dwExStyle);
// Create The Window // Create The Window
if (!(hWnd=CreateWindowEx( dwExStyle, // Extended Style For The Window if(!(hWnd = CreateWindowEx(dwExStyle, "OpenGL",
"OpenGL", // Class Name title,
title, // Window Title dwStyle | WS_CLIPSIBLINGS | WS_CLIPCHILDREN,
dwStyle | // Defined Window Style 0, 0,
WS_CLIPSIBLINGS | // Required Window Style WindowRect.right-WindowRect.left,
WS_CLIPCHILDREN, // Required Window Style WindowRect.bottom-WindowRect.top,
0, 0, // Window Position NULL, NULL, hInstance, NULL))
WindowRect.right-WindowRect.left, // Calculate Window Width ){
WindowRect.bottom-WindowRect.top, // Calculate Window Height KillGLWindow();
NULL, // No Parent Window MessageBox(NULL, "Window creation error.", NULL, MB_OK | MB_ICONERROR);
NULL, // No Menu return false;
hInstance, // Instance
NULL))) // Dont Pass Anything To WM_CREATE
{
KillGLWindow(); // Reset The Display
MessageBox(NULL,"Window Creation Error.","ERROR",MB_OK|MB_ICONEXCLAMATION);
return FALSE; // Return FALSE
} }
static PIXELFORMATDESCRIPTOR pfd= // pfd Tells Windows How We Want Things To Be const PIXELFORMATDESCRIPTOR pfd = {
{ sizeof(PIXELFORMATDESCRIPTOR), 1, //Size and version
sizeof(PIXELFORMATDESCRIPTOR), // Size Of This Pixel Format Descriptor PFD_DRAW_TO_WINDOW | //dwFlags
1, // Version Number PFD_SUPPORT_OPENGL |
PFD_DRAW_TO_WINDOW | // Format Must Support Window PFD_DOUBLEBUFFER,
PFD_SUPPORT_OPENGL | // Format Must Support OpenGL PFD_TYPE_RGBA, //iPixelType
PFD_DOUBLEBUFFER, // Must Support Double Buffering bits, //cColorBits
PFD_TYPE_RGBA, // Request An RGBA Format 0, 0, 0, 0, 0, 0, 0, 0, //R,G,B,A bits
bits, // Select Our Color Depth 0, 0, 0, 0, 0, //Accumulation buffer bits
0, 0, 0, 0, 0, 0, // Color Bits Ignored 16, //cDepthBits
0, // No Alpha Buffer 0, //cStencilBits
0, // Shift Bit Ignored 0, //cAuxBuffers
0, // No Accumulation Buffer PFD_MAIN_PLANE, //iLayerType
0, 0, 0, 0, // Accumulation Bits Ignored 0, //Reserved
16, // 16Bit Z-Buffer (Depth Buffer) 0, 0, 0 //Masks
0, // No Stencil Buffer
0, // No Auxiliary Buffer
PFD_MAIN_PLANE, // Main Drawing Layer
0, // Reserved
0, 0, 0 // Layer Masks Ignored
}; };
if (!(hDC=GetDC(hWnd))) // Did We Get A Device Context? hDC = GetDC(hWnd);
{ if(!hDC){
KillGLWindow(); // Reset The Display KillGLWindow();
MessageBox(NULL,"Can't Create A GL Device Context.","ERROR",MB_OK|MB_ICONEXCLAMATION); MessageBox(NULL, "Failed to create an OpenGL device context.", NULL, MB_OK | MB_ICONERROR);
return FALSE; // Return FALSE return false;
} }
if (!(PixelFormat=ChoosePixelFormat(hDC,&pfd))) // Did Windows Find A Matching Pixel Format? unsigned PixelFormat = ChoosePixelFormat(hDC, &pfd);
{ if(!PixelFormat){
KillGLWindow(); // Reset The Display KillGLWindow();
MessageBox(NULL,"Can't Find A Suitable PixelFormat.","ERROR",MB_OK|MB_ICONEXCLAMATION); MessageBox(NULL, "Can't find a suitable PixelFormat.", NULL, MB_OK | MB_ICONERROR);
return FALSE; // Return FALSE return false;
} }
if(!SetPixelFormat(hDC,PixelFormat,&pfd)) // Are We Able To Set The Pixel Format? if(!SetPixelFormat(hDC,PixelFormat, &pfd)){
{ KillGLWindow();
KillGLWindow(); // Reset The Display MessageBox(NULL, "Can't set the PixelFormat.", NULL, MB_OK | MB_ICONERROR);
MessageBox(NULL,"Can't Set The PixelFormat.","ERROR",MB_OK|MB_ICONEXCLAMATION); return false;
return FALSE; // Return FALSE
} }
if (!(hRC=wglCreateContext(hDC))) // Are We Able To Get A Rendering Context? hRC = wglCreateContext(hDC);
{ if(!hRC){
KillGLWindow(); // Reset The Display KillGLWindow();
MessageBox(NULL,"Can't Create A GL Rendering Context.","ERROR",MB_OK|MB_ICONEXCLAMATION); MessageBox(NULL, "Failed to create an OpenGL rendering context.", NULL, MB_OK | MB_ICONERROR);
return FALSE; // Return FALSE return false;
} }
if(!wglMakeCurrent(hDC,hRC)) // Try To Activate The Rendering Context if(!wglMakeCurrent(hDC, hRC)){
{ KillGLWindow();
KillGLWindow(); // Reset The Display MessageBox(NULL, "Failed to activate an OpenGL device context.", NULL, MB_OK | MB_ICONERROR);
MessageBox(NULL,"Can't Activate The GL Rendering Context.","ERROR",MB_OK|MB_ICONEXCLAMATION); return false;
return FALSE; // Return FALSE
} }
ShowWindow(hWnd,SW_SHOW); // Show The Window ShowWindow(hWnd,SW_SHOW);
SetForegroundWindow(hWnd); // Slightly Higher Priority SetForegroundWindow(hWnd);
SetFocus(hWnd); // Sets Keyboard Focus To The Window SetFocus(hWnd);
ReSizeGLScene(width, height); // Set Up Our Perspective GL Screen ResizeScene(width, height);
if (!InitGL()) // Initialize Our Newly Created GL Window if(!InitGL()){
{ KillGLWindow();
KillGLWindow(); // Reset The Display MessageBox(NULL, "Initialization failed.", NULL, MB_OK | MB_ICONERROR);
MessageBox(NULL,"Initialization Failed.","ERROR",MB_OK|MB_ICONEXCLAMATION); return false;
return FALSE; // Return FALSE
} }
PFNWGLSWAPINTERVALFARPROC wglSwapIntervalEXT = 0; PFNWGLSWAPINTERVALFARPROC wglSwapIntervalEXT = 0;
@ -564,256 +542,123 @@ BOOL CreateGLWindow(const char * title, int width, int height, int bits, bool fu
QueryPerformanceFrequency(&ClockFreq); QueryPerformanceFrequency(&ClockFreq);
QueryPerformanceCounter(&PreviousTime); QueryPerformanceCounter(&PreviousTime);
return TRUE; // Success return true;
} }
LRESULT CALLBACK WndProc( HWND hWnd, // Handle For This Window LRESULT CALLBACK WndProc(HWND hWnd, UINT uMsg, WPARAM wParam, LPARAM lParam)
UINT uMsg, // Message For This Window
WPARAM wParam, // Additional Message Information
LPARAM lParam) // Additional Message Information
{ {
switch (uMsg) // Check For Windows Messages switch (uMsg) {
{ case WM_KEYDOWN: {
case WM_ACTIVATE: // Watch For Window Activate Message if(wParam == VK_ESCAPE){
{ PostQuitMessage(0);
}else if(wParam == VK_F11 && !keys[VK_F11]){
KillGLWindow();
fullscreen = !fullscreen;
if(!CreateGLWindow("libvitaboy - Renderer",640,480,16,fullscreen)){
PostQuitMessage(0);
}
}
keys[wParam] = true;
} return 0;
case WM_KEYUP: {
keys[wParam] = false;
} return 0;
case WM_ACTIVATE: {
// LoWord Can Be WA_INACTIVE, WA_ACTIVE, WA_CLICKACTIVE, // LoWord Can Be WA_INACTIVE, WA_ACTIVE, WA_CLICKACTIVE,
// The High-Order Word Specifies The Minimized State Of The Window Being Activated Or Deactivated. // The High-Order Word Specifies The Minimized State Of The Window Being Activated Or Deactivated.
// A NonZero Value Indicates The Window Is Minimized. // A NonZero Value Indicates The Window Is Minimized.
if ((LOWORD(wParam) != WA_INACTIVE) && !((BOOL)HIWORD(wParam))) if ((LOWORD(wParam) != WA_INACTIVE) && !((BOOL)HIWORD(wParam)))
active=TRUE; // Program Is Active active = true;
else else
active=FALSE; // Program Is No Longer Active active = false;
} return 0;
return 0; // Return To The Message Loop case WM_SIZE: {
} ResizeScene(LOWORD(lParam),HIWORD(lParam));
} return 0;
case WM_SYSCOMMAND: // Intercept System Commands case WM_SYSCOMMAND: {
{ switch (wParam) {
switch (wParam) // Check System Calls case SC_SCREENSAVE:
{ case SC_MONITORPOWER:
case SC_SCREENSAVE: // Screensaver Trying To Start? return 0;
case SC_MONITORPOWER: // Monitor Trying To Enter Powersave?
return 0; // Prevent From Happening
}
break; // Exit
} }
} break;
case WM_KEYDOWN: // Is A Key Being Held Down? case WM_DEVMODECHANGE: {
{
if(wParam == VK_ESCAPE){
PostQuitMessage(0);
}else if(wParam == VK_F11){
KillGLWindow(); // Kill Our Current Window
fullscreen=!fullscreen; // Toggle Fullscreen / Windowed Mode
// Recreate Our OpenGL Window
if (!CreateGLWindow("NeHe's Solid Object Tutorial",640,480,16,fullscreen))
{
PostQuitMessage(0); // Quit If Window Was Not Created
}
}
else keys[wParam] = TRUE;
return 0; // Jump Back
}
case WM_KEYUP: // Has A Key Been Released?
{
keys[wParam] = FALSE; // If So, Mark It As FALSE
return 0; // Jump Back
}
case WM_SIZE: // Resize The OpenGL Window
{
ReSizeGLScene(LOWORD(lParam),HIWORD(lParam)); // LoWord=Width, HiWord=Height
return 0; // Jump Back
}
case WM_DEVMODECHANGE:
{
DEVMODE dm; DEVMODE dm;
EnumDisplaySettings(NULL, ENUM_CURRENT_SETTINGS, &dm); EnumDisplaySettings(NULL, ENUM_CURRENT_SETTINGS, &dm);
FramePeriod = 1.0f/dm.dmDisplayFrequency; FramePeriod = 1.0f/dm.dmDisplayFrequency;
return 0; } return 0;
case WM_CLOSE: {
PostQuitMessage(0);
} return 0;
} }
case WM_QUIT: return DefWindowProc(hWnd, uMsg, wParam, lParam);
case WM_CLOSE: // Did We Receive A Close Message?
{
PostQuitMessage(0); // Send A Quit Message
return 0; // Jump Back
}
}
// Pass All Unhandled Messages To DefWindowProc
return DefWindowProc(hWnd,uMsg,wParam,lParam);
} }
int WINAPI WinMain( HINSTANCE, // Instance bool Read(const char * Filename, uint8_t ** InData){
HINSTANCE, // Previous Instance *InData = File::ReadFile(Filename);
LPSTR, // Command Line Parameters if(*InData != NULL){
int) // Window Show State VBFile.set(*InData, File::FileSize);
return true;
}
const char * Message;
switch(File::Error){
case FERR_NOT_FOUND:
Message = "%s does not exist.";
break;
case FERR_OPEN:
Message = "%s could not be opened for reading.";
break;
case FERR_BLANK:
Message = "%s is corrupt or invalid.";
break;
case FERR_MEMORY:
Message = "Memory for %s could not be allocated.";
break;
default:
Message = "%s could not be read.";
break;
}
char Buffer[1024];
sprintf(Buffer, Message, Filename);
MessageBox(hWnd, Buffer, NULL, MB_OK | MB_ICONERROR);
return false;
}
int APIENTRY WinMain(HINSTANCE, HINSTANCE, LPSTR, int)
{ {
HANDLE hFile; uint8_t * InData;
unsigned FileSize;
uint8_t *InData;
DWORD bytestransferred;
hFile = CreateFile("skeleton.skel", GENERIC_READ, FILE_SHARE_READ, NULL, OPEN_EXISTING, FILE_FLAG_SEQUENTIAL_SCAN, NULL); if(!Read("skeleton.skel", &InData))
if(hFile == INVALID_HANDLE_VALUE){
if(GetLastError() == ERROR_FILE_NOT_FOUND){
MessageBox(NULL, "The specified skeleton does not exist.", "Error", MB_OK);
return 0; return 0;
}
MessageBox(NULL, "The skeleton could not be opened for reading.", "Error", MB_OK);
return 0;
}
FileSize = GetFileSize(hFile, NULL);
InData = (uint8_t*) malloc(FileSize);
if(InData == NULL){
MessageBox(NULL, "Memory for the skeleton could not be allocated.", "Error", MB_OK);
return 0;
}
if(!ReadFile(hFile, InData, FileSize, &bytestransferred, NULL) || bytestransferred != FileSize){
MessageBox(NULL, "The skeleton could not be read.", "Error", MB_OK);
return 0;
}
CloseHandle(hFile);
VBFile.set(InData, FileSize);
ReadSkeleton(Skeleton); ReadSkeleton(Skeleton);
free(InData); free(InData);
hFile = CreateFile("body.mesh", GENERIC_READ, FILE_SHARE_READ, NULL, OPEN_EXISTING, FILE_FLAG_SEQUENTIAL_SCAN, NULL); for(unsigned i=0; i<MeshCount; i++){
if(hFile == INVALID_HANDLE_VALUE){ if(!Read(MeshPaths[i], &InData))
if(GetLastError() == ERROR_FILE_NOT_FOUND){
MessageBox(NULL, "body.mesh does not exist.", "Error", MB_OK);
return 0; return 0;
} ReadMesh(Meshes[i]);
MessageBox(NULL, "body.mesh could not be opened for reading.", "Error", MB_OK);
return 0;
}
FileSize = GetFileSize(hFile, NULL);
InData = (uint8_t*) malloc(FileSize);
if(InData == NULL){
MessageBox(NULL, "Memory for body.mesh could not be allocated.", "Error", MB_OK);
return 0;
}
if(!ReadFile(hFile, InData, FileSize, &bytestransferred, NULL) || bytestransferred != FileSize){
MessageBox(NULL, "body.mesh could not be read.", "Error", MB_OK);
return 0;
}
CloseHandle(hFile);
VBFile.set(InData, FileSize);
ReadMesh(Meshes[0]);
free(InData); free(InData);
}
hFile = CreateFile("head.mesh", GENERIC_READ, FILE_SHARE_READ, NULL, OPEN_EXISTING, FILE_FLAG_SEQUENTIAL_SCAN, NULL); if(!Read("animation.anim", &InData))
if(hFile == INVALID_HANDLE_VALUE){
if(GetLastError() == ERROR_FILE_NOT_FOUND){
MessageBox(NULL, "head.mesh does not exist.", "Error", MB_OK);
return 0; return 0;
}
MessageBox(NULL, "head.mesh could not be opened for reading.", "Error", MB_OK);
return 0;
}
FileSize = GetFileSize(hFile, NULL);
InData = (uint8_t*) malloc(FileSize);
if(InData == NULL){
MessageBox(NULL, "Memory for head.mesh could not be allocated.", "Error", MB_OK);
return 0;
}
if(!ReadFile(hFile, InData, FileSize, &bytestransferred, NULL) || bytestransferred != FileSize){
MessageBox(NULL, "head.mesh could not be read.", "Error", MB_OK);
return 0;
}
CloseHandle(hFile);
VBFile.set(InData, FileSize);
ReadMesh(Meshes[1]);
free(InData);
hFile = CreateFile("lhand.mesh", GENERIC_READ, FILE_SHARE_READ, NULL, OPEN_EXISTING, FILE_FLAG_SEQUENTIAL_SCAN, NULL);
if(hFile == INVALID_HANDLE_VALUE){
if(GetLastError() == ERROR_FILE_NOT_FOUND){
MessageBox(NULL, "lhand.mesh does not exist.", "Error", MB_OK);
return 0;
}
MessageBox(NULL, "lhand.mesh could not be opened for reading.", "Error", MB_OK);
return 0;
}
FileSize = GetFileSize(hFile, NULL);
InData = (uint8_t*) malloc(FileSize);
if(InData == NULL){
MessageBox(NULL, "Memory for lhand.mesh could not be allocated.", "Error", MB_OK);
return 0;
}
if(!ReadFile(hFile, InData, FileSize, &bytestransferred, NULL) || bytestransferred != FileSize){
MessageBox(NULL, "lhand.mesh could not be read.", "Error", MB_OK);
return 0;
}
CloseHandle(hFile);
VBFile.set(InData, FileSize);
ReadMesh(Meshes[2]);
free(InData);
hFile = CreateFile("rhand.mesh", GENERIC_READ, FILE_SHARE_READ, NULL, OPEN_EXISTING, FILE_FLAG_SEQUENTIAL_SCAN, NULL);
if(hFile == INVALID_HANDLE_VALUE){
if(GetLastError() == ERROR_FILE_NOT_FOUND){
MessageBox(NULL, "rhand.mesh does not exist.", "Error", MB_OK);
return 0;
}
MessageBox(NULL, "rhand.mesh could not be opened for reading.", "Error", MB_OK);
return 0;
}
FileSize = GetFileSize(hFile, NULL);
InData = (uint8_t*) malloc(FileSize);
if(InData == NULL){
MessageBox(NULL, "Memory for rhand.mesh could not be allocated.", "Error", MB_OK);
return 0;
}
if(!ReadFile(hFile, InData, FileSize, &bytestransferred, NULL) || bytestransferred != FileSize){
MessageBox(NULL, "rhand.mesh could not be read.", "Error", MB_OK);
return 0;
}
CloseHandle(hFile);
VBFile.set(InData, FileSize);
ReadMesh(Meshes[3]);
free(InData);
hFile = CreateFile("animation.anim", GENERIC_READ, FILE_SHARE_READ, NULL, OPEN_EXISTING, FILE_FLAG_SEQUENTIAL_SCAN, NULL);
if(hFile == INVALID_HANDLE_VALUE){
if(GetLastError() == ERROR_FILE_NOT_FOUND){
MessageBox(NULL, "animation.anim does not exist.", "Error", MB_OK);
return 0;
}
MessageBox(NULL, "animation.anim could not be opened for reading.", "Error", MB_OK);
return 0;
}
FileSize = GetFileSize(hFile, NULL);
InData = (uint8_t*) malloc(FileSize);
if(InData == NULL){
MessageBox(NULL, "Memory for animation.anim could not be allocated.", "Error", MB_OK);
return 0;
}
if(!ReadFile(hFile, InData, FileSize, &bytestransferred, NULL) || bytestransferred != FileSize){
MessageBox(NULL, "animation.anim could not be read.", "Error", MB_OK);
return 0;
}
CloseHandle(hFile);
VBFile.set(InData, FileSize);
ReadAnimation(Animation); ReadAnimation(Animation);
free(InData); free(InData);
AdvanceFrame(Skeleton, Animation, 0); AdvanceFrame(Skeleton, Animation, 0);
// Create Our OpenGL Window if(!CreateGLWindow("libvitaboy - Renderer",640,480,16,fullscreen)){
if (!CreateGLWindow("libvitaboy - Renderer",640,480,16,fullscreen)) return 0;
{
return 0; // Quit If Window Was Not Created
} }
DEVMODE dm; DEVMODE dm;
@ -824,8 +669,8 @@ int WINAPI WinMain( HINSTANCE, // Instance
MSG msg; MSG msg;
while(true){ while(true){
while(PeekMessage(&msg, NULL, 0, 0, PM_REMOVE)){ while(PeekMessage(&msg, NULL, 0, 0, PM_REMOVE)){
TranslateMessage(&msg); // Translate The Message TranslateMessage(&msg);
DispatchMessage(&msg); // Dispatch The Message DispatchMessage(&msg);
if(msg.message == WM_QUIT) if(msg.message == WM_QUIT)
quit = true; quit = true;
@ -840,7 +685,7 @@ int WINAPI WinMain( HINSTANCE, // Instance
if(SleepDuration > 1) Sleep((unsigned) SleepDuration); if(SleepDuration > 1) Sleep((unsigned) SleepDuration);
} }
// Shutdown //Shutdown
KillGLWindow(); // Kill The Window KillGLWindow();
return (msg.wParam); // Exit The Program return (msg.wParam);
} }

View file

@ -40,23 +40,6 @@ float DotProduct(Rotation_t * q1, Rotation_t * q2){
return q1->x*q2->x + q1->y*q2->y + q1->z*q2->z + q1->w*q2->w; return q1->x*q2->x + q1->y*q2->y + q1->z*q2->z + q1->w*q2->w;
} }
void CombineQuaternions(Rotation_t * Destination, Rotation_t * Source){
// the constructor takes its arguments as (x, y, z, w)
float dx = Destination->x;
float dy = Destination->y;
float dz = Destination->z;
float dw = Destination->w;
float sx = Source->x;
float sy = Source->y;
float sz = Source->z;
float sw = Source->w;
Destination->x = dw*sx + dx*sw + dy*sz - dz*sy;
Destination->y = dw*sy + dy*sw + dz*sx - dx*sz;
Destination->z = dw*sz + dz*sw + dx*sy - dy*sx;
Destination->w = dw*sw - dx*sx - dy*sy - dz*sz;
}
void FindQuaternionMatrix(float * Matrix, Rotation_t * Quaternion){ void FindQuaternionMatrix(float * Matrix, Rotation_t * Quaternion){
float x2 = Quaternion->x * Quaternion->x; float x2 = Quaternion->x * Quaternion->x;
float y2 = Quaternion->y * Quaternion->y; float y2 = Quaternion->y * Quaternion->y;