From 91a7199d02a4c6908cc408c8fa86744018320e39 Mon Sep 17 00:00:00 2001 From: hybrid Date: Fri, 4 Jan 2008 11:10:37 +0000 Subject: [PATCH] Merged 1134:1151 from branch 1.4 git-svn-id: http://svn.code.sf.net/p/irrlicht/code/trunk@1152 dfc29bdd-3216-0410-991c-e03cc46cb475 --- examples/01.HelloWorld/main.cpp | 2 +- include/IGUIComboBox.h | 6 +- include/IrrCompileConfig.h | 25 +- include/irrMath.h | 4 +- source/Irrlicht/CFileList.cpp | 4 +- source/Irrlicht/CFileSystem.cpp | 4 +- source/Irrlicht/CGUIComboBox.cpp | 6 +- source/Irrlicht/CGUIComboBox.h | 2 +- source/Irrlicht/CMS3DMeshFileLoader.cpp | 362 +++-- source/Irrlicht/CMS3DMeshFileLoader.h | 12 +- source/Irrlicht/COSOperator.cpp | 9 +- source/Irrlicht/COpenGLDriver.cpp | 10 +- source/Irrlicht/COpenGLDriver.h | 6 +- source/Irrlicht/COpenGLExtensionHandler.h | 2 +- source/Irrlicht/COpenGLMaterialRenderer.h | 1435 ++++++++--------- source/Irrlicht/COpenGLSLMaterialRenderer.h | 2 +- .../Irrlicht/COpenGLShaderMaterialRenderer.h | 2 +- source/Irrlicht/COpenGLTexture.h | 2 +- source/Irrlicht/CPakReader.cpp | 4 +- source/Irrlicht/CSoftwareDriver2.cpp | 16 +- source/Irrlicht/CXMLWriter.cpp | 2 +- source/Irrlicht/CZipReader.cpp | 4 +- source/Irrlicht/MacOSX/CIrrDeviceMacOSX.h | 428 ++--- source/Irrlicht/MacOSX/CIrrDeviceMacOSX.mm | 1260 +++++++-------- .../MacOSX/MacOSX.xcodeproj/project.pbxproj | 78 +- source/Irrlicht/SoftwareDriver2_helper.h | 6 - source/Irrlicht/os.cpp | 3 +- 27 files changed, 1926 insertions(+), 1770 deletions(-) diff --git a/examples/01.HelloWorld/main.cpp b/examples/01.HelloWorld/main.cpp index e3ba351a..dc7385ea 100644 --- a/examples/01.HelloWorld/main.cpp +++ b/examples/01.HelloWorld/main.cpp @@ -109,7 +109,7 @@ int main() */ IrrlichtDevice *device = -#ifdef MACOSX +#ifdef _IRR_OSX_PLATFORM_ createDevice( video::EDT_OPENGL, dimension2d(640, 480), 16, false, false, false, 0); #else diff --git a/include/IGUIComboBox.h b/include/IGUIComboBox.h index f60f9cfb..a0d801c4 100644 --- a/include/IGUIComboBox.h +++ b/include/IGUIComboBox.h @@ -33,8 +33,8 @@ namespace gui virtual u32 addItem(const wchar_t* text) = 0; //! Removes an item from the combo box. - /** Warning. This will change the IDs of all following items */ - virtual void removeItem(u32 id) = 0; + /** Warning. This will change the index of all following items */ + virtual void removeItem(u32 idx) = 0; //! Deletes all items in the combo box virtual void clear() = 0; @@ -43,7 +43,7 @@ namespace gui virtual s32 getSelected() const = 0; //! Sets the selected item. Set this to -1 if no item should be selected - virtual void setSelected(s32 id) = 0; + virtual void setSelected(s32 idx) = 0; }; diff --git a/include/IrrCompileConfig.h b/include/IrrCompileConfig.h index 093e7e4f..2e7305a1 100644 --- a/include/IrrCompileConfig.h +++ b/include/IrrCompileConfig.h @@ -14,17 +14,22 @@ //! _IRR_WINDOWS_API_ for Windows or XBox //! _IRR_LINUX_PLATFORM_ for Linux (it is defined here if no other os is defined) //! _IRR_SOLARIS_PLATFORM_ for Solaris +//! _IRR_OSX_PLATFORM_ for Apple systems running OSX //! _IRR_POSIX_API_ for Posix compatible systems //! _IRR_USE_SDL_DEVICE_ for platform independent SDL framework //! _IRR_USE_WINDOWS_DEVICE_ for Windows API based device //! _IRR_USE_WINDOWS_CE_DEVICE_ for Windows CE API based device //! _IRR_USE_LINUX_DEVICE_ for X11 based device -//! MACOSX for Mac OS X +//! _IRR_USE_OSX_DEVICE_ for Cocoa native windowing on OSX +//! Note: PLATFORM defines the OS specific layer, API can groups several platforms +//! DEVICE is the windowing system used, several PLATFORMs support more than one DEVICE +//! Moreover, the DEVICE defined here is not directly related to the Irrlicht devices created in the app (but may depend on each other). //#define _IRR_USE_SDL_DEVICE_ 1 //! WIN32 for Windows32 //! WIN64 for Windows64 +// The windows platform and API support SDL and WINDOW device #if defined(WIN32) || defined(WIN64) || defined(_WIN32_WCE) #define _IRR_WINDOWS_ #define _IRR_WINDOWS_API_ @@ -33,12 +38,24 @@ #endif #endif +// XBox only suppots the native Window stuff #if defined(_XBOX) #define _IRR_XBOX_PLATFORM_ #define _IRR_WINDOWS_API_ +#define _IRR_USE_WINDOWS_DEVICE_ #endif -#if !defined(_IRR_WINDOWS_API_) && !defined(MACOSX) +#if defined(__APPLE__) || defined(MACOSX) +#if !defined(MACOSX) +#define MACOSX // legacy support +#endif +#define _IRR_OSX_PLATFORM_ +#if !defined(_IRR_USE_LINUX_DEVICE_) // for X11 windowing declare this +#define _IRR_USE_OSX_DEVICE_ +#endif +#endif + +#if !defined(_IRR_WINDOWS_API_) && !defined(_IRR_OSX_PLATFORM_) #if defined(__sparc__) || defined(__sun__) #define __BIG_ENDIAN__ #define _IRR_SOLARIS_PLATFORM_ @@ -93,7 +110,7 @@ define out. */ //! Define _IRR_OPENGL_USE_EXTPOINTER_ if the OpenGL renderer should use OpenGL extensions via function pointers. /** On some systems there is no support for the dynamic extension of OpenGL via function pointers such that this has to be undef'ed. */ -#if !defined(MACOSX) && !defined(_IRR_SOLARIS_PLATFORM_) +#if !defined(_IRR_OSX_PLATFORM_) && !defined(_IRR_SOLARIS_PLATFORM_) #define _IRR_OPENGL_USE_EXTPOINTER_ #endif @@ -302,7 +319,7 @@ B3D, MS3D or X meshes */ /** Irrlicht should use approximate float and integer fpu techniques precision will be lower but speed higher. currently X86 only */ -#if !defined(MACOSX) && !defined(_IRR_SOLARIS_PLATFORM_) +#if !defined(_IRR_OSX_PLATFORM_) && !defined(_IRR_SOLARIS_PLATFORM_) //#define IRRLICHT_FAST_MATH #endif diff --git a/include/irrMath.h b/include/irrMath.h index c3da4234..630e09a5 100644 --- a/include/irrMath.h +++ b/include/irrMath.h @@ -211,7 +211,9 @@ namespace core // only same sign #define F32_A_GREATER_B(a,b) (F32_AS_S32((a)) > F32_AS_S32((b))) + #else + #define F32_LOWER_0(n) ((n) < 0.0f) #define F32_LOWER_EQUAL_0(n) ((n) <= 0.0f) #define F32_GREATER_0(n) ((n) > 0.0f) @@ -246,7 +248,7 @@ namespace core /* if (condition) state |= m; else state &= ~m; */ - REALINLINE void setbit ( u32 &state, s32 condition, u32 mask ) + REALINLINE void setbit_cond ( u32 &state, s32 condition, u32 mask ) { // 0, or any postive to mask //s32 conmask = -condition >> 31; diff --git a/source/Irrlicht/CFileList.cpp b/source/Irrlicht/CFileList.cpp index 8da2af88..5f66ef57 100644 --- a/source/Irrlicht/CFileList.cpp +++ b/source/Irrlicht/CFileList.cpp @@ -12,7 +12,7 @@ namespace irr namespace io { -#if (defined(_IRR_POSIX_API_) || defined(MACOSX)) +#if (defined(_IRR_POSIX_API_) || defined(_IRR_OSX_PLATFORM_)) #include #include #include @@ -72,7 +72,7 @@ CFileList::CFileList() // -------------------------------------------- // Linux version - #if (defined(_IRR_POSIX_API_) || defined(MACOSX)) + #if (defined(_IRR_POSIX_API_) || defined(_IRR_OSX_PLATFORM_)) FileEntry entry; diff --git a/source/Irrlicht/CFileSystem.cpp b/source/Irrlicht/CFileSystem.cpp index 9d2e612c..3839052a 100644 --- a/source/Irrlicht/CFileSystem.cpp +++ b/source/Irrlicht/CFileSystem.cpp @@ -191,7 +191,7 @@ const c8* CFileSystem::getWorkingDirectory() #endif #endif -#if (defined(_IRR_POSIX_API_) || defined(MACOSX)) +#if (defined(_IRR_POSIX_API_) || defined(_IRR_OSX_PLATFORM_)) getcwd(WorkingDirectory, (size_t)FILE_SYSTEM_MAX_PATH); #endif return WorkingDirectory; @@ -227,7 +227,7 @@ core::stringc CFileSystem::getAbsolutePath(const core::stringc& filename) const ret = p; #endif -#elif (defined(_IRR_POSIX_API_) || defined(MACOSX)) +#elif (defined(_IRR_POSIX_API_) || defined(_IRR_OSX_PLATFORM_)) c8 fpath[4096]; p = realpath(filename.c_str(), fpath); diff --git a/source/Irrlicht/CGUIComboBox.cpp b/source/Irrlicht/CGUIComboBox.cpp index 60fb2d6b..7cc98720 100644 --- a/source/Irrlicht/CGUIComboBox.cpp +++ b/source/Irrlicht/CGUIComboBox.cpp @@ -127,12 +127,12 @@ s32 CGUIComboBox::getSelected() const //! sets the selected item. Set this to -1 if no item should be selected -void CGUIComboBox::setSelected(s32 id) +void CGUIComboBox::setSelected(s32 idx) { - if (id < -1 || id >= (s32)Items.size()) + if (idx < -1 || idx >= (s32)Items.size()) return; - Selected = id; + Selected = idx; } void CGUIComboBox::updateAbsolutePosition() diff --git a/source/Irrlicht/CGUIComboBox.h b/source/Irrlicht/CGUIComboBox.h index f6e4a863..ead41707 100644 --- a/source/Irrlicht/CGUIComboBox.h +++ b/source/Irrlicht/CGUIComboBox.h @@ -50,7 +50,7 @@ namespace gui virtual s32 getSelected() const; //! sets the selected item. Set this to -1 if no item should be selected - virtual void setSelected(s32 id); + virtual void setSelected(s32 idx); //! update the position virtual void updateAbsolutePosition(); diff --git a/source/Irrlicht/CMS3DMeshFileLoader.cpp b/source/Irrlicht/CMS3DMeshFileLoader.cpp index 97a2626f..f30198fc 100644 --- a/source/Irrlicht/CMS3DMeshFileLoader.cpp +++ b/source/Irrlicht/CMS3DMeshFileLoader.cpp @@ -11,7 +11,6 @@ #include "CSkinnedMesh.h" - namespace irr { namespace scene @@ -31,16 +30,16 @@ namespace scene // File header struct MS3DHeader { - c8 ID[10]; - s32 Version; + char ID[10]; + int Version; } PACK_STRUCT; // Vertex information struct MS3DVertex { u8 Flags; - f32 Vertex[3]; - s8 BoneID; + float Vertex[3]; + char BoneID; u8 RefCount; } PACK_STRUCT; @@ -49,8 +48,8 @@ struct MS3DTriangle { u16 Flags; u16 VertexIndices[3]; - f32 VertexNormals[3][3]; - f32 S[3], T[3]; + float VertexNormals[3][3]; + float S[3], T[3]; u8 SmoothingGroup; u8 GroupIndex; } PACK_STRUCT; @@ -58,26 +57,26 @@ struct MS3DTriangle // Material information struct MS3DMaterial { - s8 Name[32]; - f32 Ambient[4]; - f32 Diffuse[4]; - f32 Specular[4]; - f32 Emissive[4]; - f32 Shininess; // 0.0f - 128.0f - f32 Transparency; // 0.0f - 1.0f + char Name[32]; + float Ambient[4]; + float Diffuse[4]; + float Specular[4]; + float Emissive[4]; + float Shininess; // 0.0f - 128.0f + float Transparency; // 0.0f - 1.0f u8 Mode; // 0, 1, 2 is unused now - s8 Texture[128]; - s8 Alphamap[128]; + char Texture[128]; + char Alphamap[128]; } PACK_STRUCT; // Joint information struct MS3DJoint { u8 Flags; - s8 Name[32]; - s8 ParentName[32]; - f32 Rotation[3]; - f32 Translation[3]; + char Name[32]; + char ParentName[32]; + float Rotation[3]; + float Translation[3]; u16 NumRotationKeyframes; u16 NumTranslationKeyframes; } PACK_STRUCT; @@ -85,8 +84,15 @@ struct MS3DJoint // Keyframe data struct MS3DKeyframe { - f32 Time; - f32 Parameter[3]; + float Time; + float Parameter[3]; +} PACK_STRUCT; + +// vertex weights in 1.8.x +struct MS3DVertexWeights +{ + char boneIds[3]; + u8 weights[3]; } PACK_STRUCT; // Default alignment @@ -96,6 +102,13 @@ struct MS3DKeyframe #undef PACK_STRUCT +struct SGroup +{ + core::stringc Name; + core::array VertexIds; + u16 MaterialIdx; +}; + //! Constructor CMS3DMeshFileLoader::CMS3DMeshFileLoader(video::IVideoDriver *driver) : Driver(driver), AnimatedMesh(0) @@ -137,7 +150,7 @@ IAnimatedMesh* CMS3DMeshFileLoader::createMesh(io::IReadFile* file) } -//! loads an md2 file +//! loads a milkshape file bool CMS3DMeshFileLoader::load(io::IReadFile* file) { if (!file) @@ -180,11 +193,6 @@ bool CMS3DMeshFileLoader::load(io::IReadFile* file) return false; } - if ( pHeader->Version == 4 ) - { - os::Printer::log("Milkshape3D version 4 (1.8) is not fully supported. Some features may not be available.", file->getFileName(), ELL_WARNING); - } - // get pointers to data // vertices @@ -195,6 +203,12 @@ bool CMS3DMeshFileLoader::load(io::IReadFile* file) pPtr += sizeof(u16); MS3DVertex *vertices = (MS3DVertex*)pPtr; pPtr += sizeof(MS3DVertex) * numVertices; + if (pPtr > buffer+fileSize) + { + delete [] buffer; + os::Printer::log("Loading failed. Corrupted data found.", file->getFileName(), ELL_ERROR); + return false; + } #ifdef __BIG_ENDIAN__ for (u16 tmp=0; tmp buffer+fileSize) + { + delete [] buffer; + os::Printer::log("Loading failed. Corrupted data found.", file->getFileName(), ELL_ERROR); + return false; + } #ifdef __BIG_ENDIAN__ for (u16 tmp=0; tmp groups; + groups.reallocate(numGroups); - //skip groups + //store groups u32 i; for (i=0; i buffer+fileSize) + { + delete [] buffer; + os::Printer::log("Loading failed. Corrupted data found.", file->getFileName(), ELL_ERROR); + return false; + } } // skip materials @@ -276,12 +306,10 @@ bool CMS3DMeshFileLoader::load(io::IReadFile* file) // MS3DMaterial *materials = (MS3DMaterial*)pPtr; // pPtr += sizeof(MS3DMaterial) * numMaterials; - if(numMaterials <= 0) + if(numMaterials == 0) { // if there are no materials, add at least one buffer - AnimatedMesh->createBuffer(); - } for (i=0; iTransparency = os::Byteswap::byteswap(material->Transparency); #endif pPtr += sizeof(MS3DMaterial); - + if (pPtr > buffer+fileSize) + { + delete [] buffer; + os::Printer::log("Loading failed. Corrupted data found.", file->getFileName(), ELL_ERROR); + return false; + } scene::SSkinMeshBuffer *tmpBuffer = AnimatedMesh->createBuffer(); @@ -331,26 +364,36 @@ bool CMS3DMeshFileLoader::load(io::IReadFile* file) } // animation time - f32 framesPerSecond = *(f32*)pPtr; + f32 framesPerSecond = *(float*)pPtr; #ifdef __BIG_ENDIAN__ framesPerSecond = os::Byteswap::byteswap(framesPerSecond); #endif - pPtr += sizeof(f32) * 2; // fps and current time + pPtr += sizeof(float) * 2; // fps and current time + if (framesPerSecond<1.f) + framesPerSecond=1.f; - if (framesPerSecond==0) - framesPerSecond=1; - - pPtr += sizeof(s32); // frameCount +// calculated inside SkinnedMesh +// s32 frameCount = *(int*)pPtr; +#ifdef __BIG_ENDIAN__ +// frameCount = os::Byteswap::byteswap(frameCount); +#endif + pPtr += sizeof(int); u16 jointCount = *(u16*)pPtr; #ifdef __BIG_ENDIAN__ jointCount = os::Byteswap::byteswap(jointCount); #endif pPtr += sizeof(u16); + if (pPtr > buffer+fileSize) + { + delete [] buffer; + os::Printer::log("Loading failed. Corrupted data found.", file->getFileName(), ELL_ERROR); + return false; + } - - core::array ParentNames; + core::array parentNames; + parentNames.reallocate(jointCount); // load joints for (i=0; iNumTranslationKeyframes = os::Byteswap::byteswap(pJoint->NumTranslationKeyframes); #endif pPtr += sizeof(MS3DJoint); + if (pPtr > buffer+fileSize) + { + delete [] buffer; + os::Printer::log("Loading failed. Corrupted data found.", file->getFileName(), ELL_ERROR); + return false; + } ISkinnedMesh::SJoint *jnt = AnimatedMesh->createJoint(); - /* - jnt.Name = pJoint->Name; - jnt.Index = i; - jnt.Rotation.X = pJoint->Rotation[0]; - jnt.Rotation.Y = pJoint->Rotation[1]; - jnt.Rotation.Z = pJoint->Rotation[2]; - jnt.Translation.X = pJoint->Translation[0]; - jnt.Translation.Y = pJoint->Translation[1]; - jnt.Translation.Z = pJoint->Translation[2]; - jnt.ParentName = pJoint->ParentName; - jnt.Parent = -1; - */ - jnt->Name = pJoint->Name; - jnt->LocalMatrix.makeIdentity(); - - jnt->LocalMatrix.setRotationRadians( core::vector3df(pJoint->Rotation[0], pJoint->Rotation[1], pJoint->Rotation[2]) ); jnt->LocalMatrix.setTranslation( core::vector3df(pJoint->Translation[0], pJoint->Translation[1], pJoint->Translation[2]) ); - ParentNames.push_back( (c8*)pJoint->ParentName ); + parentNames.push_back( (c8*)pJoint->ParentName ); /*if (pJoint->NumRotationKeyframes || pJoint->NumTranslationKeyframes) @@ -411,6 +444,12 @@ bool CMS3DMeshFileLoader::load(io::IReadFile* file) kf->Parameter[l] = os::Byteswap::byteswap(kf->Parameter[l]); #endif pPtr += sizeof(MS3DKeyframe); + if (pPtr > buffer+fileSize) + { + delete [] buffer; + os::Printer::log("Loading failed. Corrupted data found.", file->getFileName(), ELL_ERROR); + return false; + } ISkinnedMesh::SRotationKey *k=AnimatedMesh->createRotationKey(jnt); k->frame = kf->Time * framesPerSecond; @@ -436,6 +475,12 @@ bool CMS3DMeshFileLoader::load(io::IReadFile* file) kf->Parameter[l] = os::Byteswap::byteswap(kf->Parameter[l]); #endif pPtr += sizeof(MS3DKeyframe); + if (pPtr > buffer+fileSize) + { + delete [] buffer; + os::Printer::log("Loading failed. Corrupted data found.", file->getFileName(), ELL_ERROR); + return false; + } ISkinnedMesh::SPositionKey *k=AnimatedMesh->createPositionKey(jnt); k->frame = kf->Time * framesPerSecond; @@ -447,21 +492,109 @@ bool CMS3DMeshFileLoader::load(io::IReadFile* file) } } + core::array vertexWeights; + + if ((pHeader->Version == 4) && (pPtr < buffer+fileSize)) + { + s32 subVersion = *(s32*)pPtr; // comment subVersion, always 1 +#ifdef __BIG_ENDIAN__ + subVersion = os::Byteswap::byteswap(subVersion); +#endif + pPtr += sizeof(s32); + + for (u32 j=0; j<4; ++j) // four comment groups + { + u32 numComments = *(u32*)pPtr; +#ifdef __BIG_ENDIAN__ + numComments = os::Byteswap::byteswap(numComments); +#endif + pPtr += sizeof(u32); + for (i=0; i buffer+fileSize) + { + delete [] buffer; + os::Printer::log("Loading failed. Corrupted data found.", file->getFileName(), ELL_ERROR); + return false; + } + } + + if (pPtr < buffer+fileSize) + { + subVersion = *(s32*)pPtr; // vertex subVersion, 1 or 2 +#ifdef __BIG_ENDIAN__ + subVersion = os::Byteswap::byteswap(subVersion); +#endif + pPtr += sizeof(s32); + + // read vertex weights, ignoring data 'extra' from 1.8.2 + vertexWeights.reallocate(numVertices); + const char offset = (subVersion==1)?6:10; + for (i=0; i buffer+fileSize) + { + delete [] buffer; + os::Printer::log("Loading failed. Corrupted data found.", file->getFileName(), ELL_ERROR); + return false; + } + } + + if (pPtr < buffer+fileSize) + { + subVersion = *(s32*)pPtr; // joint subVersion, 1 or 2 +#ifdef __BIG_ENDIAN__ + subVersion = os::Byteswap::byteswap(subVersion); +#endif + pPtr += sizeof(s32); + // skip joint colors + pPtr += 3*sizeof(float)*jointCount; + + if (pPtr > buffer+fileSize) + { + delete [] buffer; + os::Printer::log("Loading failed. Corrupted data found", file->getFileName(), ELL_ERROR); + return false; + } + } + + if (pPtr < buffer+fileSize) + { + subVersion = *(s32*)pPtr; // model subVersion, 1 or 2 +#ifdef __BIG_ENDIAN__ + subVersion = os::Byteswap::byteswap(subVersion); +#endif + pPtr += sizeof(s32); + // now the model extra information would follow + // we also skip this for now + } + } + //find parent of every joint for (u32 jointnum=0; jointnumgetAllJoints().size(); ++jointnum) { for (u32 j2=0; j2getAllJoints().size(); ++j2) { - if (jointnum != j2 && ParentNames[jointnum] == AnimatedMesh->getAllJoints()[j2]->Name ) + if (jointnum != j2 && parentNames[jointnum] == AnimatedMesh->getAllJoints()[j2]->Name ) { AnimatedMesh->getAllJoints()[j2]->Children.push_back(AnimatedMesh->getAllJoints()[jointnum]); break; } } } - /*if (Joints[jointnum].Parent == -1) - os::Printer::log("Found joint in model without parent.", ELL_WARNING);*/ - // create vertices and indices, attach them to the joints. video::S3DVertex v; @@ -470,7 +603,7 @@ bool CMS3DMeshFileLoader::load(io::IReadFile* file) for (i=0; igetMeshBuffers()[tmp]->Vertices_Standard; for (u16 j = 0; j<3; ++j) @@ -482,8 +615,8 @@ bool CMS3DMeshFileLoader::load(io::IReadFile* file) v.Normal.Y = triangles[i].VertexNormals[j][1]; v.Normal.Z = triangles[i].VertexNormals[j][2]; - if(triangles[i].GroupIndex < Groups.size() && Groups[triangles[i].GroupIndex].MaterialIdx < AnimatedMesh->getMeshBuffers().size()) - v.Color = AnimatedMesh->getMeshBuffers()[Groups[triangles[i].GroupIndex].MaterialIdx]->Material.DiffuseColor; + if(triangles[i].GroupIndex < groups.size() && groups[triangles[i].GroupIndex].MaterialIdx < AnimatedMesh->getMeshBuffers().size()) + v.Color = AnimatedMesh->getMeshBuffers()[groups[triangles[i].GroupIndex].MaterialIdx]->Material.DiffuseColor; else v.Color.set(255,255,255,255); v.Pos.X = vertices[triangles[i].VertexIndices[j]].Vertex[0]; @@ -503,20 +636,67 @@ bool CMS3DMeshFileLoader::load(io::IReadFile* file) if (index == -1) { - s32 boneid = vertices[triangles[i].VertexIndices[j]].BoneID; - if (boneid>=0 && boneid<(s32)AnimatedMesh->getAllJoints().size()) + index = Vertices->size(); + const u32 vertidx = triangles[i].VertexIndices[j]; + const u32 matidx = groups[triangles[i].GroupIndex].MaterialIdx; + if (vertexWeights.size()==0) { - ISkinnedMesh::SWeight *w=AnimatedMesh->createWeight(AnimatedMesh->getAllJoints()[boneid]); - w->buffer_id = Groups[triangles[i].GroupIndex].MaterialIdx; - w->strength = 1.0f; - w->vertex_id = Vertices->size(); - //Joints[boneid]->VertexIds.push_back(Vertices.size()); - - + const s32 boneid = vertices[vertidx].BoneID; + if ((u32)boneid < AnimatedMesh->getAllJoints().size()) + { + ISkinnedMesh::SWeight *w=AnimatedMesh->createWeight(AnimatedMesh->getAllJoints()[boneid]); + w->buffer_id = matidx; + w->strength = 1.0f; + w->vertex_id = index; + } + } + else // new weights from 1.8.x + { + f32 sum = 1.0f; + s32 boneid = vertices[vertidx].BoneID; + if (((u32)boneid < AnimatedMesh->getAllJoints().size()) && (vertexWeights[vertidx].weights[0] != 0)) + { + ISkinnedMesh::SWeight *w=AnimatedMesh->createWeight(AnimatedMesh->getAllJoints()[boneid]); + w->buffer_id = matidx; + sum -= (w->strength = vertexWeights[vertidx].weights[0]/100.f); + w->vertex_id = index; + } + boneid = vertexWeights[vertidx].boneIds[0]; + if (((u32)boneid < AnimatedMesh->getAllJoints().size()) && (vertexWeights[vertidx].weights[1] != 0)) + { + ISkinnedMesh::SWeight *w=AnimatedMesh->createWeight(AnimatedMesh->getAllJoints()[boneid]); + w->buffer_id = matidx; + sum -= (w->strength = vertexWeights[vertidx].weights[1]/100.f); + w->vertex_id = index; + } + boneid = vertexWeights[vertidx].boneIds[1]; + if (((u32)boneid < AnimatedMesh->getAllJoints().size()) && (vertexWeights[vertidx].weights[2] != 0)) + { + ISkinnedMesh::SWeight *w=AnimatedMesh->createWeight(AnimatedMesh->getAllJoints()[boneid]); + w->buffer_id = matidx; + sum -= (w->strength = vertexWeights[vertidx].weights[2]/100.f); + w->vertex_id = index; + } + boneid = vertexWeights[vertidx].boneIds[2]; + if (((u32)boneid < AnimatedMesh->getAllJoints().size()) && (sum > 0.f)) + { + ISkinnedMesh::SWeight *w=AnimatedMesh->createWeight(AnimatedMesh->getAllJoints()[boneid]); + w->buffer_id = matidx; + w->strength = sum; + w->vertex_id = index; + } + // fallback, if no bone chosen. Seems to be an error in the specs + boneid = vertices[vertidx].BoneID; + if ((sum == 1.f) && ((u32)boneid < AnimatedMesh->getAllJoints().size())) + { + ISkinnedMesh::SWeight *w=AnimatedMesh->createWeight(AnimatedMesh->getAllJoints()[boneid]); + w->buffer_id = matidx; + w->strength = 1.f; + w->vertex_id = index; + } } Vertices->push_back(v); - index = Vertices->size() - 1; } Indices.push_back(index); } @@ -524,9 +704,9 @@ bool CMS3DMeshFileLoader::load(io::IReadFile* file) //create groups s32 iIndex = -1; - for (i=0; i= AnimatedMesh->getMeshBuffers().size()) grp.MaterialIdx = 0; @@ -538,31 +718,7 @@ bool CMS3DMeshFileLoader::load(io::IReadFile* file) indices.push_back(Indices[++iIndex]); } - // calculate bounding box -/* - // inverse translate and rotate all vertices for making animation easier - if (HasAnimation) - for (i=0; i VertexIds; - u16 MaterialIdx; - }; - - core::array Groups; - }; } // end namespace scene diff --git a/source/Irrlicht/COSOperator.cpp b/source/Irrlicht/COSOperator.cpp index 8699fac6..6c2e2818 100644 --- a/source/Irrlicht/COSOperator.cpp +++ b/source/Irrlicht/COSOperator.cpp @@ -10,7 +10,7 @@ #else #include #include -#ifdef MACOSX +#ifdef _IRR_USE_OSX_DEVICE_ #include "OSXClipboard.h" #include #include @@ -59,9 +59,10 @@ void COSOperator::copyToClipboard(const c8* text) const CloseClipboard(); // MacOSX version -#elif defined(MACOSX) +#elif defined(_IRR_USE_OSX_DEVICE_) OSXCopyToClipboard(text); +#else // todo: Linux version #endif @@ -84,7 +85,7 @@ c8* COSOperator::getTextFromClipboard() const CloseClipboard(); return buffer; -#elif defined(MACOSX) +#elif defined(_IRR_USE_OSX_DEVICE_) return (OSXCopyFromClipboard()); #else @@ -121,7 +122,7 @@ bool COSOperator::getProcessorSpeedMHz(u32* MHz) const _IRR_IMPLEMENT_MANAGED_MARSHALLING_BUGFIX; return true; -#elif defined(MACOSX) +#elif defined(_IRR_OSX_PLATFORM_) struct clockinfo CpuClock; size_t Size = sizeof(clockinfo); diff --git a/source/Irrlicht/COpenGLDriver.cpp b/source/Irrlicht/COpenGLDriver.cpp index fde26726..c2dde8bb 100644 --- a/source/Irrlicht/COpenGLDriver.cpp +++ b/source/Irrlicht/COpenGLDriver.cpp @@ -156,9 +156,9 @@ bool COpenGLDriver::initDriver(const core::dimension2d& screenSize, #endif //IRR_USE_WINDOWS_DEVICE_ // ----------------------------------------------------------------------- -// MACOSX CONSTRUCTOR +// MacOSX CONSTRUCTOR // ----------------------------------------------------------------------- -#ifdef MACOSX +#ifdef _IRR_USE_OSX_DEVICE_ //! Windows constructor and init code COpenGLDriver::COpenGLDriver(const core::dimension2d& screenSize, bool fullscreen, bool stencilBuffer, CIrrDeviceMacOSX *device, io::IFileSystem* io, bool vsync, bool antiAlias) : CNullDriver(io, screenSize), COpenGLExtensionHandler(), @@ -400,7 +400,7 @@ bool COpenGLDriver::endScene( s32 windowId, core::rect* sourceRect ) #elif defined(_IRR_USE_LINUX_DEVICE_) glXSwapBuffers(XDisplay, XWindow); return true; -#elif defined(MACOSX) +#elif defined(_IRR_USE_OSX_DEVICE_) _device->flush(); return true; #elif defined(_IRR_USE_SDL_DEVICE_) @@ -2661,7 +2661,7 @@ IVideoDriver* createOpenGLDriver(const core::dimension2d& screenSize, // ----------------------------------- // MACOSX VERSION // ----------------------------------- -#ifdef MACOSX +#if defined(_IRR_USE_OSX_DEVICE_) IVideoDriver* createOpenGLDriver(const core::dimension2d& screenSize, CIrrDeviceMacOSX *device, bool fullscreen, bool stencilBuffer, io::IFileSystem* io, bool vsync, bool antiAlias) @@ -2673,7 +2673,7 @@ IVideoDriver* createOpenGLDriver(const core::dimension2d& screenSize, return 0; #endif // _IRR_COMPILE_WITH_OPENGL_ } -#endif // MACOSX +#endif // _IRR_USE_OSX_DEVICE_ // ----------------------------------- // LINUX VERSION diff --git a/source/Irrlicht/COpenGLDriver.h b/source/Irrlicht/COpenGLDriver.h index cc9f2ced..0d5f930a 100644 --- a/source/Irrlicht/COpenGLDriver.h +++ b/source/Irrlicht/COpenGLDriver.h @@ -22,7 +22,7 @@ #pragma comment(lib, "OpenGL32.lib") #pragma comment(lib, "GLu32.lib") #endif -#elif defined(MACOSX) +#elif defined(_IRR_USE_OSX_DEVICE_) #include "CIrrDeviceMacOSX.h" #if defined(_IRR_OPENGL_USE_EXTPOINTER_) #define GL_GLEXT_LEGACY 1 @@ -84,7 +84,7 @@ namespace video bool stencilBuffer, io::IFileSystem* io, bool vsync, bool antiAlias); #endif - #ifdef MACOSX + #ifdef _IRR_USE_OSX_DEVICE_ COpenGLDriver(const core::dimension2d& screenSize, bool fullscreen, bool stencilBuffer, CIrrDeviceMacOSX *device,io::IFileSystem* io, bool vsync, bool antiAlias); #endif @@ -388,7 +388,7 @@ namespace video #elif defined(_IRR_USE_LINUX_DEVICE_) GLXDrawable XWindow; Display* XDisplay; - #elif defined(MACOSX) + #elif defined(_IRR_USE_OSX_DEVICE_) CIrrDeviceMacOSX *_device; #endif }; diff --git a/source/Irrlicht/COpenGLExtensionHandler.h b/source/Irrlicht/COpenGLExtensionHandler.h index 31030225..ec95790a 100644 --- a/source/Irrlicht/COpenGLExtensionHandler.h +++ b/source/Irrlicht/COpenGLExtensionHandler.h @@ -21,7 +21,7 @@ #ifdef _MSC_VER #pragma comment(lib, "OpenGL32.lib") #endif -#elif defined(MACOSX) +#elif defined(_IRR_USE_OSX_DEVICE_) #include "CIrrDeviceMacOSX.h" #if defined(_IRR_OPENGL_USE_EXTPOINTER_) #define GL_GLEXT_LEGACY 1 diff --git a/source/Irrlicht/COpenGLMaterialRenderer.h b/source/Irrlicht/COpenGLMaterialRenderer.h index b323c716..c4d6703b 100644 --- a/source/Irrlicht/COpenGLMaterialRenderer.h +++ b/source/Irrlicht/COpenGLMaterialRenderer.h @@ -1,719 +1,716 @@ -// Copyright (C) 2002-2007 Nikolaus Gebhardt -// This file is part of the "Irrlicht Engine". -// For conditions of distribution and use, see copyright notice in irrlicht.h - -#ifndef __C_OPENGL_MATERIAL_RENDERER_H_INCLUDED__ -#define __C_OPENGL_MATERIAL_RENDERER_H_INCLUDED__ - -#include "IrrCompileConfig.h" -#ifdef _IRR_COMPILE_WITH_OPENGL_ - -#include "COpenGLDriver.h" -#include "IMaterialRenderer.h" - -//Varmint: 2007/12/18 -#ifdef MACOSX - #define GL_COMBINE_EXT 0x8570 - #define GL_COMBINE_RGB_EXT 0x8571 - #define GL_COMBINE_ALPHA_EXT 0x8572 - #define GL_RGB_SCALE_EXT 0x8573 - #define GL_ADD_SIGNED_EXT 0x8574 - #define GL_INTERPOLATE_EXT 0x8575 - #define GL_CONSTANT_EXT 0x8576 - #define GL_PRIMARY_COLOR_EXT 0x8577 - #define GL_PREVIOUS_EXT 0x8578 - #define GL_SOURCE0_RGB_EXT 0x8580 - #define GL_SOURCE1_RGB_EXT 0x8581 - #define GL_SOURCE2_RGB_EXT 0x8582 - #define GL_SOURCE3_RGB_EXT 0x8583 - #define GL_SOURCE4_RGB_EXT 0x8584 - #define GL_SOURCE5_RGB_EXT 0x8585 - #define GL_SOURCE6_RGB_EXT 0x8586 - #define GL_SOURCE7_RGB_EXT 0x8587 - #define GL_SOURCE0_ALPHA_EXT 0x8588 - #define GL_SOURCE1_ALPHA_EXT 0x8589 - #define GL_SOURCE2_ALPHA_EXT 0x858A - #define GL_SOURCE3_ALPHA_EXT 0x858B - #define GL_SOURCE4_ALPHA_EXT 0x858C - #define GL_SOURCE5_ALPHA_EXT 0x858D - #define GL_SOURCE6_ALPHA_EXT 0x858E - #define GL_SOURCE7_ALPHA_EXT 0x858F - #define GL_OPERAND0_RGB_EXT 0x8590 - #define GL_OPERAND1_RGB_EXT 0x8591 - #define GL_OPERAND2_RGB_EXT 0x8592 - #define GL_OPERAND3_RGB_EXT 0x8593 - #define GL_OPERAND4_RGB_EXT 0x8594 - #define GL_OPERAND5_RGB_EXT 0x8595 - #define GL_OPERAND6_RGB_EXT 0x8596 - #define GL_OPERAND7_RGB_EXT 0x8597 - #define GL_OPERAND0_ALPHA_EXT 0x8598 - #define GL_OPERAND1_ALPHA_EXT 0x8599 - #define GL_OPERAND2_ALPHA_EXT 0x859A - #define GL_OPERAND3_ALPHA_EXT 0x859B - #define GL_OPERAND4_ALPHA_EXT 0x859C - #define GL_OPERAND5_ALPHA_EXT 0x859D - #define GL_OPERAND6_ALPHA_EXT 0x859E - #define GL_OPERAND7_ALPHA_EXT 0x859F -#endif - -namespace irr -{ -namespace video -{ - -//! Base class for all internal OpenGL material renderers -class COpenGLMaterialRenderer : public IMaterialRenderer -{ -public: - - //! Constructor - COpenGLMaterialRenderer(video::COpenGLDriver* driver) : Driver(driver) - { - } - -protected: - - video::COpenGLDriver* Driver; -}; - - -//! Solid material renderer -class COpenGLMaterialRenderer_SOLID : public COpenGLMaterialRenderer -{ -public: - - COpenGLMaterialRenderer_SOLID(video::COpenGLDriver* d) - : COpenGLMaterialRenderer(d) {} - - virtual void OnSetMaterial(const SMaterial& material, const SMaterial& lastMaterial, - bool resetAllRenderstates, IMaterialRendererServices* services) - { - Driver->disableTextures(1); - Driver->setTexture(0, material.getTexture(0)); - Driver->setBasicRenderStates(material, lastMaterial, resetAllRenderstates); - - if (material.MaterialType != lastMaterial.MaterialType || resetAllRenderstates) - { - // thanks to Murphy, the following line removed some - // bugs with several OpenGL implementations. - glTexEnvi(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_MODULATE); - } - } -}; - - -//! Generic Texture Blend -class COpenGLMaterialRenderer_ONETEXTURE_BLEND : public COpenGLMaterialRenderer -{ -public: - - COpenGLMaterialRenderer_ONETEXTURE_BLEND(video::COpenGLDriver* d) - : COpenGLMaterialRenderer(d) {} - - virtual void OnSetMaterial(const SMaterial& material, const SMaterial& lastMaterial, - bool resetAllRenderstates, IMaterialRendererServices* services) - { - Driver->disableTextures(1); - Driver->setTexture(0, material.getTexture(0)); - Driver->setBasicRenderStates(material, lastMaterial, resetAllRenderstates); - -// if (material.MaterialType != lastMaterial.MaterialType || -// material.MaterialTypeParam != lastMaterial.MaterialTypeParam || -// resetAllRenderstates) - { - E_BLEND_FACTOR srcFact,dstFact; - E_MODULATE_FUNC modulate; - unpack_texureBlendFunc ( srcFact, dstFact, modulate, material.MaterialTypeParam ); - - glTexEnvf(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_COMBINE_EXT); - glTexEnvf(GL_TEXTURE_ENV, GL_COMBINE_RGB_EXT, GL_MODULATE); - glTexEnvf(GL_TEXTURE_ENV, GL_SOURCE0_RGB_EXT, GL_TEXTURE); - glTexEnvf(GL_TEXTURE_ENV, GL_SOURCE1_RGB_EXT, GL_PREVIOUS_EXT); - - glTexEnvf(GL_TEXTURE_ENV, GL_RGB_SCALE_EXT, (f32) modulate ); - - glBlendFunc( getGLBlend(srcFact), getGLBlend(dstFact) ); - glEnable(GL_ALPHA_TEST); - glEnable(GL_BLEND); - - if ( getTexelAlpha ( srcFact ) + getTexelAlpha ( dstFact ) ) - { - glTexEnvf(GL_TEXTURE_ENV, GL_COMBINE_ALPHA_EXT, GL_REPLACE); - glTexEnvf(GL_TEXTURE_ENV, GL_SOURCE0_ALPHA_EXT, GL_TEXTURE); - - glTexEnvf(GL_TEXTURE_ENV, GL_SOURCE1_RGB_EXT, GL_PRIMARY_COLOR_EXT); - } - } - } - - virtual void OnUnsetMaterial() - { - glTexEnvf(GL_TEXTURE_ENV, GL_RGB_SCALE_EXT, 1.f ); - glTexEnvf(GL_TEXTURE_ENV, GL_SOURCE1_RGB_EXT, GL_PREVIOUS_EXT); - - glDisable(GL_BLEND); - glDisable(GL_ALPHA_TEST); - } - - private: - - u32 getGLBlend ( E_BLEND_FACTOR factor ) const - { - u32 r = 0; - switch ( factor ) - { - case EBF_ZERO: r = GL_ZERO; break; - case EBF_ONE: r = GL_ONE; break; - case EBF_DST_COLOR: r = GL_DST_COLOR; break; - case EBF_ONE_MINUS_DST_COLOR: r = GL_ONE_MINUS_DST_COLOR; break; - case EBF_SRC_COLOR: r = GL_SRC_COLOR; break; - case EBF_ONE_MINUS_SRC_COLOR: r = GL_ONE_MINUS_SRC_COLOR; break; - case EBF_SRC_ALPHA: r = GL_SRC_ALPHA; break; - case EBF_ONE_MINUS_SRC_ALPHA: r = GL_ONE_MINUS_SRC_ALPHA; break; - case EBF_DST_ALPHA: r = GL_DST_ALPHA; break; - case EBF_ONE_MINUS_DST_ALPHA: r = GL_ONE_MINUS_DST_ALPHA; break; - case EBF_SRC_ALPHA_SATURATE: r = GL_SRC_ALPHA_SATURATE; break; - } - return r; - } - - u32 getTexelAlpha ( E_BLEND_FACTOR factor ) const - { - u32 r; - switch ( factor ) - { - case EBF_SRC_ALPHA: r = 1; break; - case EBF_ONE_MINUS_SRC_ALPHA: r = 1; break; - case EBF_DST_ALPHA: r = 1; break; - case EBF_ONE_MINUS_DST_ALPHA: r = 1; break; - case EBF_SRC_ALPHA_SATURATE: r = 1; break; - default: r = 0; break; - } - return r; - } -}; - - -//! Solid 2 layer material renderer -class COpenGLMaterialRenderer_SOLID_2_LAYER : public COpenGLMaterialRenderer -{ -public: - - COpenGLMaterialRenderer_SOLID_2_LAYER(video::COpenGLDriver* d) - : COpenGLMaterialRenderer(d) {} - - virtual void OnSetMaterial(const SMaterial& material, const SMaterial& lastMaterial, - bool resetAllRenderstates, IMaterialRendererServices* services) - { - Driver->disableTextures(2); - Driver->setTexture(1, material.getTexture(1)); - Driver->setTexture(0, material.getTexture(0)); - Driver->setBasicRenderStates(material, lastMaterial, resetAllRenderstates); - - if (material.MaterialType != lastMaterial.MaterialType || resetAllRenderstates) - { - if (Driver->queryFeature(EVDF_MULTITEXTURE)) - { - Driver->extGlActiveTexture(GL_TEXTURE1_ARB); - glTexEnvi(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_REPLACE); - - Driver->extGlActiveTexture(GL_TEXTURE0_ARB); - } - - glTexEnvi(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_MODULATE); - } - } -}; - - -//! Transparent add color material renderer -class COpenGLMaterialRenderer_TRANSPARENT_ADD_COLOR : public COpenGLMaterialRenderer -{ -public: - - COpenGLMaterialRenderer_TRANSPARENT_ADD_COLOR(video::COpenGLDriver* d) - : COpenGLMaterialRenderer(d) {} - - virtual void OnSetMaterial(const SMaterial& material, const SMaterial& lastMaterial, - bool resetAllRenderstates, IMaterialRendererServices* services) - { - Driver->disableTextures(1); - Driver->setTexture(0, material.getTexture(0)); - Driver->setBasicRenderStates(material, lastMaterial, resetAllRenderstates); - - if ((material.MaterialType != lastMaterial.MaterialType) || resetAllRenderstates) - { - glBlendFunc(GL_ONE, GL_ONE_MINUS_SRC_COLOR); - glTexEnvi(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_MODULATE); - glEnable(GL_BLEND); - } - } - - virtual void OnUnsetMaterial() - { - glDisable(GL_BLEND); - } - - //! Returns if the material is transparent. - virtual bool isTransparent() const - { - return true; - } -}; - - -//! Transparent vertex alpha material renderer -class COpenGLMaterialRenderer_TRANSPARENT_VERTEX_ALPHA : public COpenGLMaterialRenderer -{ -public: - - COpenGLMaterialRenderer_TRANSPARENT_VERTEX_ALPHA(video::COpenGLDriver* d) - : COpenGLMaterialRenderer(d) {} - - virtual void OnSetMaterial(const SMaterial& material, const SMaterial& lastMaterial, - bool resetAllRenderstates, IMaterialRendererServices* services) - { - Driver->disableTextures(1); - Driver->setTexture(0, material.getTexture(0)); - Driver->setBasicRenderStates(material, lastMaterial, resetAllRenderstates); - - if (material.MaterialType != lastMaterial.MaterialType || resetAllRenderstates) - { - glTexEnvf(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_COMBINE_EXT); - - glTexEnvf(GL_TEXTURE_ENV, GL_COMBINE_ALPHA_EXT, GL_REPLACE); - glTexEnvf(GL_TEXTURE_ENV, GL_SOURCE0_ALPHA_EXT, GL_PRIMARY_COLOR_EXT ); - - glTexEnvf(GL_TEXTURE_ENV, GL_COMBINE_RGB_EXT, GL_MODULATE); - glTexEnvf(GL_TEXTURE_ENV, GL_SOURCE0_RGB_EXT, GL_PRIMARY_COLOR_EXT ); - glTexEnvf(GL_TEXTURE_ENV, GL_SOURCE1_RGB_EXT, GL_TEXTURE); - - glBlendFunc(GL_ONE, GL_ONE_MINUS_SRC_ALPHA); - glEnable(GL_BLEND); - } - glDepthMask(GL_FALSE); - } - - virtual void OnUnsetMaterial() - { - // default values - glTexEnvi(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_COMBINE_EXT); - glTexEnvf(GL_TEXTURE_ENV, GL_COMBINE_ALPHA_EXT, GL_MODULATE ); - glTexEnvf(GL_TEXTURE_ENV, GL_SOURCE0_ALPHA_EXT, GL_TEXTURE ); - glTexEnvf(GL_TEXTURE_ENV, GL_SOURCE1_ALPHA_EXT, GL_PREVIOUS_EXT ); - glTexEnvf(GL_TEXTURE_ENV, GL_COMBINE_RGB_EXT, GL_MODULATE); - glTexEnvf(GL_TEXTURE_ENV, GL_SOURCE0_RGB_EXT, GL_TEXTURE ); - glTexEnvf(GL_TEXTURE_ENV, GL_SOURCE1_RGB_EXT, GL_PREVIOUS_EXT); - - glDisable(GL_BLEND); - } - - //! Returns if the material is transparent. - virtual bool isTransparent() const - { - return true; - } -}; - - -//! Transparent alpha channel material renderer -class COpenGLMaterialRenderer_TRANSPARENT_ALPHA_CHANNEL : public COpenGLMaterialRenderer -{ -public: - - COpenGLMaterialRenderer_TRANSPARENT_ALPHA_CHANNEL(video::COpenGLDriver* d) - : COpenGLMaterialRenderer(d) {} - - virtual void OnSetMaterial(const SMaterial& material, const SMaterial& lastMaterial, - bool resetAllRenderstates, IMaterialRendererServices* services) - { - Driver->disableTextures(1); - Driver->setTexture(0, material.getTexture(0)); - Driver->setBasicRenderStates(material, lastMaterial, resetAllRenderstates); - - if (material.MaterialType != lastMaterial.MaterialType || resetAllRenderstates - || material.MaterialTypeParam != lastMaterial.MaterialTypeParam ) - { - glTexEnvf(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_COMBINE_EXT); - glTexEnvf(GL_TEXTURE_ENV, GL_COMBINE_RGB_EXT, GL_MODULATE); - glTexEnvf(GL_TEXTURE_ENV, GL_SOURCE0_RGB_EXT, GL_TEXTURE); - glTexEnvf(GL_TEXTURE_ENV, GL_SOURCE1_RGB_EXT, GL_PREVIOUS_EXT); - - glTexEnvf(GL_TEXTURE_ENV, GL_COMBINE_ALPHA_EXT, GL_REPLACE); - glTexEnvf(GL_TEXTURE_ENV, GL_SOURCE0_ALPHA_EXT, GL_TEXTURE); - - glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA); - glEnable(GL_BLEND); - glEnable(GL_ALPHA_TEST); - - f32 refValue = material.MaterialTypeParam; - if ( refValue == 0.0f ) - refValue = 0.5f; - - glAlphaFunc(GL_GREATER, refValue); - } - } - - virtual void OnUnsetMaterial() - { - glDisable(GL_ALPHA_TEST); - glDisable(GL_BLEND); - } - - //! Returns if the material is transparent. - virtual bool isTransparent() const - { - return true; - } -}; - - - -//! Transparent alpha channel material renderer -class COpenGLMaterialRenderer_TRANSPARENT_ALPHA_CHANNEL_REF : public COpenGLMaterialRenderer -{ -public: - - COpenGLMaterialRenderer_TRANSPARENT_ALPHA_CHANNEL_REF(video::COpenGLDriver* d) - : COpenGLMaterialRenderer(d) {} - - virtual void OnSetMaterial(const SMaterial& material, const SMaterial& lastMaterial, - bool resetAllRenderstates, IMaterialRendererServices* services) - { - Driver->disableTextures(1); - Driver->setTexture(0, material.getTexture(0)); - Driver->setBasicRenderStates(material, lastMaterial, resetAllRenderstates); - - if (material.MaterialType != lastMaterial.MaterialType || resetAllRenderstates) - { - glEnable(GL_ALPHA_TEST); - glAlphaFunc(GL_GREATER, 0.5); - glTexEnvi(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_REPLACE); - } - } - - virtual void OnUnsetMaterial() - { - glDisable(GL_ALPHA_TEST); - } - - //! Returns if the material is transparent. - virtual bool isTransparent() const - { - return false; // this material is not really transparent because it does no blending. - } -}; - - -//! material renderer for all kinds of lightmaps -class COpenGLMaterialRenderer_LIGHTMAP : public COpenGLMaterialRenderer -{ -public: - - COpenGLMaterialRenderer_LIGHTMAP(video::COpenGLDriver* d) - : COpenGLMaterialRenderer(d) {} - - virtual void OnSetMaterial(const SMaterial& material, const SMaterial& lastMaterial, - bool resetAllRenderstates, IMaterialRendererServices* services) - { - Driver->disableTextures(2); - Driver->setTexture(1, material.getTexture(1)); - Driver->setTexture(0, material.getTexture(0)); - Driver->setBasicRenderStates(material, lastMaterial, resetAllRenderstates); - - if (material.MaterialType != lastMaterial.MaterialType || resetAllRenderstates) - { - // diffuse map - - glTexEnvi(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_COMBINE_EXT); - switch (material.MaterialType) - { - case EMT_LIGHTMAP_LIGHTING: - case EMT_LIGHTMAP_LIGHTING_M2: - case EMT_LIGHTMAP_LIGHTING_M4: - glTexEnvi(GL_TEXTURE_ENV, GL_COMBINE_RGB_EXT, GL_MODULATE); - break; - case EMT_LIGHTMAP_ADD: - case EMT_LIGHTMAP: - case EMT_LIGHTMAP_M2: - case EMT_LIGHTMAP_M4: - default: - glTexEnvi(GL_TEXTURE_ENV, GL_COMBINE_RGB_EXT, GL_REPLACE); - break; - } - glTexEnvf(GL_TEXTURE_ENV, GL_SOURCE0_RGB_EXT, GL_TEXTURE); - glTexEnvi(GL_TEXTURE_ENV, GL_OPERAND0_RGB_EXT, GL_SRC_COLOR); - glTexEnvf(GL_TEXTURE_ENV, GL_SOURCE1_RGB_EXT, GL_PREVIOUS_EXT); - glTexEnvi(GL_TEXTURE_ENV, GL_OPERAND1_RGB_EXT, GL_SRC_COLOR ); - - if (Driver->queryFeature(EVDF_MULTITEXTURE)) - { - // lightmap - - Driver->extGlActiveTexture(GL_TEXTURE1_ARB); - glTexEnvi(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_COMBINE_EXT); - - if (material.MaterialType == EMT_LIGHTMAP_ADD) - glTexEnvi(GL_TEXTURE_ENV, GL_COMBINE_RGB_EXT, GL_ADD_SIGNED_ARB); - else - glTexEnvi(GL_TEXTURE_ENV, GL_COMBINE_RGB_EXT, GL_MODULATE); - - glTexEnvi(GL_TEXTURE_ENV, GL_SOURCE0_RGB_EXT, GL_PREVIOUS_EXT); - glTexEnvi(GL_TEXTURE_ENV, GL_OPERAND0_RGB_EXT, GL_SRC_COLOR); - glTexEnvi(GL_TEXTURE_ENV, GL_SOURCE1_RGB_EXT, GL_TEXTURE); - glTexEnvi(GL_TEXTURE_ENV, GL_OPERAND1_RGB_EXT, GL_SRC_COLOR); - - glTexEnvf(GL_TEXTURE_ENV, GL_COMBINE_ALPHA_EXT, GL_MODULATE); - glTexEnvi(GL_TEXTURE_ENV, GL_SOURCE0_ALPHA_EXT, GL_PREVIOUS_ARB); - glTexEnvi(GL_TEXTURE_ENV, GL_OPERAND0_ALPHA_EXT, GL_SRC_ALPHA); - glTexEnvi(GL_TEXTURE_ENV, GL_SOURCE1_ALPHA_EXT, GL_PREVIOUS_ARB); - glTexEnvi(GL_TEXTURE_ENV, GL_OPERAND1_ALPHA_EXT, GL_SRC_ALPHA); - - switch (material.MaterialType) - { - case EMT_LIGHTMAP_M4: - case EMT_LIGHTMAP_LIGHTING_M4: - glTexEnvf(GL_TEXTURE_ENV, GL_RGB_SCALE_EXT, 4.0f); - break; - case EMT_LIGHTMAP_M2: - case EMT_LIGHTMAP_LIGHTING_M2: - glTexEnvf(GL_TEXTURE_ENV, GL_RGB_SCALE_EXT, 2.0f); - break; - default: - glTexEnvf(GL_TEXTURE_ENV, GL_RGB_SCALE_EXT, 1.0f); - } - } - } - } - - virtual void OnUnsetMaterial() - { - if (Driver->queryFeature(EVDF_MULTITEXTURE)) - { - Driver->extGlActiveTexture(GL_TEXTURE1_ARB); - glTexEnvi(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_MODULATE); - glTexEnvf(GL_TEXTURE_ENV, GL_RGB_SCALE_EXT, 1.f ); - Driver->extGlActiveTexture(GL_TEXTURE0_ARB); - } - glTexEnvi(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_MODULATE); - } -}; - - - -//! detail map material renderer -class COpenGLMaterialRenderer_DETAIL_MAP : public COpenGLMaterialRenderer -{ -public: - - COpenGLMaterialRenderer_DETAIL_MAP(video::COpenGLDriver* d) - : COpenGLMaterialRenderer(d) {} - - virtual void OnSetMaterial(const SMaterial& material, const SMaterial& lastMaterial, - bool resetAllRenderstates, IMaterialRendererServices* services) - { - Driver->disableTextures(2); - Driver->setTexture(1, material.getTexture(1)); - Driver->setTexture(0, material.getTexture(0)); - Driver->setBasicRenderStates(material, lastMaterial, resetAllRenderstates); - - if (material.MaterialType != lastMaterial.MaterialType || resetAllRenderstates) - { - // diffuse map - - glTexEnvi(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_COMBINE_EXT); - glTexEnvi(GL_TEXTURE_ENV, GL_COMBINE_RGB_EXT, GL_MODULATE); - - if (Driver->queryFeature(EVDF_MULTITEXTURE)) - { - // detail map - - Driver->extGlActiveTexture(GL_TEXTURE1_ARB); - - glTexEnvi(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_COMBINE_EXT); - glTexEnvi(GL_TEXTURE_ENV, GL_COMBINE_RGB_EXT, GL_ADD_SIGNED_EXT); - - glTexEnvi(GL_TEXTURE_ENV,GL_SOURCE0_RGB_EXT,GL_PREVIOUS_EXT); - glTexEnvi(GL_TEXTURE_ENV,GL_OPERAND0_RGB_EXT,GL_SRC_COLOR); - - glTexEnvi(GL_TEXTURE_ENV,GL_SOURCE1_RGB_EXT, GL_TEXTURE); - glTexEnvi(GL_TEXTURE_ENV,GL_OPERAND1_RGB_EXT,GL_SRC_COLOR); - Driver->extGlActiveTexture(GL_TEXTURE0_ARB); - } - } - } -}; - - -//! sphere map material renderer -class COpenGLMaterialRenderer_SPHERE_MAP : public COpenGLMaterialRenderer -{ -public: - - COpenGLMaterialRenderer_SPHERE_MAP(video::COpenGLDriver* d) - : COpenGLMaterialRenderer(d) {} - - virtual void OnSetMaterial(const SMaterial& material, const SMaterial& lastMaterial, - bool resetAllRenderstates, IMaterialRendererServices* services) - { - Driver->disableTextures(1); - Driver->setTexture(0, material.getTexture(0)); - Driver->setBasicRenderStates(material, lastMaterial, resetAllRenderstates); - - if (material.MaterialType != lastMaterial.MaterialType || resetAllRenderstates) - { - glTexEnvi(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_MODULATE); - - glTexGeni(GL_S, GL_TEXTURE_GEN_MODE, GL_SPHERE_MAP); - glTexGeni(GL_T, GL_TEXTURE_GEN_MODE, GL_SPHERE_MAP); - - glEnable(GL_TEXTURE_GEN_S); - glEnable(GL_TEXTURE_GEN_T); - } - } - - virtual void OnUnsetMaterial() - { - glDisable(GL_TEXTURE_GEN_S); - glDisable(GL_TEXTURE_GEN_T); - } -}; - - -//! reflection 2 layer material renderer -class COpenGLMaterialRenderer_REFLECTION_2_LAYER : public COpenGLMaterialRenderer -{ -public: - - COpenGLMaterialRenderer_REFLECTION_2_LAYER(video::COpenGLDriver* d) - : COpenGLMaterialRenderer(d) {} - - virtual void OnSetMaterial(const SMaterial& material, const SMaterial& lastMaterial, - bool resetAllRenderstates, IMaterialRendererServices* services) - { - Driver->disableTextures(2); - Driver->setTexture(1, material.getTexture(1)); - Driver->setTexture(0, material.getTexture(0)); - Driver->setBasicRenderStates(material, lastMaterial, resetAllRenderstates); - - if (material.MaterialType != lastMaterial.MaterialType || resetAllRenderstates) - { - if (Driver->queryFeature(EVDF_MULTITEXTURE)) - { - glTexEnvi(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_COMBINE_EXT); - glTexEnvi(GL_TEXTURE_ENV, GL_COMBINE_RGB_EXT, GL_MODULATE); - glTexEnvf(GL_TEXTURE_ENV, GL_SOURCE0_RGB_EXT, GL_TEXTURE ); - glTexEnvf(GL_TEXTURE_ENV, GL_SOURCE1_RGB_EXT, GL_PRIMARY_COLOR_EXT ); - - Driver->extGlActiveTexture(GL_TEXTURE1_ARB); - - glTexEnvi(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_COMBINE_EXT); - - glTexEnvi(GL_TEXTURE_ENV, GL_COMBINE_RGB_EXT, GL_MODULATE); - glTexEnvi(GL_TEXTURE_ENV, GL_SOURCE0_RGB_EXT, GL_PREVIOUS_EXT); - glTexEnvi(GL_TEXTURE_ENV, GL_OPERAND0_RGB_EXT, GL_SRC_COLOR); - glTexEnvi(GL_TEXTURE_ENV, GL_SOURCE1_RGB_EXT, GL_TEXTURE); - glTexEnvi(GL_TEXTURE_ENV, GL_OPERAND1_RGB_EXT, GL_SRC_COLOR); - - } - glTexGeni(GL_S, GL_TEXTURE_GEN_MODE, GL_SPHERE_MAP); - glTexGeni(GL_T, GL_TEXTURE_GEN_MODE, GL_SPHERE_MAP); - glEnable(GL_TEXTURE_GEN_S); - glEnable(GL_TEXTURE_GEN_T); - } - } - - virtual void OnUnsetMaterial() - { - if (Driver->queryFeature(EVDF_MULTITEXTURE)) - { - Driver->extGlActiveTexture(GL_TEXTURE1_ARB); - glTexEnvi(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_MODULATE); - } - glDisable(GL_TEXTURE_GEN_S); - glDisable(GL_TEXTURE_GEN_T); - if (Driver->queryFeature(EVDF_MULTITEXTURE)) - { - Driver->extGlActiveTexture(GL_TEXTURE0_ARB); - - glTexEnvi(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_MODULATE); - } - } -}; - - -//! reflection 2 layer material renderer -class COpenGLMaterialRenderer_TRANSPARENT_REFLECTION_2_LAYER : public COpenGLMaterialRenderer -{ -public: - - COpenGLMaterialRenderer_TRANSPARENT_REFLECTION_2_LAYER(video::COpenGLDriver* d) - : COpenGLMaterialRenderer(d) {} - - virtual void OnSetMaterial(const SMaterial& material, const SMaterial& lastMaterial, - bool resetAllRenderstates, IMaterialRendererServices* services) - { - Driver->disableTextures(2); - Driver->setTexture(1, material.getTexture(1)); - Driver->setTexture(0, material.getTexture(0)); - Driver->setBasicRenderStates(material, lastMaterial, resetAllRenderstates); - - if (material.MaterialType != lastMaterial.MaterialType || resetAllRenderstates) - { - if (Driver->queryFeature(EVDF_MULTITEXTURE)) - { - glTexEnvi(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_COMBINE_EXT); - glTexEnvi(GL_TEXTURE_ENV, GL_COMBINE_RGB_EXT, GL_MODULATE); - glTexEnvf(GL_TEXTURE_ENV, GL_SOURCE0_RGB_EXT, GL_TEXTURE ); - glTexEnvf(GL_TEXTURE_ENV, GL_SOURCE1_RGB_EXT, GL_PRIMARY_COLOR_EXT ); - - Driver->extGlActiveTexture(GL_TEXTURE1_ARB); - - glTexEnvi(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_COMBINE_EXT); - - glTexEnvi(GL_TEXTURE_ENV, GL_COMBINE_RGB_EXT, GL_MODULATE); - glTexEnvi(GL_TEXTURE_ENV, GL_SOURCE0_RGB_EXT, GL_PREVIOUS_EXT); - glTexEnvi(GL_TEXTURE_ENV, GL_OPERAND0_RGB_EXT, GL_SRC_COLOR); - glTexEnvi(GL_TEXTURE_ENV, GL_SOURCE1_RGB_EXT, GL_TEXTURE); - glTexEnvi(GL_TEXTURE_ENV, GL_OPERAND1_RGB_EXT, GL_SRC_COLOR); - } - glTexGeni(GL_S, GL_TEXTURE_GEN_MODE, GL_SPHERE_MAP); - glTexGeni(GL_T, GL_TEXTURE_GEN_MODE, GL_SPHERE_MAP); - glEnable(GL_TEXTURE_GEN_S); - glEnable(GL_TEXTURE_GEN_T); - - glBlendFunc(GL_ONE, GL_ONE_MINUS_SRC_COLOR); - glEnable(GL_BLEND); - } - } - - virtual void OnUnsetMaterial() - { - if (Driver->queryFeature(EVDF_MULTITEXTURE)) - { - Driver->extGlActiveTexture(GL_TEXTURE1_ARB); - glTexEnvi(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_MODULATE); - } - glDisable(GL_TEXTURE_GEN_S); - glDisable(GL_TEXTURE_GEN_T); - if (Driver->queryFeature(EVDF_MULTITEXTURE)) - { - Driver->extGlActiveTexture(GL_TEXTURE0_ARB); - glTexEnvi(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_MODULATE); - } - glDisable(GL_BLEND); - } - - //! Returns if the material is transparent. - virtual bool isTransparent() const - { - return true; - } -}; - -} // end namespace video -} // end namespace irr - -#endif -#endif - +// Copyright (C) 2002-2007 Nikolaus Gebhardt +// This file is part of the "Irrlicht Engine". +// For conditions of distribution and use, see copyright notice in irrlicht.h + +#ifndef __C_OPENGL_MATERIAL_RENDERER_H_INCLUDED__ +#define __C_OPENGL_MATERIAL_RENDERER_H_INCLUDED__ + +#include "IrrCompileConfig.h" +#ifdef _IRR_COMPILE_WITH_OPENGL_ + +#include "COpenGLDriver.h" +#include "IMaterialRenderer.h" +#include "IMaterialRenderer.h" +#if defined(_IRR_USE_OSX_DEVICE_) + #define GL_COMBINE_EXT 0x8570 + #define GL_COMBINE_RGB_EXT 0x8571 + #define GL_COMBINE_ALPHA_EXT 0x8572 + #define GL_RGB_SCALE_EXT 0x8573 + #define GL_ADD_SIGNED_EXT 0x8574 + #define GL_INTERPOLATE_EXT 0x8575 + #define GL_CONSTANT_EXT 0x8576 + #define GL_PRIMARY_COLOR_EXT 0x8577 + #define GL_PREVIOUS_EXT 0x8578 + #define GL_SOURCE0_RGB_EXT 0x8580 + #define GL_SOURCE1_RGB_EXT 0x8581 + #define GL_SOURCE2_RGB_EXT 0x8582 + #define GL_SOURCE3_RGB_EXT 0x8583 + #define GL_SOURCE4_RGB_EXT 0x8584 + #define GL_SOURCE5_RGB_EXT 0x8585 + #define GL_SOURCE6_RGB_EXT 0x8586 + #define GL_SOURCE7_RGB_EXT 0x8587 + #define GL_SOURCE0_ALPHA_EXT 0x8588 + #define GL_SOURCE1_ALPHA_EXT 0x8589 + #define GL_SOURCE2_ALPHA_EXT 0x858A + #define GL_SOURCE3_ALPHA_EXT 0x858B + #define GL_SOURCE4_ALPHA_EXT 0x858C + #define GL_SOURCE5_ALPHA_EXT 0x858D + #define GL_SOURCE6_ALPHA_EXT 0x858E + #define GL_SOURCE7_ALPHA_EXT 0x858F + #define GL_OPERAND0_RGB_EXT 0x8590 + #define GL_OPERAND1_RGB_EXT 0x8591 + #define GL_OPERAND2_RGB_EXT 0x8592 + #define GL_OPERAND3_RGB_EXT 0x8593 + #define GL_OPERAND4_RGB_EXT 0x8594 + #define GL_OPERAND5_RGB_EXT 0x8595 + #define GL_OPERAND6_RGB_EXT 0x8596 + #define GL_OPERAND7_RGB_EXT 0x8597 + #define GL_OPERAND0_ALPHA_EXT 0x8598 + #define GL_OPERAND1_ALPHA_EXT 0x8599 + #define GL_OPERAND2_ALPHA_EXT 0x859A + #define GL_OPERAND3_ALPHA_EXT 0x859B + #define GL_OPERAND4_ALPHA_EXT 0x859C + #define GL_OPERAND5_ALPHA_EXT 0x859D + #define GL_OPERAND6_ALPHA_EXT 0x859E + #define GL_OPERAND7_ALPHA_EXT 0x859F +#endif + +namespace irr +{ +namespace video +{ + +//! Base class for all internal OpenGL material renderers +class COpenGLMaterialRenderer : public IMaterialRenderer +{ +public: + + //! Constructor + COpenGLMaterialRenderer(video::COpenGLDriver* driver) : Driver(driver) + { + } + +protected: + + video::COpenGLDriver* Driver; +}; + + +//! Solid material renderer +class COpenGLMaterialRenderer_SOLID : public COpenGLMaterialRenderer +{ +public: + + COpenGLMaterialRenderer_SOLID(video::COpenGLDriver* d) + : COpenGLMaterialRenderer(d) {} + + virtual void OnSetMaterial(const SMaterial& material, const SMaterial& lastMaterial, + bool resetAllRenderstates, IMaterialRendererServices* services) + { + Driver->disableTextures(1); + Driver->setTexture(0, material.getTexture(0)); + Driver->setBasicRenderStates(material, lastMaterial, resetAllRenderstates); + + if (material.MaterialType != lastMaterial.MaterialType || resetAllRenderstates) + { + // thanks to Murphy, the following line removed some + // bugs with several OpenGL implementations. + glTexEnvi(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_MODULATE); + } + } +}; + + +//! Generic Texture Blend +class COpenGLMaterialRenderer_ONETEXTURE_BLEND : public COpenGLMaterialRenderer +{ +public: + + COpenGLMaterialRenderer_ONETEXTURE_BLEND(video::COpenGLDriver* d) + : COpenGLMaterialRenderer(d) {} + + virtual void OnSetMaterial(const SMaterial& material, const SMaterial& lastMaterial, + bool resetAllRenderstates, IMaterialRendererServices* services) + { + Driver->disableTextures(1); + Driver->setTexture(0, material.getTexture(0)); + Driver->setBasicRenderStates(material, lastMaterial, resetAllRenderstates); + +// if (material.MaterialType != lastMaterial.MaterialType || +// material.MaterialTypeParam != lastMaterial.MaterialTypeParam || +// resetAllRenderstates) + { + E_BLEND_FACTOR srcFact,dstFact; + E_MODULATE_FUNC modulate; + unpack_texureBlendFunc ( srcFact, dstFact, modulate, material.MaterialTypeParam ); + + glTexEnvf(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_COMBINE_EXT); + glTexEnvf(GL_TEXTURE_ENV, GL_COMBINE_RGB_EXT, GL_MODULATE); + glTexEnvf(GL_TEXTURE_ENV, GL_SOURCE0_RGB_EXT, GL_TEXTURE); + glTexEnvf(GL_TEXTURE_ENV, GL_SOURCE1_RGB_EXT, GL_PREVIOUS_EXT); + + glTexEnvf(GL_TEXTURE_ENV, GL_RGB_SCALE_EXT, (f32) modulate ); + + glBlendFunc( getGLBlend(srcFact), getGLBlend(dstFact) ); + glEnable(GL_ALPHA_TEST); + glEnable(GL_BLEND); + + if ( getTexelAlpha ( srcFact ) + getTexelAlpha ( dstFact ) ) + { + glTexEnvf(GL_TEXTURE_ENV, GL_COMBINE_ALPHA_EXT, GL_REPLACE); + glTexEnvf(GL_TEXTURE_ENV, GL_SOURCE0_ALPHA_EXT, GL_TEXTURE); + + glTexEnvf(GL_TEXTURE_ENV, GL_SOURCE1_RGB_EXT, GL_PRIMARY_COLOR_EXT); + } + } + } + + virtual void OnUnsetMaterial() + { + glTexEnvf(GL_TEXTURE_ENV, GL_RGB_SCALE_EXT, 1.f ); + glTexEnvf(GL_TEXTURE_ENV, GL_SOURCE1_RGB_EXT, GL_PREVIOUS_EXT); + + glDisable(GL_BLEND); + glDisable(GL_ALPHA_TEST); + } + + private: + + u32 getGLBlend ( E_BLEND_FACTOR factor ) const + { + u32 r = 0; + switch ( factor ) + { + case EBF_ZERO: r = GL_ZERO; break; + case EBF_ONE: r = GL_ONE; break; + case EBF_DST_COLOR: r = GL_DST_COLOR; break; + case EBF_ONE_MINUS_DST_COLOR: r = GL_ONE_MINUS_DST_COLOR; break; + case EBF_SRC_COLOR: r = GL_SRC_COLOR; break; + case EBF_ONE_MINUS_SRC_COLOR: r = GL_ONE_MINUS_SRC_COLOR; break; + case EBF_SRC_ALPHA: r = GL_SRC_ALPHA; break; + case EBF_ONE_MINUS_SRC_ALPHA: r = GL_ONE_MINUS_SRC_ALPHA; break; + case EBF_DST_ALPHA: r = GL_DST_ALPHA; break; + case EBF_ONE_MINUS_DST_ALPHA: r = GL_ONE_MINUS_DST_ALPHA; break; + case EBF_SRC_ALPHA_SATURATE: r = GL_SRC_ALPHA_SATURATE; break; + } + return r; + } + + u32 getTexelAlpha ( E_BLEND_FACTOR factor ) const + { + u32 r; + switch ( factor ) + { + case EBF_SRC_ALPHA: r = 1; break; + case EBF_ONE_MINUS_SRC_ALPHA: r = 1; break; + case EBF_DST_ALPHA: r = 1; break; + case EBF_ONE_MINUS_DST_ALPHA: r = 1; break; + case EBF_SRC_ALPHA_SATURATE: r = 1; break; + default: r = 0; break; + } + return r; + } +}; + + +//! Solid 2 layer material renderer +class COpenGLMaterialRenderer_SOLID_2_LAYER : public COpenGLMaterialRenderer +{ +public: + + COpenGLMaterialRenderer_SOLID_2_LAYER(video::COpenGLDriver* d) + : COpenGLMaterialRenderer(d) {} + + virtual void OnSetMaterial(const SMaterial& material, const SMaterial& lastMaterial, + bool resetAllRenderstates, IMaterialRendererServices* services) + { + Driver->disableTextures(2); + Driver->setTexture(1, material.getTexture(1)); + Driver->setTexture(0, material.getTexture(0)); + Driver->setBasicRenderStates(material, lastMaterial, resetAllRenderstates); + + if (material.MaterialType != lastMaterial.MaterialType || resetAllRenderstates) + { + if (Driver->queryFeature(EVDF_MULTITEXTURE)) + { + Driver->extGlActiveTexture(GL_TEXTURE1_ARB); + glTexEnvi(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_REPLACE); + + Driver->extGlActiveTexture(GL_TEXTURE0_ARB); + } + + glTexEnvi(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_MODULATE); + } + } +}; + + +//! Transparent add color material renderer +class COpenGLMaterialRenderer_TRANSPARENT_ADD_COLOR : public COpenGLMaterialRenderer +{ +public: + + COpenGLMaterialRenderer_TRANSPARENT_ADD_COLOR(video::COpenGLDriver* d) + : COpenGLMaterialRenderer(d) {} + + virtual void OnSetMaterial(const SMaterial& material, const SMaterial& lastMaterial, + bool resetAllRenderstates, IMaterialRendererServices* services) + { + Driver->disableTextures(1); + Driver->setTexture(0, material.getTexture(0)); + Driver->setBasicRenderStates(material, lastMaterial, resetAllRenderstates); + + if ((material.MaterialType != lastMaterial.MaterialType) || resetAllRenderstates) + { + glBlendFunc(GL_ONE, GL_ONE_MINUS_SRC_COLOR); + glTexEnvi(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_MODULATE); + glEnable(GL_BLEND); + } + } + + virtual void OnUnsetMaterial() + { + glDisable(GL_BLEND); + } + + //! Returns if the material is transparent. + virtual bool isTransparent() const + { + return true; + } +}; + + +//! Transparent vertex alpha material renderer +class COpenGLMaterialRenderer_TRANSPARENT_VERTEX_ALPHA : public COpenGLMaterialRenderer +{ +public: + + COpenGLMaterialRenderer_TRANSPARENT_VERTEX_ALPHA(video::COpenGLDriver* d) + : COpenGLMaterialRenderer(d) {} + + virtual void OnSetMaterial(const SMaterial& material, const SMaterial& lastMaterial, + bool resetAllRenderstates, IMaterialRendererServices* services) + { + Driver->disableTextures(1); + Driver->setTexture(0, material.getTexture(0)); + Driver->setBasicRenderStates(material, lastMaterial, resetAllRenderstates); + + if (material.MaterialType != lastMaterial.MaterialType || resetAllRenderstates) + { + glTexEnvf(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_COMBINE_EXT); + + glTexEnvf(GL_TEXTURE_ENV, GL_COMBINE_ALPHA_EXT, GL_REPLACE); + glTexEnvf(GL_TEXTURE_ENV, GL_SOURCE0_ALPHA_EXT, GL_PRIMARY_COLOR_EXT ); + + glTexEnvf(GL_TEXTURE_ENV, GL_COMBINE_RGB_EXT, GL_MODULATE); + glTexEnvf(GL_TEXTURE_ENV, GL_SOURCE0_RGB_EXT, GL_PRIMARY_COLOR_EXT ); + glTexEnvf(GL_TEXTURE_ENV, GL_SOURCE1_RGB_EXT, GL_TEXTURE); + + glBlendFunc(GL_ONE, GL_ONE_MINUS_SRC_ALPHA); + glEnable(GL_BLEND); + } + glDepthMask(GL_FALSE); + } + + virtual void OnUnsetMaterial() + { + // default values + glTexEnvi(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_COMBINE_EXT); + glTexEnvf(GL_TEXTURE_ENV, GL_COMBINE_ALPHA_EXT, GL_MODULATE ); + glTexEnvf(GL_TEXTURE_ENV, GL_SOURCE0_ALPHA_EXT, GL_TEXTURE ); + glTexEnvf(GL_TEXTURE_ENV, GL_SOURCE1_ALPHA_EXT, GL_PREVIOUS_EXT ); + glTexEnvf(GL_TEXTURE_ENV, GL_COMBINE_RGB_EXT, GL_MODULATE); + glTexEnvf(GL_TEXTURE_ENV, GL_SOURCE0_RGB_EXT, GL_TEXTURE ); + glTexEnvf(GL_TEXTURE_ENV, GL_SOURCE1_RGB_EXT, GL_PREVIOUS_EXT); + + glDisable(GL_BLEND); + } + + //! Returns if the material is transparent. + virtual bool isTransparent() const + { + return true; + } +}; + + +//! Transparent alpha channel material renderer +class COpenGLMaterialRenderer_TRANSPARENT_ALPHA_CHANNEL : public COpenGLMaterialRenderer +{ +public: + + COpenGLMaterialRenderer_TRANSPARENT_ALPHA_CHANNEL(video::COpenGLDriver* d) + : COpenGLMaterialRenderer(d) {} + + virtual void OnSetMaterial(const SMaterial& material, const SMaterial& lastMaterial, + bool resetAllRenderstates, IMaterialRendererServices* services) + { + Driver->disableTextures(1); + Driver->setTexture(0, material.getTexture(0)); + Driver->setBasicRenderStates(material, lastMaterial, resetAllRenderstates); + + if (material.MaterialType != lastMaterial.MaterialType || resetAllRenderstates + || material.MaterialTypeParam != lastMaterial.MaterialTypeParam ) + { + glTexEnvf(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_COMBINE_EXT); + glTexEnvf(GL_TEXTURE_ENV, GL_COMBINE_RGB_EXT, GL_MODULATE); + glTexEnvf(GL_TEXTURE_ENV, GL_SOURCE0_RGB_EXT, GL_TEXTURE); + glTexEnvf(GL_TEXTURE_ENV, GL_SOURCE1_RGB_EXT, GL_PREVIOUS_EXT); + + glTexEnvf(GL_TEXTURE_ENV, GL_COMBINE_ALPHA_EXT, GL_REPLACE); + glTexEnvf(GL_TEXTURE_ENV, GL_SOURCE0_ALPHA_EXT, GL_TEXTURE); + + glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA); + glEnable(GL_BLEND); + glEnable(GL_ALPHA_TEST); + + f32 refValue = material.MaterialTypeParam; + if ( refValue == 0.0f ) + refValue = 0.5f; + + glAlphaFunc(GL_GREATER, refValue); + } + } + + virtual void OnUnsetMaterial() + { + glDisable(GL_ALPHA_TEST); + glDisable(GL_BLEND); + } + + //! Returns if the material is transparent. + virtual bool isTransparent() const + { + return true; + } +}; + + + +//! Transparent alpha channel material renderer +class COpenGLMaterialRenderer_TRANSPARENT_ALPHA_CHANNEL_REF : public COpenGLMaterialRenderer +{ +public: + + COpenGLMaterialRenderer_TRANSPARENT_ALPHA_CHANNEL_REF(video::COpenGLDriver* d) + : COpenGLMaterialRenderer(d) {} + + virtual void OnSetMaterial(const SMaterial& material, const SMaterial& lastMaterial, + bool resetAllRenderstates, IMaterialRendererServices* services) + { + Driver->disableTextures(1); + Driver->setTexture(0, material.getTexture(0)); + Driver->setBasicRenderStates(material, lastMaterial, resetAllRenderstates); + + if (material.MaterialType != lastMaterial.MaterialType || resetAllRenderstates) + { + glEnable(GL_ALPHA_TEST); + glAlphaFunc(GL_GREATER, 0.5); + glTexEnvi(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_REPLACE); + } + } + + virtual void OnUnsetMaterial() + { + glDisable(GL_ALPHA_TEST); + } + + //! Returns if the material is transparent. + virtual bool isTransparent() const + { + return false; // this material is not really transparent because it does no blending. + } +}; + + +//! material renderer for all kinds of lightmaps +class COpenGLMaterialRenderer_LIGHTMAP : public COpenGLMaterialRenderer +{ +public: + + COpenGLMaterialRenderer_LIGHTMAP(video::COpenGLDriver* d) + : COpenGLMaterialRenderer(d) {} + + virtual void OnSetMaterial(const SMaterial& material, const SMaterial& lastMaterial, + bool resetAllRenderstates, IMaterialRendererServices* services) + { + Driver->disableTextures(2); + Driver->setTexture(1, material.getTexture(1)); + Driver->setTexture(0, material.getTexture(0)); + Driver->setBasicRenderStates(material, lastMaterial, resetAllRenderstates); + + if (material.MaterialType != lastMaterial.MaterialType || resetAllRenderstates) + { + // diffuse map + + glTexEnvi(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_COMBINE_EXT); + switch (material.MaterialType) + { + case EMT_LIGHTMAP_LIGHTING: + case EMT_LIGHTMAP_LIGHTING_M2: + case EMT_LIGHTMAP_LIGHTING_M4: + glTexEnvi(GL_TEXTURE_ENV, GL_COMBINE_RGB_EXT, GL_MODULATE); + break; + case EMT_LIGHTMAP_ADD: + case EMT_LIGHTMAP: + case EMT_LIGHTMAP_M2: + case EMT_LIGHTMAP_M4: + default: + glTexEnvi(GL_TEXTURE_ENV, GL_COMBINE_RGB_EXT, GL_REPLACE); + break; + } + glTexEnvf(GL_TEXTURE_ENV, GL_SOURCE0_RGB_EXT, GL_TEXTURE); + glTexEnvi(GL_TEXTURE_ENV, GL_OPERAND0_RGB_EXT, GL_SRC_COLOR); + glTexEnvf(GL_TEXTURE_ENV, GL_SOURCE1_RGB_EXT, GL_PREVIOUS_EXT); + glTexEnvi(GL_TEXTURE_ENV, GL_OPERAND1_RGB_EXT, GL_SRC_COLOR ); + + if (Driver->queryFeature(EVDF_MULTITEXTURE)) + { + // lightmap + + Driver->extGlActiveTexture(GL_TEXTURE1_ARB); + glTexEnvi(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_COMBINE_EXT); + + if (material.MaterialType == EMT_LIGHTMAP_ADD) + glTexEnvi(GL_TEXTURE_ENV, GL_COMBINE_RGB_EXT, GL_ADD_SIGNED_ARB); + else + glTexEnvi(GL_TEXTURE_ENV, GL_COMBINE_RGB_EXT, GL_MODULATE); + + glTexEnvi(GL_TEXTURE_ENV, GL_SOURCE0_RGB_EXT, GL_PREVIOUS_EXT); + glTexEnvi(GL_TEXTURE_ENV, GL_OPERAND0_RGB_EXT, GL_SRC_COLOR); + glTexEnvi(GL_TEXTURE_ENV, GL_SOURCE1_RGB_EXT, GL_TEXTURE); + glTexEnvi(GL_TEXTURE_ENV, GL_OPERAND1_RGB_EXT, GL_SRC_COLOR); + + glTexEnvf(GL_TEXTURE_ENV, GL_COMBINE_ALPHA_EXT, GL_MODULATE); + glTexEnvi(GL_TEXTURE_ENV, GL_SOURCE0_ALPHA_EXT, GL_PREVIOUS_ARB); + glTexEnvi(GL_TEXTURE_ENV, GL_OPERAND0_ALPHA_EXT, GL_SRC_ALPHA); + glTexEnvi(GL_TEXTURE_ENV, GL_SOURCE1_ALPHA_EXT, GL_PREVIOUS_ARB); + glTexEnvi(GL_TEXTURE_ENV, GL_OPERAND1_ALPHA_EXT, GL_SRC_ALPHA); + + switch (material.MaterialType) + { + case EMT_LIGHTMAP_M4: + case EMT_LIGHTMAP_LIGHTING_M4: + glTexEnvf(GL_TEXTURE_ENV, GL_RGB_SCALE_EXT, 4.0f); + break; + case EMT_LIGHTMAP_M2: + case EMT_LIGHTMAP_LIGHTING_M2: + glTexEnvf(GL_TEXTURE_ENV, GL_RGB_SCALE_EXT, 2.0f); + break; + default: + glTexEnvf(GL_TEXTURE_ENV, GL_RGB_SCALE_EXT, 1.0f); + } + } + } + } + + virtual void OnUnsetMaterial() + { + if (Driver->queryFeature(EVDF_MULTITEXTURE)) + { + Driver->extGlActiveTexture(GL_TEXTURE1_ARB); + glTexEnvf(GL_TEXTURE_ENV, GL_RGB_SCALE_EXT, 1.f ); + Driver->extGlActiveTexture(GL_TEXTURE0_ARB); + } + } +}; + + + +//! detail map material renderer +class COpenGLMaterialRenderer_DETAIL_MAP : public COpenGLMaterialRenderer +{ +public: + + COpenGLMaterialRenderer_DETAIL_MAP(video::COpenGLDriver* d) + : COpenGLMaterialRenderer(d) {} + + virtual void OnSetMaterial(const SMaterial& material, const SMaterial& lastMaterial, + bool resetAllRenderstates, IMaterialRendererServices* services) + { + Driver->disableTextures(2); + Driver->setTexture(1, material.getTexture(1)); + Driver->setTexture(0, material.getTexture(0)); + Driver->setBasicRenderStates(material, lastMaterial, resetAllRenderstates); + + if (material.MaterialType != lastMaterial.MaterialType || resetAllRenderstates) + { + // diffuse map + + glTexEnvi(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_COMBINE_EXT); + glTexEnvi(GL_TEXTURE_ENV, GL_COMBINE_RGB_EXT, GL_MODULATE); + + if (Driver->queryFeature(EVDF_MULTITEXTURE)) + { + // detail map + + Driver->extGlActiveTexture(GL_TEXTURE1_ARB); + + glTexEnvi(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_COMBINE_EXT); + glTexEnvi(GL_TEXTURE_ENV, GL_COMBINE_RGB_EXT, GL_ADD_SIGNED_EXT); + + glTexEnvi(GL_TEXTURE_ENV,GL_SOURCE0_RGB_EXT,GL_PREVIOUS_EXT); + glTexEnvi(GL_TEXTURE_ENV,GL_OPERAND0_RGB_EXT,GL_SRC_COLOR); + + glTexEnvi(GL_TEXTURE_ENV,GL_SOURCE1_RGB_EXT, GL_TEXTURE); + glTexEnvi(GL_TEXTURE_ENV,GL_OPERAND1_RGB_EXT,GL_SRC_COLOR); + Driver->extGlActiveTexture(GL_TEXTURE0_ARB); + } + } + } +}; + + +//! sphere map material renderer +class COpenGLMaterialRenderer_SPHERE_MAP : public COpenGLMaterialRenderer +{ +public: + + COpenGLMaterialRenderer_SPHERE_MAP(video::COpenGLDriver* d) + : COpenGLMaterialRenderer(d) {} + + virtual void OnSetMaterial(const SMaterial& material, const SMaterial& lastMaterial, + bool resetAllRenderstates, IMaterialRendererServices* services) + { + Driver->disableTextures(1); + Driver->setTexture(0, material.getTexture(0)); + Driver->setBasicRenderStates(material, lastMaterial, resetAllRenderstates); + + if (material.MaterialType != lastMaterial.MaterialType || resetAllRenderstates) + { + glTexEnvi(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_MODULATE); + + glTexGeni(GL_S, GL_TEXTURE_GEN_MODE, GL_SPHERE_MAP); + glTexGeni(GL_T, GL_TEXTURE_GEN_MODE, GL_SPHERE_MAP); + + glEnable(GL_TEXTURE_GEN_S); + glEnable(GL_TEXTURE_GEN_T); + } + } + + virtual void OnUnsetMaterial() + { + glDisable(GL_TEXTURE_GEN_S); + glDisable(GL_TEXTURE_GEN_T); + } +}; + + +//! reflection 2 layer material renderer +class COpenGLMaterialRenderer_REFLECTION_2_LAYER : public COpenGLMaterialRenderer +{ +public: + + COpenGLMaterialRenderer_REFLECTION_2_LAYER(video::COpenGLDriver* d) + : COpenGLMaterialRenderer(d) {} + + virtual void OnSetMaterial(const SMaterial& material, const SMaterial& lastMaterial, + bool resetAllRenderstates, IMaterialRendererServices* services) + { + Driver->disableTextures(2); + Driver->setTexture(1, material.getTexture(1)); + Driver->setTexture(0, material.getTexture(0)); + Driver->setBasicRenderStates(material, lastMaterial, resetAllRenderstates); + + if (material.MaterialType != lastMaterial.MaterialType || resetAllRenderstates) + { + if (Driver->queryFeature(EVDF_MULTITEXTURE)) + { + glTexEnvi(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_COMBINE_EXT); + glTexEnvi(GL_TEXTURE_ENV, GL_COMBINE_RGB_EXT, GL_MODULATE); + glTexEnvf(GL_TEXTURE_ENV, GL_SOURCE0_RGB_EXT, GL_TEXTURE ); + glTexEnvf(GL_TEXTURE_ENV, GL_SOURCE1_RGB_EXT, GL_PRIMARY_COLOR_EXT ); + + Driver->extGlActiveTexture(GL_TEXTURE1_ARB); + + glTexEnvi(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_COMBINE_EXT); + + glTexEnvi(GL_TEXTURE_ENV, GL_COMBINE_RGB_EXT, GL_MODULATE); + glTexEnvi(GL_TEXTURE_ENV, GL_SOURCE0_RGB_EXT, GL_PREVIOUS_EXT); + glTexEnvi(GL_TEXTURE_ENV, GL_OPERAND0_RGB_EXT, GL_SRC_COLOR); + glTexEnvi(GL_TEXTURE_ENV, GL_SOURCE1_RGB_EXT, GL_TEXTURE); + glTexEnvi(GL_TEXTURE_ENV, GL_OPERAND1_RGB_EXT, GL_SRC_COLOR); + + } + glTexGeni(GL_S, GL_TEXTURE_GEN_MODE, GL_SPHERE_MAP); + glTexGeni(GL_T, GL_TEXTURE_GEN_MODE, GL_SPHERE_MAP); + glEnable(GL_TEXTURE_GEN_S); + glEnable(GL_TEXTURE_GEN_T); + } + } + + virtual void OnUnsetMaterial() + { + if (Driver->queryFeature(EVDF_MULTITEXTURE)) + { + Driver->extGlActiveTexture(GL_TEXTURE1_ARB); + glTexEnvi(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_MODULATE); + } + glDisable(GL_TEXTURE_GEN_S); + glDisable(GL_TEXTURE_GEN_T); + if (Driver->queryFeature(EVDF_MULTITEXTURE)) + { + Driver->extGlActiveTexture(GL_TEXTURE0_ARB); + + glTexEnvi(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_MODULATE); + } + } +}; + + +//! reflection 2 layer material renderer +class COpenGLMaterialRenderer_TRANSPARENT_REFLECTION_2_LAYER : public COpenGLMaterialRenderer +{ +public: + + COpenGLMaterialRenderer_TRANSPARENT_REFLECTION_2_LAYER(video::COpenGLDriver* d) + : COpenGLMaterialRenderer(d) {} + + virtual void OnSetMaterial(const SMaterial& material, const SMaterial& lastMaterial, + bool resetAllRenderstates, IMaterialRendererServices* services) + { + Driver->disableTextures(2); + Driver->setTexture(1, material.getTexture(1)); + Driver->setTexture(0, material.getTexture(0)); + Driver->setBasicRenderStates(material, lastMaterial, resetAllRenderstates); + + if (material.MaterialType != lastMaterial.MaterialType || resetAllRenderstates) + { + if (Driver->queryFeature(EVDF_MULTITEXTURE)) + { + glTexEnvi(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_COMBINE_EXT); + glTexEnvi(GL_TEXTURE_ENV, GL_COMBINE_RGB_EXT, GL_MODULATE); + glTexEnvf(GL_TEXTURE_ENV, GL_SOURCE0_RGB_EXT, GL_TEXTURE ); + glTexEnvf(GL_TEXTURE_ENV, GL_SOURCE1_RGB_EXT, GL_PRIMARY_COLOR_EXT ); + + Driver->extGlActiveTexture(GL_TEXTURE1_ARB); + + glTexEnvi(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_COMBINE_EXT); + + glTexEnvi(GL_TEXTURE_ENV, GL_COMBINE_RGB_EXT, GL_MODULATE); + glTexEnvi(GL_TEXTURE_ENV, GL_SOURCE0_RGB_EXT, GL_PREVIOUS_EXT); + glTexEnvi(GL_TEXTURE_ENV, GL_OPERAND0_RGB_EXT, GL_SRC_COLOR); + glTexEnvi(GL_TEXTURE_ENV, GL_SOURCE1_RGB_EXT, GL_TEXTURE); + glTexEnvi(GL_TEXTURE_ENV, GL_OPERAND1_RGB_EXT, GL_SRC_COLOR); + } + glTexGeni(GL_S, GL_TEXTURE_GEN_MODE, GL_SPHERE_MAP); + glTexGeni(GL_T, GL_TEXTURE_GEN_MODE, GL_SPHERE_MAP); + glEnable(GL_TEXTURE_GEN_S); + glEnable(GL_TEXTURE_GEN_T); + + glBlendFunc(GL_ONE, GL_ONE_MINUS_SRC_COLOR); + glEnable(GL_BLEND); + } + } + + virtual void OnUnsetMaterial() + { + if (Driver->queryFeature(EVDF_MULTITEXTURE)) + { + Driver->extGlActiveTexture(GL_TEXTURE1_ARB); + glTexEnvi(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_MODULATE); + } + glDisable(GL_TEXTURE_GEN_S); + glDisable(GL_TEXTURE_GEN_T); + if (Driver->queryFeature(EVDF_MULTITEXTURE)) + { + Driver->extGlActiveTexture(GL_TEXTURE0_ARB); + glTexEnvi(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_MODULATE); + } + glDisable(GL_BLEND); + } + + //! Returns if the material is transparent. + virtual bool isTransparent() const + { + return true; + } +}; + +} // end namespace video +} // end namespace irr + +#endif +#endif + diff --git a/source/Irrlicht/COpenGLSLMaterialRenderer.h b/source/Irrlicht/COpenGLSLMaterialRenderer.h index 9abca1c2..03baed6c 100644 --- a/source/Irrlicht/COpenGLSLMaterialRenderer.h +++ b/source/Irrlicht/COpenGLSLMaterialRenderer.h @@ -17,7 +17,7 @@ #if defined(_IRR_OPENGL_USE_EXTPOINTER_) #define GL_GLEXT_LEGACY 1 #endif -#if defined(MACOSX) +#if defined(_IRR_USE_OSX_DEVICE_) #include #else #include diff --git a/source/Irrlicht/COpenGLShaderMaterialRenderer.h b/source/Irrlicht/COpenGLShaderMaterialRenderer.h index 16776fb9..46ebc279 100644 --- a/source/Irrlicht/COpenGLShaderMaterialRenderer.h +++ b/source/Irrlicht/COpenGLShaderMaterialRenderer.h @@ -16,7 +16,7 @@ #if defined(_IRR_OPENGL_USE_EXTPOINTER_) #define GL_GLEXT_LEGACY 1 #endif -#if defined(MACOSX) +#if defined(_IRR_USE_OSX_DEVICE_) #include #else #include diff --git a/source/Irrlicht/COpenGLTexture.h b/source/Irrlicht/COpenGLTexture.h index 84512f23..8c60159d 100644 --- a/source/Irrlicht/COpenGLTexture.h +++ b/source/Irrlicht/COpenGLTexture.h @@ -25,7 +25,7 @@ #if defined(_IRR_OPENGL_USE_EXTPOINTER_) #define GL_GLEXT_LEGACY 1 #endif - #if defined(MACOSX) + #if defined(_IRR_USE_OSX_DEVICE_) #include #else #include diff --git a/source/Irrlicht/CPakReader.cpp b/source/Irrlicht/CPakReader.cpp index 062ea836..a54a0337 100644 --- a/source/Irrlicht/CPakReader.cpp +++ b/source/Irrlicht/CPakReader.cpp @@ -174,13 +174,11 @@ void CPakReader::deletePathFromFilename(core::stringc& filename) // delete path from filename const c8* p = filename.c_str() + filename.size(); - // suche ein slash oder den anfang. + // search for path separator or beginning while (*p!='/' && *p!='\\' && p!=filename.c_str()) --p; - core::stringc newName; - if (p != filename.c_str()) { ++p; diff --git a/source/Irrlicht/CSoftwareDriver2.cpp b/source/Irrlicht/CSoftwareDriver2.cpp index 53533d31..eaaec996 100644 --- a/source/Irrlicht/CSoftwareDriver2.cpp +++ b/source/Irrlicht/CSoftwareDriver2.cpp @@ -515,16 +515,16 @@ const sVec4 CBurningVideoDriver::NDCPlane[6] = for ( u32 i = 0; i!= 6; ++i ) { dotPlane = v->Pos.dotProduct ( NDCPlane[i] ); - setbit ( flag, dotPlane <= 0.f, 1 << i ); + core::setbit_cond( flag, dotPlane <= 0.f, 1 << i ); } // this is the base for ndc frustum <-w,w>,<-w,w>,<-w,w> - setbits ( flag, ( v->Pos.z - v->Pos.w ) <= 0.f, 1 ); - setbits ( flag, (-v->Pos.z - v->Pos.w ) <= 0.f, 2 ); - setbits ( flag, ( v->Pos.x - v->Pos.w ) <= 0.f, 4 ); - setbits ( flag, (-v->Pos.x - v->Pos.w ) <= 0.f, 8 ); - setbits ( flag, ( v->Pos.y - v->Pos.w ) <= 0.f, 16 ); - setbits ( flag, (-v->Pos.y - v->Pos.w ) <= 0.f, 32 ); + core::setbit_cond( flag, ( v->Pos.z - v->Pos.w ) <= 0.f, 1 ); + core::setbit_cond( flag, (-v->Pos.z - v->Pos.w ) <= 0.f, 2 ); + core::setbit_cond( flag, ( v->Pos.x - v->Pos.w ) <= 0.f, 4 ); + core::setbit_cond( flag, (-v->Pos.x - v->Pos.w ) <= 0.f, 8 ); + core::setbit_cond( flag, ( v->Pos.y - v->Pos.w ) <= 0.f, 16 ); + core::setbit_cond( flag, (-v->Pos.y - v->Pos.w ) <= 0.f, 32 ); */ #ifdef _MSC_VER @@ -572,7 +572,7 @@ REALINLINE u32 CBurningVideoDriver::clipToFrustumTest ( const s4DVertex * v ) c u32 flag = 0; for ( u32 i = 0; i!= 6; ++i ) { - core::setbit ( flag, v->Pos.dotProduct ( NDCPlane[i] ) <= 0.f, 1 << i ); + core::setbit_cond( flag, v->Pos.dotProduct ( NDCPlane[i] ) <= 0.f, 1 << i ); } return flag; } diff --git a/source/Irrlicht/CXMLWriter.cpp b/source/Irrlicht/CXMLWriter.cpp index 06b0b790..78c00d23 100644 --- a/source/Irrlicht/CXMLWriter.cpp +++ b/source/Irrlicht/CXMLWriter.cpp @@ -233,7 +233,7 @@ void CXMLWriter::writeLineBreak() if (!File) return; -#if defined(MACOSX) +#if defined(_IRR_OSX_PLATFORM_) File->write(L"\r", sizeof(wchar_t)); #elif defined(_IRR_WINDOWS_API_) File->write(L"\r\n", 2*sizeof(wchar_t)); diff --git a/source/Irrlicht/CZipReader.cpp b/source/Irrlicht/CZipReader.cpp index 1723dcda..6d3d2ddd 100644 --- a/source/Irrlicht/CZipReader.cpp +++ b/source/Irrlicht/CZipReader.cpp @@ -298,13 +298,11 @@ void CZipReader::deletePathFromFilename(core::stringc& filename) // delete path from filename const c8* p = filename.c_str() + filename.size(); - // suche ein slash oder den anfang. + // search for path separator or beginning while (*p!='/' && *p!='\\' && p!=filename.c_str()) --p; - core::stringc newName; - if (p != filename.c_str()) { ++p; diff --git a/source/Irrlicht/MacOSX/CIrrDeviceMacOSX.h b/source/Irrlicht/MacOSX/CIrrDeviceMacOSX.h index 9808f88e..d957ca79 100644 --- a/source/Irrlicht/MacOSX/CIrrDeviceMacOSX.h +++ b/source/Irrlicht/MacOSX/CIrrDeviceMacOSX.h @@ -1,214 +1,214 @@ -// Copyright (C) 2005 Etienne Petitjean -// This file is part of the "Irrlicht Engine". -// For conditions of distribution and use, see copyright notice in Irrlicht.h - -#ifndef __C_IRR_DEVICE_MACOSX_H_INCLUDED__ -#define __C_IRR_DEVICE_MACOSX_H_INCLUDED__ - -#include "IrrCompileConfig.h" - -#ifdef MACOSX - -#include "CIrrDeviceStub.h" -#include "IrrlichtDevice.h" -#include "IImagePresenter.h" -#include "IGUIEnvironment.h" -#include "ICursorControl.h" - -#include -#include - -namespace irr -{ - class CIrrDeviceMacOSX : public CIrrDeviceStub, video::IImagePresenter - { - public: - - //! constructor - CIrrDeviceMacOSX(video::E_DRIVER_TYPE driverType, - const core::dimension2d& windowSize, - u32 bits, bool fullscreen, - bool sbuffer, bool vsync, - bool antiAlias, IEventReceiver* receiver, - const char* version); - - //! destructor - virtual ~CIrrDeviceMacOSX(); - - //! runs the device. Returns false if device wants to be deleted - virtual bool run(); - - //! Cause the device to temporarily pause execution and let other processes to run - // This should bring down processor usage without major performance loss for Irrlicht - virtual void yield(); - - //! Pause execution and let other processes to run for a specified amount of time. - virtual void sleep(u32 timeMs, bool pauseTimer); - - //! sets the caption of the window - virtual void setWindowCaption(const wchar_t* text); - - //! returns if window is active. if not, nothing need to be drawn - virtual bool isWindowActive() const; - - //! presents a surface in the client area - virtual void present(video::IImage* surface, s32 windowId = 0, core::rect* src=0 ); - - //! notifies the device that it should close itself - virtual void closeDevice(); - - //! Sets if the window should be resizeable in windowed mode. - virtual void setResizeAble(bool resize); - - void flush(); - void setMouseLocation(int x,int y); - void setResize(int width,int height); - void setCursorVisible(bool visible); - - private: - - //! create the driver - void createDriver(video::E_DRIVER_TYPE driverType, - const core::dimension2d& windowSize, u32 bits, bool fullscreen, - bool stencilbuffer, bool vsync, bool antiAlias); - - //! Implementation of the macos x cursor control - class CCursorControl : public gui::ICursorControl - { - public: - - CCursorControl(const core::dimension2d& wsize, CIrrDeviceMacOSX *device) : WindowSize(wsize), IsVisible(true), InvWindowSize(0.0f, 0.0f), _device(device), UseReferenceRect(false) - { - CursorPos.X = CursorPos.Y = 0; - if (WindowSize.Width!=0) InvWindowSize.Width = 1.0f / WindowSize.Width; - if (WindowSize.Height!=0) InvWindowSize.Height = 1.0f / WindowSize.Height; - } - - //! Changes the visible state of the mouse cursor. - virtual void setVisible(bool visible) - { - IsVisible = visible; - _device->setCursorVisible(visible); - } - - //! Returns if the cursor is currently visible. - virtual bool isVisible() const - { - return IsVisible; - } - - //! Sets the new position of the cursor. - virtual void setPosition(const core::position2d &pos) - { - setPosition(pos.X, pos.Y); - } - - //! Sets the new position of the cursor. - virtual void setPosition(f32 x, f32 y) - { - setPosition((s32)(x*WindowSize.Width), (s32)(y*WindowSize.Height)); - } - - //! Sets the new position of the cursor. - virtual void setPosition(const core::position2d &pos) - { - if (CursorPos.X != pos.X || CursorPos.Y != pos.Y) - setPosition(pos.X, pos.Y); - } - - //! Sets the new position of the cursor. - virtual void setPosition(s32 x, s32 y) - { - if (UseReferenceRect) - { - _device->setMouseLocation(ReferenceRect.UpperLeftCorner.X + x, ReferenceRect.UpperLeftCorner.Y + y); - } - else - { - _device->setMouseLocation(x,y); - } - } - - //! Returns the current position of the mouse cursor. - virtual core::position2d getPosition() - { - return CursorPos; - } - - //! Returns the current position of the mouse cursor. - virtual core::position2d getRelativePosition() - { - if (!UseReferenceRect) - { - return core::position2d(CursorPos.X * InvWindowSize.Width, - CursorPos.Y * InvWindowSize.Height); - } - - return core::position2d(CursorPos.X / (f32)ReferenceRect.getWidth(), - CursorPos.Y / (f32)ReferenceRect.getHeight()); - } - - //! Sets an absolute reference rect for calculating the cursor position. - virtual void setReferenceRect(core::rect* rect=0) - { - if (rect) - { - ReferenceRect = *rect; - UseReferenceRect = true; - - // prevent division through zero and uneven sizes - - if (!ReferenceRect.getHeight() || ReferenceRect.getHeight()%2) - ReferenceRect.LowerRightCorner.Y += 1; - - if (!ReferenceRect.getWidth() || ReferenceRect.getWidth()%2) - ReferenceRect.LowerRightCorner.X += 1; - } - else - UseReferenceRect = false; - } - - //! Updates the internal cursor position - void updateInternalCursorPosition(int x,int y) - { - CursorPos.X = x; - CursorPos.Y = y; - } - - private: - - core::position2d CursorPos; - core::dimension2d WindowSize; - core::dimension2d InvWindowSize; - CIrrDeviceMacOSX *_device; - bool IsVisible; - bool UseReferenceRect; - core::rect ReferenceRect; - }; - - bool createWindow(const irr::core::dimension2d& windowSize, irr::u32 bits, bool fullscreen, bool vsync, bool stencilBuffer); - void initKeycodes(); - void storeMouseLocation(); - void postMouseEvent(void *event,irr::SEvent &ievent); - void postKeyEvent(void *event,irr::SEvent &ievent,bool pressed); - - video::E_DRIVER_TYPE DriverType; - bool stencilbuffer; - - void *_window; - CGLContextObj _cglcontext; - void *_oglcontext; - int _width; - int _height; - std::map _keycodes; - int _screenWidth; - int _screenHeight; - bool _active; - }; - - -} // end namespace irr - -#endif // MACOSX -#endif // __C_IRR_DEVICE_MACOSX_H_INCLUDED__ - +// Copyright (C) 2005 Etienne Petitjean +// This file is part of the "Irrlicht Engine". +// For conditions of distribution and use, see copyright notice in Irrlicht.h + +#ifndef __C_IRR_DEVICE_MACOSX_H_INCLUDED__ +#define __C_IRR_DEVICE_MACOSX_H_INCLUDED__ + +#include "IrrCompileConfig.h" + +#ifdef _IRR_USE_OSX_DEVICE_ + +#include "CIrrDeviceStub.h" +#include "IrrlichtDevice.h" +#include "IImagePresenter.h" +#include "IGUIEnvironment.h" +#include "ICursorControl.h" + +#include +#include + +namespace irr +{ + class CIrrDeviceMacOSX : public CIrrDeviceStub, video::IImagePresenter + { + public: + + //! constructor + CIrrDeviceMacOSX(video::E_DRIVER_TYPE driverType, + const core::dimension2d& windowSize, + u32 bits, bool fullscreen, + bool sbuffer, bool vsync, + bool antiAlias, IEventReceiver* receiver, + const char* version); + + //! destructor + virtual ~CIrrDeviceMacOSX(); + + //! runs the device. Returns false if device wants to be deleted + virtual bool run(); + + //! Cause the device to temporarily pause execution and let other processes to run + // This should bring down processor usage without major performance loss for Irrlicht + virtual void yield(); + + //! Pause execution and let other processes to run for a specified amount of time. + virtual void sleep(u32 timeMs, bool pauseTimer); + + //! sets the caption of the window + virtual void setWindowCaption(const wchar_t* text); + + //! returns if window is active. if not, nothing need to be drawn + virtual bool isWindowActive() const; + + //! presents a surface in the client area + virtual void present(video::IImage* surface, s32 windowId = 0, core::rect* src=0 ); + + //! notifies the device that it should close itself + virtual void closeDevice(); + + //! Sets if the window should be resizeable in windowed mode. + virtual void setResizeAble(bool resize); + + void flush(); + void setMouseLocation(int x,int y); + void setResize(int width,int height); + void setCursorVisible(bool visible); + + private: + + //! create the driver + void createDriver(video::E_DRIVER_TYPE driverType, + const core::dimension2d& windowSize, u32 bits, bool fullscreen, + bool stencilbuffer, bool vsync, bool antiAlias); + + //! Implementation of the macos x cursor control + class CCursorControl : public gui::ICursorControl + { + public: + + CCursorControl(const core::dimension2d& wsize, CIrrDeviceMacOSX *device) : WindowSize(wsize), IsVisible(true), InvWindowSize(0.0f, 0.0f), _device(device), UseReferenceRect(false) + { + CursorPos.X = CursorPos.Y = 0; + if (WindowSize.Width!=0) InvWindowSize.Width = 1.0f / WindowSize.Width; + if (WindowSize.Height!=0) InvWindowSize.Height = 1.0f / WindowSize.Height; + } + + //! Changes the visible state of the mouse cursor. + virtual void setVisible(bool visible) + { + IsVisible = visible; + _device->setCursorVisible(visible); + } + + //! Returns if the cursor is currently visible. + virtual bool isVisible() const + { + return IsVisible; + } + + //! Sets the new position of the cursor. + virtual void setPosition(const core::position2d &pos) + { + setPosition(pos.X, pos.Y); + } + + //! Sets the new position of the cursor. + virtual void setPosition(f32 x, f32 y) + { + setPosition((s32)(x*WindowSize.Width), (s32)(y*WindowSize.Height)); + } + + //! Sets the new position of the cursor. + virtual void setPosition(const core::position2d &pos) + { + if (CursorPos.X != pos.X || CursorPos.Y != pos.Y) + setPosition(pos.X, pos.Y); + } + + //! Sets the new position of the cursor. + virtual void setPosition(s32 x, s32 y) + { + if (UseReferenceRect) + { + _device->setMouseLocation(ReferenceRect.UpperLeftCorner.X + x, ReferenceRect.UpperLeftCorner.Y + y); + } + else + { + _device->setMouseLocation(x,y); + } + } + + //! Returns the current position of the mouse cursor. + virtual core::position2d getPosition() + { + return CursorPos; + } + + //! Returns the current position of the mouse cursor. + virtual core::position2d getRelativePosition() + { + if (!UseReferenceRect) + { + return core::position2d(CursorPos.X * InvWindowSize.Width, + CursorPos.Y * InvWindowSize.Height); + } + + return core::position2d(CursorPos.X / (f32)ReferenceRect.getWidth(), + CursorPos.Y / (f32)ReferenceRect.getHeight()); + } + + //! Sets an absolute reference rect for calculating the cursor position. + virtual void setReferenceRect(core::rect* rect=0) + { + if (rect) + { + ReferenceRect = *rect; + UseReferenceRect = true; + + // prevent division through zero and uneven sizes + + if (!ReferenceRect.getHeight() || ReferenceRect.getHeight()%2) + ReferenceRect.LowerRightCorner.Y += 1; + + if (!ReferenceRect.getWidth() || ReferenceRect.getWidth()%2) + ReferenceRect.LowerRightCorner.X += 1; + } + else + UseReferenceRect = false; + } + + //! Updates the internal cursor position + void updateInternalCursorPosition(int x,int y) + { + CursorPos.X = x; + CursorPos.Y = y; + } + + private: + + core::position2d CursorPos; + core::dimension2d WindowSize; + core::dimension2d InvWindowSize; + CIrrDeviceMacOSX *_device; + bool IsVisible; + bool UseReferenceRect; + core::rect ReferenceRect; + }; + + bool createWindow(const irr::core::dimension2d& windowSize, irr::u32 bits, bool fullscreen, bool vsync, bool stencilBuffer); + void initKeycodes(); + void storeMouseLocation(); + void postMouseEvent(void *event,irr::SEvent &ievent); + void postKeyEvent(void *event,irr::SEvent &ievent,bool pressed); + + video::E_DRIVER_TYPE DriverType; + bool stencilbuffer; + + void *_window; + CGLContextObj _cglcontext; + void *_oglcontext; + int _width; + int _height; + std::map _keycodes; + int _screenWidth; + int _screenHeight; + bool _active; + }; + + +} // end namespace irr + +#endif // _IRR_USE_OSX_DEVICE_ +#endif // __C_IRR_DEVICE_MACOSX_H_INCLUDED__ + diff --git a/source/Irrlicht/MacOSX/CIrrDeviceMacOSX.mm b/source/Irrlicht/MacOSX/CIrrDeviceMacOSX.mm index 6e78cd2d..216f7574 100644 --- a/source/Irrlicht/MacOSX/CIrrDeviceMacOSX.mm +++ b/source/Irrlicht/MacOSX/CIrrDeviceMacOSX.mm @@ -1,629 +1,631 @@ -// Copyright (C) 2005 Etienne Petitjean -// This file is part of the "Irrlicht Engine". -// For conditions of distribution and use, see copyright notice in Irrlicht.h - -#ifdef MACOSX - -#import -#import - -#include "CIrrDeviceMacOSX.h" -#include "IEventReceiver.h" -#include "irrList.h" -#include "os.h" -#include "CTimer.h" -#include "irrString.h" -#include "Keycodes.h" -#include -#include -#include "COSOperator.h" -#include "irrlicht.h" -#import -#import -#import "AppDelegate.h" - -namespace irr -{ - namespace video - { - IVideoDriver* createOpenGLDriver(const core::dimension2d& screenSize, CIrrDeviceMacOSX *device, bool fullscreen, bool stencilBuffer, io::IFileSystem* io, bool vsync, bool antiAlias); - } -} // end namespace irr - -static bool firstLaunch = true; - -namespace irr -{ -//! constructor -CIrrDeviceMacOSX::CIrrDeviceMacOSX(video::E_DRIVER_TYPE driverType, - const core::dimension2d& windowSize, - u32 bits, bool fullscreen, - bool sbuffer, bool vsync, - bool antiAlias, IEventReceiver* receiver, - const char* version) - : CIrrDeviceStub(version, receiver), DriverType(driverType), stencilbuffer(sbuffer), _window(NULL), _active(true), _oglcontext(NULL), _cglcontext(NULL) -{ - struct utsname name; - NSString *path; - - #ifdef _DEBUG - setDebugName("CIrrDeviceMacOSX"); - #endif - - if (firstLaunch) - { - firstLaunch = false; - - [[NSAutoreleasePool alloc] init]; - [NSApplication sharedApplication]; - [NSApp setDelegate:[[[AppDelegate alloc] initWithDevice:this] autorelease]]; - [NSBundle loadNibNamed:@"MainMenu" owner:[NSApp delegate]]; - [NSApp finishLaunching]; - - path = [[[NSBundle mainBundle] bundlePath] stringByDeletingLastPathComponent]; - chdir([path cString]); - } - - uname(&name); - Operator = new COSOperator(name.version); - os::Printer::log(name.version,ELL_INFORMATION); - - initKeycodes(); - if (driverType != video::EDT_NULL) createWindow(windowSize,bits,fullscreen,vsync,stencilbuffer); - CursorControl = new CCursorControl(windowSize, this); - createDriver(driverType,windowSize,bits,fullscreen,stencilbuffer,vsync,antiAlias); - createGUIAndScene(); -} - -CIrrDeviceMacOSX::~CIrrDeviceMacOSX() -{ - closeDevice(); -} - -void CIrrDeviceMacOSX::closeDevice() -{ - if (_window != NULL) - { - [_window setIsVisible:FALSE]; - - if (_oglcontext != NULL) - { - [_oglcontext clearDrawable]; - [_oglcontext release]; - _oglcontext = NULL; - } - - [_window setReleasedWhenClosed:TRUE]; - [_window release]; - _window = NULL; - } - else - { - if (_cglcontext != NULL) - { - CGLSetCurrentContext(NULL); - CGLClearDrawable(_cglcontext); - CGLDestroyContext(_cglcontext); - } - } - - _active = FALSE; - _cglcontext = NULL; -} - -bool CIrrDeviceMacOSX::createWindow(const irr::core::dimension2d& windowSize, irr::u32 bits, bool fullscreen, bool vsync, bool stencilBuffer) -{ - int index; - CGDisplayErr error; - bool result; - NSOpenGLPixelFormat *format; - CGDirectDisplayID display; - CGLPixelFormatObj pixelFormat; - CGRect displayRect; - CGLPixelFormatAttribute fullattribs[32]; - NSOpenGLPixelFormatAttribute windowattribs[32]; - CFDictionaryRef displaymode,olddisplaymode; - long numPixelFormats,newSwapInterval; - - result = false; - display = CGMainDisplayID(); - _screenWidth = (int) CGDisplayPixelsWide(display); - _screenHeight = (int) CGDisplayPixelsHigh(display); - - if (!fullscreen) - { - _window = [[NSWindow alloc] initWithContentRect:NSMakeRect(0,0,windowSize.Width,windowSize.Height) styleMask:NSTitledWindowMask+NSClosableWindowMask+NSResizableWindowMask backing:NSBackingStoreBuffered defer:FALSE]; - if (_window != NULL) - { - index = 0; - windowattribs[index++] = NSOpenGLPFANoRecovery; - windowattribs[index++] = NSOpenGLPFADoubleBuffer; - windowattribs[index++] = NSOpenGLPFAAccelerated; - windowattribs[index++] = NSOpenGLPFADepthSize; - windowattribs[index++] = (NSOpenGLPixelFormatAttribute)16; - windowattribs[index++] = NSOpenGLPFAColorSize; - windowattribs[index++] = (NSOpenGLPixelFormatAttribute)bits; - - if (stencilBuffer) - { - windowattribs[index++] = NSOpenGLPFAStencilSize; - windowattribs[index++] = (NSOpenGLPixelFormatAttribute)1; - } - - windowattribs[index++] = (NSOpenGLPixelFormatAttribute)NULL; - - format = [[NSOpenGLPixelFormat alloc] initWithAttributes:windowattribs]; - if (format != NULL) - { - _oglcontext = [[NSOpenGLContext alloc] initWithFormat:format shareContext:NULL]; - [format release]; - } - - if (_oglcontext != NULL) - { - [_window center]; - [_window setDelegate:[NSApp delegate]]; - [_oglcontext setView:[_window contentView]]; - [_window setAcceptsMouseMovedEvents:TRUE]; - [_window setIsVisible:TRUE]; - [_window makeKeyAndOrderFront:nil]; - - _cglcontext = (CGLContextObj) [_oglcontext CGLContextObj]; - _width = windowSize.Width; - _height = windowSize.Height; - result = true; - } - } - } - else - { - displaymode = CGDisplayBestModeForParameters(display,bits,windowSize.Width,windowSize.Height,NULL); - if (displaymode != NULL) - { - olddisplaymode = CGDisplayCurrentMode(display); - error = CGCaptureAllDisplays(); - if (error == CGDisplayNoErr) - { - error = CGDisplaySwitchToMode(display,displaymode); - if (error == CGDisplayNoErr) - { - pixelFormat = NULL; - numPixelFormats = 0; - - index = 0; - fullattribs[index++] = kCGLPFAFullScreen; - fullattribs[index++] = kCGLPFADisplayMask; - fullattribs[index++] = (CGLPixelFormatAttribute)CGDisplayIDToOpenGLDisplayMask(display); - fullattribs[index++] = kCGLPFADoubleBuffer; - fullattribs[index++] = kCGLPFAAccelerated; - fullattribs[index++] = kCGLPFADepthSize; - fullattribs[index++] = (CGLPixelFormatAttribute)16; - fullattribs[index++] = kCGLPFAColorSize; - fullattribs[index++] = (CGLPixelFormatAttribute)bits; - - if (stencilBuffer) - { - fullattribs[index++] = kCGLPFAStencilSize; - fullattribs[index++] = (CGLPixelFormatAttribute)1; - } - - fullattribs[index++] = (CGLPixelFormatAttribute)NULL; - CGLChoosePixelFormat(fullattribs,&pixelFormat,&numPixelFormats); - - if (pixelFormat != NULL) - { - CGLCreateContext(pixelFormat,NULL,&_cglcontext); - CGLDestroyPixelFormat(pixelFormat); - } - - if (_cglcontext != NULL) - { - CGLSetFullScreen(_cglcontext); - displayRect = CGDisplayBounds(display); - _width = (int)displayRect.size.width; - _height = (int)displayRect.size.height; - result = true; - } - } - } - } - } - - if (result) - { - CGLSetCurrentContext(_cglcontext); - newSwapInterval = (vsync) ? 1 : 0; - CGLSetParameter(_cglcontext,kCGLCPSwapInterval,&newSwapInterval); - glViewport(0,0,_width,_height); - glMatrixMode(GL_PROJECTION); - glLoadIdentity(); - glMatrixMode(GL_MODELVIEW); - glLoadIdentity(); - } - - return (result); -} - -void CIrrDeviceMacOSX::setResize(int width,int height) -{ - _width = width; - _height = height; - [_oglcontext update]; - getVideoDriver()->OnResize(core::dimension2d(width, height)); -} - -void CIrrDeviceMacOSX::createDriver(video::E_DRIVER_TYPE driverType,const core::dimension2d& windowSize,u32 bits,bool fullscreen,bool stencilbuffer, bool vsync, bool antiAlias) -{ - switch (driverType) - { - case video::EDT_SOFTWARE: - #ifdef _IRR_COMPILE_WITH_SOFTWARE_ - VideoDriver = video::createSoftwareDriver(windowSize, fullscreen, FileSystem, this); - #else - os::Printer::log("No Software driver support compiled in.", ELL_ERROR); - #endif - break; - - case video::EDT_BURNINGSVIDEO: - #ifdef _IRR_COMPILE_WITH_BURNINGSVIDEO_ - VideoDriver = video::createSoftwareDriver2(windowSize, fullscreen, FileSystem, this); - #else - os::Printer::log("Burning's video driver was not compiled in.", ELL_ERROR); - #endif - break; - - case video::EDT_OPENGL: - #ifdef _IRR_COMPILE_WITH_OPENGL_ - VideoDriver = video::createOpenGLDriver(windowSize, this, fullscreen, stencilbuffer, FileSystem, vsync, antiAlias); - #else - os::Printer::log("No OpenGL support compiled in.", ELL_ERROR); - #endif - break; - - case video::EDT_DIRECT3D8: - case video::EDT_DIRECT3D9: - os::Printer::log("This driver is not available in OSX. Try OpenGL or Software renderer.", ELL_ERROR); - break; - - case video::EDT_NULL: - VideoDriver = video::createNullDriver(FileSystem, windowSize); - break; - - default: - os::Printer::log("Unable to create video driver of unknown type.", ELL_ERROR); - break; - } -} - -void CIrrDeviceMacOSX::flush() -{ - if (_cglcontext != NULL) - { - glFinish(); - CGLFlushDrawable(_cglcontext); - } -} - -bool CIrrDeviceMacOSX::run() -{ - NSEvent *event; - irr::SEvent ievent; - - os::Timer::tick(); - storeMouseLocation(); - - event = [NSApp nextEventMatchingMask:NSAnyEventMask untilDate:nil inMode:NSDefaultRunLoopMode dequeue:YES]; - if (event != nil) - { - bzero(&ievent,sizeof(ievent)); - - switch([event type]) - { - case NSKeyDown: - postKeyEvent(event,ievent,true); - break; - - case NSKeyUp: - postKeyEvent(event,ievent,false); - break; - - case NSLeftMouseDown: - ievent.EventType = irr::EET_MOUSE_INPUT_EVENT; - ievent.MouseInput.Event = irr::EMIE_LMOUSE_PRESSED_DOWN; - postMouseEvent(event,ievent); - break; - - case NSLeftMouseUp: - ievent.EventType = irr::EET_MOUSE_INPUT_EVENT; - ievent.MouseInput.Event = irr::EMIE_LMOUSE_LEFT_UP; - postMouseEvent(event,ievent); - break; - - case NSMouseMoved: - case NSLeftMouseDragged: - case NSRightMouseDragged: - ievent.EventType = irr::EET_MOUSE_INPUT_EVENT; - ievent.MouseInput.Event = irr::EMIE_MOUSE_MOVED; - postMouseEvent(event,ievent); - break; - - case NSRightMouseDown: - ievent.EventType = irr::EET_MOUSE_INPUT_EVENT; - ievent.MouseInput.Event = irr::EMIE_RMOUSE_PRESSED_DOWN; - postMouseEvent(event,ievent); - break; - - case NSRightMouseUp: - ievent.EventType = irr::EET_MOUSE_INPUT_EVENT; - ievent.MouseInput.Event = irr::EMIE_RMOUSE_LEFT_UP; - postMouseEvent(event,ievent); - break; - - case NSScrollWheel: - ievent.EventType = irr::EET_MOUSE_INPUT_EVENT; - ievent.MouseInput.Event = irr::EMIE_MOUSE_WHEEL; - ievent.MouseInput.Wheel = [event deltaY]; - if (ievent.MouseInput.Wheel < 1.0f) ievent.MouseInput.Wheel *= 10.0f; - else ievent.MouseInput.Wheel *= 5.0f; - postMouseEvent(event,ievent); - break; - - default: - [NSApp sendEvent:event]; - break; - } - } - - return (![[NSApp delegate] isQuit] && _active); -} - -//! Pause the current process for the minimum time allowed only to allow other processes to execute -void CIrrDeviceMacOSX::yield() -{ - // TODO: Does this work or maybe is there a better way? - struct timespec ts = {0,0}; - nanosleep(&ts, NULL); -} - -//! Pause execution and let other processes to run for a specified amount of time. -void CIrrDeviceMacOSX::sleep(u32 timeMs, bool pauseTimer=false) -{ - // TODO: Does this work or maybe is there a better way? - - bool wasStopped = Timer ? Timer->isStopped() : true; - - struct timespec ts; - ts.tv_sec = (time_t) (timeMs / 1000); - ts.tv_nsec = (long) (timeMs % 1000) * 1000000; - - if (pauseTimer && !wasStopped) - Timer->stop(); - - nanosleep(&ts, NULL); - - if (pauseTimer && !wasStopped) - Timer->start(); -} - -void CIrrDeviceMacOSX::present(video::IImage* image, s32 windowId, core::rect* src ) -{ -} - -void CIrrDeviceMacOSX::setWindowCaption(const wchar_t* text) -{ - size_t size; - char title[1024]; - - if (_window != NULL) - { - size = wcstombs(title,text,1024); - if (size == 1024) title[1023] = 0; - [_window setTitle:[NSString stringWithCString:title length:size]]; - } -} - -bool CIrrDeviceMacOSX::isWindowActive() const -{ - return (_active); -} - -void CIrrDeviceMacOSX::postKeyEvent(void *event,irr::SEvent &ievent,bool pressed) -{ - NSString *str; - std::map::const_iterator iter; - unsigned int result,c,mkey,mchar; - const unsigned char *cStr; - BOOL skipCommand; - - str = [event characters]; - if (str != nil && [str length] > 0) - { - mkey = mchar = 0; - skipCommand = false; - c = [str characterAtIndex:0]; - - iter = _keycodes.find(c); - if (iter != _keycodes.end()) mkey = (*iter).second; - else - { - cStr = (unsigned char *)[str cStringUsingEncoding:NSWindowsCP1252StringEncoding]; - if (cStr != NULL && strlen((char*)cStr) > 0) - { - mchar = cStr[0]; - mkey = toupper(mchar); - if ([event modifierFlags] & NSCommandKeyMask) - { - if (mkey == 'C' || mkey == 'V' || mkey == 'X') - { - mchar = 0; - skipCommand = true; - } - } - } - } - - ievent.EventType = irr::EET_KEY_INPUT_EVENT; - ievent.KeyInput.Key = (irr::EKEY_CODE)mkey; - ievent.KeyInput.PressedDown = pressed; - ievent.KeyInput.Shift = ([event modifierFlags] & NSShiftKeyMask) != 0; - ievent.KeyInput.Control = ([event modifierFlags] & NSControlKeyMask) != 0; - ievent.KeyInput.Char = (irr::EKEY_CODE)mchar; - - if (skipCommand) - ievent.KeyInput.Control = true; - else if ([event modifierFlags] & NSCommandKeyMask) - [NSApp sendEvent:(NSEvent *)event]; - - postEventFromUser(ievent); - } -} - -void CIrrDeviceMacOSX::postMouseEvent(void *event,irr::SEvent &ievent) -{ - BOOL post = true; - - if (_window != NULL) - { - ievent.MouseInput.X = (int)[event locationInWindow].x; - ievent.MouseInput.Y = _height - (int)[event locationInWindow].y; - if (ievent.MouseInput.Y < 0) post = false; - } - else - { - ievent.MouseInput.X = (int)[NSEvent mouseLocation].x; - ievent.MouseInput.Y = _height - (int)[NSEvent mouseLocation].y; - } - - if (post) postEventFromUser(ievent); - [NSApp sendEvent:(NSEvent *)event]; -} - -void CIrrDeviceMacOSX::storeMouseLocation() -{ - NSPoint p; - int x,y; - - p = [NSEvent mouseLocation]; - - if (_window != NULL) - { - p = [_window convertScreenToBase:p]; - x = (int)p.x; - y = _height - (int)p.y; - } - else - { - x = (int)p.x; - y = _screenHeight - (int)p.y; - } - - ((CCursorControl *)CursorControl)->updateInternalCursorPosition(x,y); -} - -void CIrrDeviceMacOSX::setMouseLocation(int x,int y) -{ - NSPoint p; - CGPoint c; - - if (_window != NULL) - { - p.x = (float) x; - p.y = (float) (_height - y); - p = [_window convertBaseToScreen:p]; - p.y = _screenHeight - p.y; - } - else - { - p.x = (float) x; - p.y = (float) (_height - y); - } - - c.x = p.x; - c.y = p.y; - CGSetLocalEventsSuppressionInterval(0); - CGWarpMouseCursorPosition(c); -} - -void CIrrDeviceMacOSX::setCursorVisible(bool visible) -{ - CGDirectDisplayID display; - - display = CGMainDisplayID(); - if (visible) CGDisplayShowCursor(display); - else CGDisplayHideCursor(display); -} - -void CIrrDeviceMacOSX::initKeycodes() -{ - _keycodes[NSUpArrowFunctionKey] = irr::KEY_UP; - _keycodes[NSDownArrowFunctionKey] = irr::KEY_DOWN; - _keycodes[NSLeftArrowFunctionKey] = irr::KEY_LEFT; - _keycodes[NSRightArrowFunctionKey] = irr::KEY_RIGHT; - _keycodes[NSF1FunctionKey] = irr::KEY_F1; - _keycodes[NSF2FunctionKey] = irr::KEY_F2; - _keycodes[NSF3FunctionKey] = irr::KEY_F3; - _keycodes[NSF4FunctionKey] = irr::KEY_F4; - _keycodes[NSF5FunctionKey] = irr::KEY_F5; - _keycodes[NSF6FunctionKey] = irr::KEY_F6; - _keycodes[NSF7FunctionKey] = irr::KEY_F7; - _keycodes[NSF8FunctionKey] = irr::KEY_F8; - _keycodes[NSF9FunctionKey] = irr::KEY_F9; - _keycodes[NSF10FunctionKey] = irr::KEY_F10; - _keycodes[NSF11FunctionKey] = irr::KEY_F11; - _keycodes[NSF12FunctionKey] = irr::KEY_F12; - _keycodes[NSF13FunctionKey] = irr::KEY_F13; - _keycodes[NSF14FunctionKey] = irr::KEY_F14; - _keycodes[NSF15FunctionKey] = irr::KEY_F15; - _keycodes[NSF16FunctionKey] = irr::KEY_F16; - _keycodes[NSHomeFunctionKey] = irr::KEY_HOME; - _keycodes[NSEndFunctionKey] = irr::KEY_END; - _keycodes[NSInsertFunctionKey] = irr::KEY_INSERT; - _keycodes[NSDeleteFunctionKey] = irr::KEY_DELETE; - _keycodes[NSHelpFunctionKey] = irr::KEY_HELP; - _keycodes[NSSelectFunctionKey] = irr::KEY_SELECT; - _keycodes[NSPrintFunctionKey] = irr::KEY_PRINT; - _keycodes[NSExecuteFunctionKey] = irr::KEY_EXECUT; - _keycodes[NSPrintScreenFunctionKey] = irr::KEY_SNAPSHOT; - _keycodes[NSPauseFunctionKey] = irr::KEY_PAUSE; - _keycodes[NSScrollLockFunctionKey] = irr::KEY_SCROLL; - _keycodes[0x7F] = irr::KEY_BACK; - _keycodes[0x09] = irr::KEY_TAB; - _keycodes[0x0D] = irr::KEY_RETURN; - _keycodes[0x03] = irr::KEY_RETURN; - _keycodes[0x1B] = irr::KEY_ESCAPE; -} - -//! Sets if the window should be resizeable in windowed mode. - -void CIrrDeviceMacOSX::setResizeAble(bool resize) -{ - // todo: implement resize -} - - -IRRLICHT_API IrrlichtDevice* IRRCALLCONV createDeviceEx(const SIrrlichtCreationParameters& param) -{ - CIrrDeviceMacOSX* dev = new CIrrDeviceMacOSX( - param.DriverType, - param.WindowSize, - param.Bits, - param.Fullscreen, - param.Stencilbuffer, - param.Vsync, - param.AntiAlias, - param.EventReceiver, - param.SDK_version_do_not_use); - - if (dev && !dev->getVideoDriver() && param.DriverType != video::EDT_NULL) - { - dev->drop(); - dev = 0; - } - - return dev; -} - -} - -#endif - +// Copyright (C) 2005 Etienne Petitjean +// This file is part of the "Irrlicht Engine". +// For conditions of distribution and use, see copyright notice in Irrlicht.h + +#include "IrrCompileConfig.h" + +#ifdef _IRR_USE_OSX_DEVICE_ + +#import +#import + +#include "CIrrDeviceMacOSX.h" +#include "IEventReceiver.h" +#include "irrList.h" +#include "os.h" +#include "CTimer.h" +#include "irrString.h" +#include "Keycodes.h" +#include +#include +#include "COSOperator.h" +#include "irrlicht.h" +#import +#import +#import "AppDelegate.h" + +namespace irr +{ + namespace video + { + IVideoDriver* createOpenGLDriver(const core::dimension2d& screenSize, CIrrDeviceMacOSX *device, bool fullscreen, bool stencilBuffer, io::IFileSystem* io, bool vsync, bool antiAlias); + } +} // end namespace irr + +static bool firstLaunch = true; + +namespace irr +{ +//! constructor +CIrrDeviceMacOSX::CIrrDeviceMacOSX(video::E_DRIVER_TYPE driverType, + const core::dimension2d& windowSize, + u32 bits, bool fullscreen, + bool sbuffer, bool vsync, + bool antiAlias, IEventReceiver* receiver, + const char* version) + : CIrrDeviceStub(version, receiver), DriverType(driverType), stencilbuffer(sbuffer), _window(NULL), _active(true), _oglcontext(NULL), _cglcontext(NULL) +{ + struct utsname name; + NSString *path; + + #ifdef _DEBUG + setDebugName("CIrrDeviceMacOSX"); + #endif + + if (firstLaunch) + { + firstLaunch = false; + + [[NSAutoreleasePool alloc] init]; + [NSApplication sharedApplication]; + [NSApp setDelegate:[[[AppDelegate alloc] initWithDevice:this] autorelease]]; + [NSBundle loadNibNamed:@"MainMenu" owner:[NSApp delegate]]; + [NSApp finishLaunching]; + + path = [[[NSBundle mainBundle] bundlePath] stringByDeletingLastPathComponent]; + chdir([path cString]); + } + + uname(&name); + Operator = new COSOperator(name.version); + os::Printer::log(name.version,ELL_INFORMATION); + + initKeycodes(); + if (driverType != video::EDT_NULL) createWindow(windowSize,bits,fullscreen,vsync,stencilbuffer); + CursorControl = new CCursorControl(windowSize, this); + createDriver(driverType,windowSize,bits,fullscreen,stencilbuffer,vsync,antiAlias); + createGUIAndScene(); +} + +CIrrDeviceMacOSX::~CIrrDeviceMacOSX() +{ + closeDevice(); +} + +void CIrrDeviceMacOSX::closeDevice() +{ + if (_window != NULL) + { + [_window setIsVisible:FALSE]; + + if (_oglcontext != NULL) + { + [_oglcontext clearDrawable]; + [_oglcontext release]; + _oglcontext = NULL; + } + + [_window setReleasedWhenClosed:TRUE]; + [_window release]; + _window = NULL; + } + else + { + if (_cglcontext != NULL) + { + CGLSetCurrentContext(NULL); + CGLClearDrawable(_cglcontext); + CGLDestroyContext(_cglcontext); + } + } + + _active = FALSE; + _cglcontext = NULL; +} + +bool CIrrDeviceMacOSX::createWindow(const irr::core::dimension2d& windowSize, irr::u32 bits, bool fullscreen, bool vsync, bool stencilBuffer) +{ + int index; + CGDisplayErr error; + bool result; + NSOpenGLPixelFormat *format; + CGDirectDisplayID display; + CGLPixelFormatObj pixelFormat; + CGRect displayRect; + CGLPixelFormatAttribute fullattribs[32]; + NSOpenGLPixelFormatAttribute windowattribs[32]; + CFDictionaryRef displaymode,olddisplaymode; + long numPixelFormats,newSwapInterval; + + result = false; + display = CGMainDisplayID(); + _screenWidth = (int) CGDisplayPixelsWide(display); + _screenHeight = (int) CGDisplayPixelsHigh(display); + + if (!fullscreen) + { + _window = [[NSWindow alloc] initWithContentRect:NSMakeRect(0,0,windowSize.Width,windowSize.Height) styleMask:NSTitledWindowMask+NSClosableWindowMask+NSResizableWindowMask backing:NSBackingStoreBuffered defer:FALSE]; + if (_window != NULL) + { + index = 0; + windowattribs[index++] = NSOpenGLPFANoRecovery; + windowattribs[index++] = NSOpenGLPFADoubleBuffer; + windowattribs[index++] = NSOpenGLPFAAccelerated; + windowattribs[index++] = NSOpenGLPFADepthSize; + windowattribs[index++] = (NSOpenGLPixelFormatAttribute)16; + windowattribs[index++] = NSOpenGLPFAColorSize; + windowattribs[index++] = (NSOpenGLPixelFormatAttribute)bits; + + if (stencilBuffer) + { + windowattribs[index++] = NSOpenGLPFAStencilSize; + windowattribs[index++] = (NSOpenGLPixelFormatAttribute)1; + } + + windowattribs[index++] = (NSOpenGLPixelFormatAttribute)NULL; + + format = [[NSOpenGLPixelFormat alloc] initWithAttributes:windowattribs]; + if (format != NULL) + { + _oglcontext = [[NSOpenGLContext alloc] initWithFormat:format shareContext:NULL]; + [format release]; + } + + if (_oglcontext != NULL) + { + [_window center]; + [_window setDelegate:[NSApp delegate]]; + [_oglcontext setView:[_window contentView]]; + [_window setAcceptsMouseMovedEvents:TRUE]; + [_window setIsVisible:TRUE]; + [_window makeKeyAndOrderFront:nil]; + + _cglcontext = (CGLContextObj) [_oglcontext CGLContextObj]; + _width = windowSize.Width; + _height = windowSize.Height; + result = true; + } + } + } + else + { + displaymode = CGDisplayBestModeForParameters(display,bits,windowSize.Width,windowSize.Height,NULL); + if (displaymode != NULL) + { + olddisplaymode = CGDisplayCurrentMode(display); + error = CGCaptureAllDisplays(); + if (error == CGDisplayNoErr) + { + error = CGDisplaySwitchToMode(display,displaymode); + if (error == CGDisplayNoErr) + { + pixelFormat = NULL; + numPixelFormats = 0; + + index = 0; + fullattribs[index++] = kCGLPFAFullScreen; + fullattribs[index++] = kCGLPFADisplayMask; + fullattribs[index++] = (CGLPixelFormatAttribute)CGDisplayIDToOpenGLDisplayMask(display); + fullattribs[index++] = kCGLPFADoubleBuffer; + fullattribs[index++] = kCGLPFAAccelerated; + fullattribs[index++] = kCGLPFADepthSize; + fullattribs[index++] = (CGLPixelFormatAttribute)16; + fullattribs[index++] = kCGLPFAColorSize; + fullattribs[index++] = (CGLPixelFormatAttribute)bits; + + if (stencilBuffer) + { + fullattribs[index++] = kCGLPFAStencilSize; + fullattribs[index++] = (CGLPixelFormatAttribute)1; + } + + fullattribs[index++] = (CGLPixelFormatAttribute)NULL; + CGLChoosePixelFormat(fullattribs,&pixelFormat,&numPixelFormats); + + if (pixelFormat != NULL) + { + CGLCreateContext(pixelFormat,NULL,&_cglcontext); + CGLDestroyPixelFormat(pixelFormat); + } + + if (_cglcontext != NULL) + { + CGLSetFullScreen(_cglcontext); + displayRect = CGDisplayBounds(display); + _width = (int)displayRect.size.width; + _height = (int)displayRect.size.height; + result = true; + } + } + } + } + } + + if (result) + { + CGLSetCurrentContext(_cglcontext); + newSwapInterval = (vsync) ? 1 : 0; + CGLSetParameter(_cglcontext,kCGLCPSwapInterval,&newSwapInterval); + glViewport(0,0,_width,_height); + glMatrixMode(GL_PROJECTION); + glLoadIdentity(); + glMatrixMode(GL_MODELVIEW); + glLoadIdentity(); + } + + return (result); +} + +void CIrrDeviceMacOSX::setResize(int width,int height) +{ + _width = width; + _height = height; + [_oglcontext update]; + getVideoDriver()->OnResize(core::dimension2d(width, height)); +} + +void CIrrDeviceMacOSX::createDriver(video::E_DRIVER_TYPE driverType,const core::dimension2d& windowSize,u32 bits,bool fullscreen,bool stencilbuffer, bool vsync, bool antiAlias) +{ + switch (driverType) + { + case video::EDT_SOFTWARE: + #ifdef _IRR_COMPILE_WITH_SOFTWARE_ + VideoDriver = video::createSoftwareDriver(windowSize, fullscreen, FileSystem, this); + #else + os::Printer::log("No Software driver support compiled in.", ELL_ERROR); + #endif + break; + + case video::EDT_BURNINGSVIDEO: + #ifdef _IRR_COMPILE_WITH_BURNINGSVIDEO_ + VideoDriver = video::createSoftwareDriver2(windowSize, fullscreen, FileSystem, this); + #else + os::Printer::log("Burning's video driver was not compiled in.", ELL_ERROR); + #endif + break; + + case video::EDT_OPENGL: + #ifdef _IRR_COMPILE_WITH_OPENGL_ + VideoDriver = video::createOpenGLDriver(windowSize, this, fullscreen, stencilbuffer, FileSystem, vsync, antiAlias); + #else + os::Printer::log("No OpenGL support compiled in.", ELL_ERROR); + #endif + break; + + case video::EDT_DIRECT3D8: + case video::EDT_DIRECT3D9: + os::Printer::log("This driver is not available in OSX. Try OpenGL or Software renderer.", ELL_ERROR); + break; + + case video::EDT_NULL: + VideoDriver = video::createNullDriver(FileSystem, windowSize); + break; + + default: + os::Printer::log("Unable to create video driver of unknown type.", ELL_ERROR); + break; + } +} + +void CIrrDeviceMacOSX::flush() +{ + if (_cglcontext != NULL) + { + glFinish(); + CGLFlushDrawable(_cglcontext); + } +} + +bool CIrrDeviceMacOSX::run() +{ + NSEvent *event; + irr::SEvent ievent; + + os::Timer::tick(); + storeMouseLocation(); + + event = [NSApp nextEventMatchingMask:NSAnyEventMask untilDate:nil inMode:NSDefaultRunLoopMode dequeue:YES]; + if (event != nil) + { + bzero(&ievent,sizeof(ievent)); + + switch([event type]) + { + case NSKeyDown: + postKeyEvent(event,ievent,true); + break; + + case NSKeyUp: + postKeyEvent(event,ievent,false); + break; + + case NSLeftMouseDown: + ievent.EventType = irr::EET_MOUSE_INPUT_EVENT; + ievent.MouseInput.Event = irr::EMIE_LMOUSE_PRESSED_DOWN; + postMouseEvent(event,ievent); + break; + + case NSLeftMouseUp: + ievent.EventType = irr::EET_MOUSE_INPUT_EVENT; + ievent.MouseInput.Event = irr::EMIE_LMOUSE_LEFT_UP; + postMouseEvent(event,ievent); + break; + + case NSMouseMoved: + case NSLeftMouseDragged: + case NSRightMouseDragged: + ievent.EventType = irr::EET_MOUSE_INPUT_EVENT; + ievent.MouseInput.Event = irr::EMIE_MOUSE_MOVED; + postMouseEvent(event,ievent); + break; + + case NSRightMouseDown: + ievent.EventType = irr::EET_MOUSE_INPUT_EVENT; + ievent.MouseInput.Event = irr::EMIE_RMOUSE_PRESSED_DOWN; + postMouseEvent(event,ievent); + break; + + case NSRightMouseUp: + ievent.EventType = irr::EET_MOUSE_INPUT_EVENT; + ievent.MouseInput.Event = irr::EMIE_RMOUSE_LEFT_UP; + postMouseEvent(event,ievent); + break; + + case NSScrollWheel: + ievent.EventType = irr::EET_MOUSE_INPUT_EVENT; + ievent.MouseInput.Event = irr::EMIE_MOUSE_WHEEL; + ievent.MouseInput.Wheel = [event deltaY]; + if (ievent.MouseInput.Wheel < 1.0f) ievent.MouseInput.Wheel *= 10.0f; + else ievent.MouseInput.Wheel *= 5.0f; + postMouseEvent(event,ievent); + break; + + default: + [NSApp sendEvent:event]; + break; + } + } + + return (![[NSApp delegate] isQuit] && _active); +} + +//! Pause the current process for the minimum time allowed only to allow other processes to execute +void CIrrDeviceMacOSX::yield() +{ + // TODO: Does this work or maybe is there a better way? + struct timespec ts = {0,0}; + nanosleep(&ts, NULL); +} + +//! Pause execution and let other processes to run for a specified amount of time. +void CIrrDeviceMacOSX::sleep(u32 timeMs, bool pauseTimer=false) +{ + // TODO: Does this work or maybe is there a better way? + + bool wasStopped = Timer ? Timer->isStopped() : true; + + struct timespec ts; + ts.tv_sec = (time_t) (timeMs / 1000); + ts.tv_nsec = (long) (timeMs % 1000) * 1000000; + + if (pauseTimer && !wasStopped) + Timer->stop(); + + nanosleep(&ts, NULL); + + if (pauseTimer && !wasStopped) + Timer->start(); +} + +void CIrrDeviceMacOSX::present(video::IImage* image, s32 windowId, core::rect* src ) +{ +} + +void CIrrDeviceMacOSX::setWindowCaption(const wchar_t* text) +{ + size_t size; + char title[1024]; + + if (_window != NULL) + { + size = wcstombs(title,text,1024); + if (size == 1024) title[1023] = 0; + [_window setTitle:[NSString stringWithCString:title length:size]]; + } +} + +bool CIrrDeviceMacOSX::isWindowActive() const +{ + return (_active); +} + +void CIrrDeviceMacOSX::postKeyEvent(void *event,irr::SEvent &ievent,bool pressed) +{ + NSString *str; + std::map::const_iterator iter; + unsigned int result,c,mkey,mchar; + const unsigned char *cStr; + BOOL skipCommand; + + str = [event characters]; + if (str != nil && [str length] > 0) + { + mkey = mchar = 0; + skipCommand = false; + c = [str characterAtIndex:0]; + + iter = _keycodes.find(c); + if (iter != _keycodes.end()) mkey = (*iter).second; + else + { + cStr = (unsigned char *)[str cStringUsingEncoding:NSWindowsCP1252StringEncoding]; + if (cStr != NULL && strlen((char*)cStr) > 0) + { + mchar = cStr[0]; + mkey = toupper(mchar); + if ([event modifierFlags] & NSCommandKeyMask) + { + if (mkey == 'C' || mkey == 'V' || mkey == 'X') + { + mchar = 0; + skipCommand = true; + } + } + } + } + + ievent.EventType = irr::EET_KEY_INPUT_EVENT; + ievent.KeyInput.Key = (irr::EKEY_CODE)mkey; + ievent.KeyInput.PressedDown = pressed; + ievent.KeyInput.Shift = ([event modifierFlags] & NSShiftKeyMask) != 0; + ievent.KeyInput.Control = ([event modifierFlags] & NSControlKeyMask) != 0; + ievent.KeyInput.Char = (irr::EKEY_CODE)mchar; + + if (skipCommand) + ievent.KeyInput.Control = true; + else if ([event modifierFlags] & NSCommandKeyMask) + [NSApp sendEvent:(NSEvent *)event]; + + postEventFromUser(ievent); + } +} + +void CIrrDeviceMacOSX::postMouseEvent(void *event,irr::SEvent &ievent) +{ + BOOL post = true; + + if (_window != NULL) + { + ievent.MouseInput.X = (int)[event locationInWindow].x; + ievent.MouseInput.Y = _height - (int)[event locationInWindow].y; + if (ievent.MouseInput.Y < 0) post = false; + } + else + { + ievent.MouseInput.X = (int)[NSEvent mouseLocation].x; + ievent.MouseInput.Y = _height - (int)[NSEvent mouseLocation].y; + } + + if (post) postEventFromUser(ievent); + [NSApp sendEvent:(NSEvent *)event]; +} + +void CIrrDeviceMacOSX::storeMouseLocation() +{ + NSPoint p; + int x,y; + + p = [NSEvent mouseLocation]; + + if (_window != NULL) + { + p = [_window convertScreenToBase:p]; + x = (int)p.x; + y = _height - (int)p.y; + } + else + { + x = (int)p.x; + y = _screenHeight - (int)p.y; + } + + ((CCursorControl *)CursorControl)->updateInternalCursorPosition(x,y); +} + +void CIrrDeviceMacOSX::setMouseLocation(int x,int y) +{ + NSPoint p; + CGPoint c; + + if (_window != NULL) + { + p.x = (float) x; + p.y = (float) (_height - y); + p = [_window convertBaseToScreen:p]; + p.y = _screenHeight - p.y; + } + else + { + p.x = (float) x; + p.y = (float) (_height - y); + } + + c.x = p.x; + c.y = p.y; + CGSetLocalEventsSuppressionInterval(0); + CGWarpMouseCursorPosition(c); +} + +void CIrrDeviceMacOSX::setCursorVisible(bool visible) +{ + CGDirectDisplayID display; + + display = CGMainDisplayID(); + if (visible) CGDisplayShowCursor(display); + else CGDisplayHideCursor(display); +} + +void CIrrDeviceMacOSX::initKeycodes() +{ + _keycodes[NSUpArrowFunctionKey] = irr::KEY_UP; + _keycodes[NSDownArrowFunctionKey] = irr::KEY_DOWN; + _keycodes[NSLeftArrowFunctionKey] = irr::KEY_LEFT; + _keycodes[NSRightArrowFunctionKey] = irr::KEY_RIGHT; + _keycodes[NSF1FunctionKey] = irr::KEY_F1; + _keycodes[NSF2FunctionKey] = irr::KEY_F2; + _keycodes[NSF3FunctionKey] = irr::KEY_F3; + _keycodes[NSF4FunctionKey] = irr::KEY_F4; + _keycodes[NSF5FunctionKey] = irr::KEY_F5; + _keycodes[NSF6FunctionKey] = irr::KEY_F6; + _keycodes[NSF7FunctionKey] = irr::KEY_F7; + _keycodes[NSF8FunctionKey] = irr::KEY_F8; + _keycodes[NSF9FunctionKey] = irr::KEY_F9; + _keycodes[NSF10FunctionKey] = irr::KEY_F10; + _keycodes[NSF11FunctionKey] = irr::KEY_F11; + _keycodes[NSF12FunctionKey] = irr::KEY_F12; + _keycodes[NSF13FunctionKey] = irr::KEY_F13; + _keycodes[NSF14FunctionKey] = irr::KEY_F14; + _keycodes[NSF15FunctionKey] = irr::KEY_F15; + _keycodes[NSF16FunctionKey] = irr::KEY_F16; + _keycodes[NSHomeFunctionKey] = irr::KEY_HOME; + _keycodes[NSEndFunctionKey] = irr::KEY_END; + _keycodes[NSInsertFunctionKey] = irr::KEY_INSERT; + _keycodes[NSDeleteFunctionKey] = irr::KEY_DELETE; + _keycodes[NSHelpFunctionKey] = irr::KEY_HELP; + _keycodes[NSSelectFunctionKey] = irr::KEY_SELECT; + _keycodes[NSPrintFunctionKey] = irr::KEY_PRINT; + _keycodes[NSExecuteFunctionKey] = irr::KEY_EXECUT; + _keycodes[NSPrintScreenFunctionKey] = irr::KEY_SNAPSHOT; + _keycodes[NSPauseFunctionKey] = irr::KEY_PAUSE; + _keycodes[NSScrollLockFunctionKey] = irr::KEY_SCROLL; + _keycodes[0x7F] = irr::KEY_BACK; + _keycodes[0x09] = irr::KEY_TAB; + _keycodes[0x0D] = irr::KEY_RETURN; + _keycodes[0x03] = irr::KEY_RETURN; + _keycodes[0x1B] = irr::KEY_ESCAPE; +} + +//! Sets if the window should be resizeable in windowed mode. + +void CIrrDeviceMacOSX::setResizeAble(bool resize) +{ + // todo: implement resize +} + + +IRRLICHT_API IrrlichtDevice* IRRCALLCONV createDeviceEx(const SIrrlichtCreationParameters& param) +{ + CIrrDeviceMacOSX* dev = new CIrrDeviceMacOSX( + param.DriverType, + param.WindowSize, + param.Bits, + param.Fullscreen, + param.Stencilbuffer, + param.Vsync, + param.AntiAlias, + param.EventReceiver, + param.SDK_version_do_not_use); + + if (dev && !dev->getVideoDriver() && param.DriverType != video::EDT_NULL) + { + dev->drop(); + dev = 0; + } + + return dev; +} + +} + +#endif // _IRR_USE_OSX_DEVICE_ + diff --git a/source/Irrlicht/MacOSX/MacOSX.xcodeproj/project.pbxproj b/source/Irrlicht/MacOSX/MacOSX.xcodeproj/project.pbxproj index 1045f211..545b3eb0 100644 --- a/source/Irrlicht/MacOSX/MacOSX.xcodeproj/project.pbxproj +++ b/source/Irrlicht/MacOSX/MacOSX.xcodeproj/project.pbxproj @@ -1155,7 +1155,7 @@ 4C53E18D0A484C2C0014E966 /* uncompr.c */ = {isa = PBXFileReference; fileEncoding = 30; lastKnownFileType = sourcecode.c.c; path = uncompr.c; sourceTree = ""; }; 4C53E1920A484C2C0014E966 /* zutil.c */ = {isa = PBXFileReference; fileEncoding = 30; lastKnownFileType = sourcecode.c.c; path = zutil.c; sourceTree = ""; }; 4C53E24D0A4850120014E966 /* libIrrlicht.a */ = {isa = PBXFileReference; explicitFileType = archive.ar; includeInIndex = 0; path = libIrrlicht.a; sourceTree = BUILT_PRODUCTS_DIR; }; - 4C53E2520A4850550014E966 /* Quake3Map.app */ = {isa = PBXFileReference; explicitFileType = wrapper.application; includeInIndex = 0; path = Quake3Map.app; sourceTree = BUILT_PRODUCTS_DIR; }; + 4C53E2520A4850550014E966 /* Quake3Map_dbg.app */ = {isa = PBXFileReference; explicitFileType = wrapper.application; includeInIndex = 0; path = Quake3Map_dbg.app; sourceTree = BUILT_PRODUCTS_DIR; }; 4C53E26D0A4850D60014E966 /* Cocoa.framework */ = {isa = PBXFileReference; lastKnownFileType = wrapper.framework; name = Cocoa.framework; path = /System/Library/Frameworks/Cocoa.framework; sourceTree = ""; }; 4C53E26E0A4850D60014E966 /* OpenGL.framework */ = {isa = PBXFileReference; lastKnownFileType = wrapper.framework; name = OpenGL.framework; path = /System/Library/Frameworks/OpenGL.framework; sourceTree = ""; }; 4C53E38E0A4855BA0014E966 /* DemoApp-Info.plist */ = {isa = PBXFileReference; fileEncoding = 30; lastKnownFileType = text.xml; path = "DemoApp-Info.plist"; sourceTree = ""; }; @@ -1219,18 +1219,18 @@ 4C53E76F0A485CD90014E966 /* wrrle.c */ = {isa = PBXFileReference; fileEncoding = 30; lastKnownFileType = sourcecode.c.c; path = wrrle.c; sourceTree = ""; }; 4C53E7700A485CD90014E966 /* wrtarga.c */ = {isa = PBXFileReference; fileEncoding = 30; lastKnownFileType = sourcecode.c.c; path = wrtarga.c; sourceTree = ""; }; 4C6DC9B60A48715A0017A6E5 /* inflate.c */ = {isa = PBXFileReference; fileEncoding = 30; lastKnownFileType = sourcecode.c.c; path = inflate.c; sourceTree = ""; }; - 4CA25B980A485D9800B4E469 /* CustomSceneNode.app */ = {isa = PBXFileReference; explicitFileType = wrapper.application; includeInIndex = 0; path = CustomSceneNode.app; sourceTree = BUILT_PRODUCTS_DIR; }; - 4CA25B9A0A485D9800B4E469 /* MeshViewer.app */ = {isa = PBXFileReference; explicitFileType = wrapper.application; includeInIndex = 0; path = MeshViewer.app; sourceTree = BUILT_PRODUCTS_DIR; }; - 4CA25B9C0A485D9800B4E469 /* RenderToTexture.app */ = {isa = PBXFileReference; explicitFileType = wrapper.application; includeInIndex = 0; path = RenderToTexture.app; sourceTree = BUILT_PRODUCTS_DIR; }; - 4CA25B9E0A485D9800B4E469 /* UserInterface.app */ = {isa = PBXFileReference; explicitFileType = wrapper.application; includeInIndex = 0; path = UserInterface.app; sourceTree = BUILT_PRODUCTS_DIR; }; - 4CA25BA00A485D9800B4E469 /* PerPixelLighting.app */ = {isa = PBXFileReference; explicitFileType = wrapper.application; includeInIndex = 0; path = PerPixelLighting.app; sourceTree = BUILT_PRODUCTS_DIR; }; - 4CA25BA20A485D9800B4E469 /* Demo.app */ = {isa = PBXFileReference; explicitFileType = wrapper.application; includeInIndex = 0; path = Demo.app; sourceTree = BUILT_PRODUCTS_DIR; }; - 4CA25BA40A485D9800B4E469 /* Movement.app */ = {isa = PBXFileReference; explicitFileType = wrapper.application; includeInIndex = 0; path = Movement.app; sourceTree = BUILT_PRODUCTS_DIR; }; - 4CA25BA60A485D9800B4E469 /* Shaders.app */ = {isa = PBXFileReference; explicitFileType = wrapper.application; includeInIndex = 0; path = Shaders.app; sourceTree = BUILT_PRODUCTS_DIR; }; - 4CA25BA80A485D9800B4E469 /* SpecialFx.app */ = {isa = PBXFileReference; explicitFileType = wrapper.application; includeInIndex = 0; path = SpecialFx.app; sourceTree = BUILT_PRODUCTS_DIR; }; - 4CA25BAA0A485D9800B4E469 /* TerrainRendering.app */ = {isa = PBXFileReference; explicitFileType = wrapper.application; includeInIndex = 0; path = TerrainRendering.app; sourceTree = BUILT_PRODUCTS_DIR; }; - 4CA25BAC0A485D9800B4E469 /* 2DGraphics.app */ = {isa = PBXFileReference; explicitFileType = wrapper.application; includeInIndex = 0; path = 2DGraphics.app; sourceTree = BUILT_PRODUCTS_DIR; }; - 4CA25BAE0A485D9800B4E469 /* Collision.app */ = {isa = PBXFileReference; explicitFileType = wrapper.application; includeInIndex = 0; path = Collision.app; sourceTree = BUILT_PRODUCTS_DIR; }; + 4CA25B980A485D9800B4E469 /* CustomSceneNode_dbg.app */ = {isa = PBXFileReference; explicitFileType = wrapper.application; includeInIndex = 0; path = CustomSceneNode_dbg.app; sourceTree = BUILT_PRODUCTS_DIR; }; + 4CA25B9A0A485D9800B4E469 /* MeshViewer_dbg.app */ = {isa = PBXFileReference; explicitFileType = wrapper.application; includeInIndex = 0; path = MeshViewer_dbg.app; sourceTree = BUILT_PRODUCTS_DIR; }; + 4CA25B9C0A485D9800B4E469 /* RenderToTexture_dbg.app */ = {isa = PBXFileReference; explicitFileType = wrapper.application; includeInIndex = 0; path = RenderToTexture_dbg.app; sourceTree = BUILT_PRODUCTS_DIR; }; + 4CA25B9E0A485D9800B4E469 /* UserInterface_dbg.app */ = {isa = PBXFileReference; explicitFileType = wrapper.application; includeInIndex = 0; path = UserInterface_dbg.app; sourceTree = BUILT_PRODUCTS_DIR; }; + 4CA25BA00A485D9800B4E469 /* PerPixelLighting_dbg.app */ = {isa = PBXFileReference; includeInIndex = 0; lastKnownFileType = wrapper.application; path = PerPixelLighting_dbg.app; sourceTree = BUILT_PRODUCTS_DIR; }; + 4CA25BA20A485D9800B4E469 /* Demo_dbg.app */ = {isa = PBXFileReference; explicitFileType = wrapper.application; includeInIndex = 0; path = Demo_dbg.app; sourceTree = BUILT_PRODUCTS_DIR; }; + 4CA25BA40A485D9800B4E469 /* Movement_dbg.app */ = {isa = PBXFileReference; explicitFileType = wrapper.application; includeInIndex = 0; path = Movement_dbg.app; sourceTree = BUILT_PRODUCTS_DIR; }; + 4CA25BA60A485D9800B4E469 /* Shaders_dbg.app */ = {isa = PBXFileReference; includeInIndex = 0; lastKnownFileType = wrapper.application; path = Shaders_dbg.app; sourceTree = BUILT_PRODUCTS_DIR; }; + 4CA25BA80A485D9800B4E469 /* SpecialFx_dbg.app */ = {isa = PBXFileReference; explicitFileType = wrapper.application; includeInIndex = 0; path = SpecialFx_dbg.app; sourceTree = BUILT_PRODUCTS_DIR; }; + 4CA25BAA0A485D9800B4E469 /* TerrainRendering_dbg.app */ = {isa = PBXFileReference; explicitFileType = wrapper.application; includeInIndex = 0; path = TerrainRendering_dbg.app; sourceTree = BUILT_PRODUCTS_DIR; }; + 4CA25BAC0A485D9800B4E469 /* 2DGraphics_dbg.app */ = {isa = PBXFileReference; explicitFileType = wrapper.application; includeInIndex = 0; path = 2DGraphics_dbg.app; sourceTree = BUILT_PRODUCTS_DIR; }; + 4CA25BAE0A485D9800B4E469 /* Collision_dbg.app */ = {isa = PBXFileReference; explicitFileType = wrapper.application; includeInIndex = 0; path = Collision_dbg.app; sourceTree = BUILT_PRODUCTS_DIR; }; 4CC36B0D0A6B61DB0076C4B2 /* CSphereSceneNode.cpp */ = {isa = PBXFileReference; fileEncoding = 30; lastKnownFileType = sourcecode.cpp.cpp; path = CSphereSceneNode.cpp; sourceTree = ""; }; 4CC36B0E0A6B61DB0076C4B2 /* CSphereSceneNode.h */ = {isa = PBXFileReference; fileEncoding = 30; lastKnownFileType = sourcecode.c.h; path = CSphereSceneNode.h; sourceTree = ""; }; 4CFA7BDC0A88735900B03626 /* CImageLoaderBMP.cpp */ = {isa = PBXFileReference; fileEncoding = 30; lastKnownFileType = sourcecode.cpp.cpp; lineEnding = 2; path = CImageLoaderBMP.cpp; sourceTree = ""; }; @@ -2588,19 +2588,19 @@ isa = PBXGroup; children = ( 4C53E24D0A4850120014E966 /* libIrrlicht.a */, - 4C53E2520A4850550014E966 /* Quake3Map.app */, - 4CA25B980A485D9800B4E469 /* CustomSceneNode.app */, - 4CA25BA40A485D9800B4E469 /* Movement.app */, - 4CA25B9E0A485D9800B4E469 /* UserInterface.app */, - 4CA25BAC0A485D9800B4E469 /* 2DGraphics.app */, - 4CA25BAE0A485D9800B4E469 /* Collision.app */, - 4CA25BA80A485D9800B4E469 /* SpecialFx.app */, - 4CA25B9A0A485D9800B4E469 /* MeshViewer.app */, - 4CA25BA60A485D9800B4E469 /* Shaders.app */, - 4CA25BA00A485D9800B4E469 /* PerPixelLighting.app */, - 4CA25B9C0A485D9800B4E469 /* RenderToTexture.app */, - 4CA25BAA0A485D9800B4E469 /* TerrainRendering.app */, - 4CA25BA20A485D9800B4E469 /* Demo.app */, + 4C53E2520A4850550014E966 /* Quake3Map_dbg.app */, + 4CA25B980A485D9800B4E469 /* CustomSceneNode_dbg.app */, + 4CA25BA40A485D9800B4E469 /* Movement_dbg.app */, + 4CA25B9E0A485D9800B4E469 /* UserInterface_dbg.app */, + 4CA25BAC0A485D9800B4E469 /* 2DGraphics_dbg.app */, + 4CA25BAE0A485D9800B4E469 /* Collision_dbg.app */, + 4CA25BA80A485D9800B4E469 /* SpecialFx_dbg.app */, + 4CA25B9A0A485D9800B4E469 /* MeshViewer_dbg.app */, + 4CA25BA60A485D9800B4E469 /* Shaders_dbg.app */, + 4CA25BA00A485D9800B4E469 /* PerPixelLighting_dbg.app */, + 4CA25B9C0A485D9800B4E469 /* RenderToTexture_dbg.app */, + 4CA25BAA0A485D9800B4E469 /* TerrainRendering_dbg.app */, + 4CA25BA20A485D9800B4E469 /* Demo_dbg.app */, 09F6493E0D2CE03E001E0599 /* LoadIrrFile.app */, 09F649650D2CE206001E0599 /* Quake3Shader.app */, 09F649030D2CDED9001E0599 /* HelloWorld.app */, @@ -2828,7 +2828,7 @@ ); name = 2DGraphics; productName = DemoApp; - productReference = 4CA25BAC0A485D9800B4E469 /* 2DGraphics.app */; + productReference = 4CA25BAC0A485D9800B4E469 /* 2DGraphics_dbg.app */; productType = "com.apple.product-type.application"; }; B81CFE82097FDDE20057C06F /* Collision */ = { @@ -2846,7 +2846,7 @@ ); name = Collision; productName = DemoApp; - productReference = 4CA25BAE0A485D9800B4E469 /* Collision.app */; + productReference = 4CA25BAE0A485D9800B4E469 /* Collision_dbg.app */; productType = "com.apple.product-type.application"; }; B81CFEA4097FDE900057C06F /* PerPixelLightning */ = { @@ -2864,7 +2864,7 @@ ); name = PerPixelLightning; productName = DemoApp; - productReference = 4CA25BA00A485D9800B4E469 /* PerPixelLighting.app */; + productReference = 4CA25BA00A485D9800B4E469 /* PerPixelLighting_dbg.app */; productType = "com.apple.product-type.application"; }; B81CFEC2097FDF020057C06F /* TerrainRendering */ = { @@ -2882,7 +2882,7 @@ ); name = TerrainRendering; productName = DemoApp; - productReference = 4CA25BAA0A485D9800B4E469 /* TerrainRendering.app */; + productReference = 4CA25BAA0A485D9800B4E469 /* TerrainRendering_dbg.app */; productType = "com.apple.product-type.application"; }; B81CFEE8097FE05F0057C06F /* SpecialFx */ = { @@ -2900,7 +2900,7 @@ ); name = SpecialFx; productName = DemoApp; - productReference = 4CA25BA80A485D9800B4E469 /* SpecialFx.app */; + productReference = 4CA25BA80A485D9800B4E469 /* SpecialFx_dbg.app */; productType = "com.apple.product-type.application"; }; B81CFF07097FE13E0057C06F /* UserInterface */ = { @@ -2918,7 +2918,7 @@ ); name = UserInterface; productName = DemoApp; - productReference = 4CA25B9E0A485D9800B4E469 /* UserInterface.app */; + productReference = 4CA25B9E0A485D9800B4E469 /* UserInterface_dbg.app */; productType = "com.apple.product-type.application"; }; B81CFF1E097FE1E00057C06F /* CustomSceneNode */ = { @@ -2936,7 +2936,7 @@ ); name = CustomSceneNode; productName = DemoApp; - productReference = 4CA25B980A485D9800B4E469 /* CustomSceneNode.app */; + productReference = 4CA25B980A485D9800B4E469 /* CustomSceneNode_dbg.app */; productType = "com.apple.product-type.application"; }; B81CFF33097FE25F0057C06F /* Quake3Map */ = { @@ -2954,7 +2954,7 @@ ); name = Quake3Map; productName = DemoApp; - productReference = 4C53E2520A4850550014E966 /* Quake3Map.app */; + productReference = 4C53E2520A4850550014E966 /* Quake3Map_dbg.app */; productType = "com.apple.product-type.application"; }; B81CFF4A097FE3050057C06F /* Shaders */ = { @@ -2972,7 +2972,7 @@ ); name = Shaders; productName = DemoApp; - productReference = 4CA25BA60A485D9800B4E469 /* Shaders.app */; + productReference = 4CA25BA60A485D9800B4E469 /* Shaders_dbg.app */; productType = "com.apple.product-type.application"; }; B81CFF78097FE3DC0057C06F /* Movement */ = { @@ -2990,7 +2990,7 @@ ); name = Movement; productName = DemoApp; - productReference = 4CA25BA40A485D9800B4E469 /* Movement.app */; + productReference = 4CA25BA40A485D9800B4E469 /* Movement_dbg.app */; productType = "com.apple.product-type.application"; }; B81CFF91097FE45E0057C06F /* MeshViewer */ = { @@ -3008,7 +3008,7 @@ ); name = MeshViewer; productName = DemoApp; - productReference = 4CA25B9A0A485D9800B4E469 /* MeshViewer.app */; + productReference = 4CA25B9A0A485D9800B4E469 /* MeshViewer_dbg.app */; productType = "com.apple.product-type.application"; }; B81CFFAF097FE5F80057C06F /* RenderToTexture */ = { @@ -3026,7 +3026,7 @@ ); name = RenderToTexture; productName = DemoApp; - productReference = 4CA25B9C0A485D9800B4E469 /* RenderToTexture.app */; + productReference = 4CA25B9C0A485D9800B4E469 /* RenderToTexture_dbg.app */; productType = "com.apple.product-type.application"; }; B8DEF35C0950229200FDEA7E /* Demo */ = { @@ -3044,7 +3044,7 @@ ); name = Demo; productName = DemoApp; - productReference = 4CA25BA20A485D9800B4E469 /* Demo.app */; + productReference = 4CA25BA20A485D9800B4E469 /* Demo_dbg.app */; productType = "com.apple.product-type.application"; }; D2AAC07D0554694100DB518D /* libIrrlicht.a */ = { diff --git a/source/Irrlicht/SoftwareDriver2_helper.h b/source/Irrlicht/SoftwareDriver2_helper.h index 7f99bfdf..c0c4f3aa 100644 --- a/source/Irrlicht/SoftwareDriver2_helper.h +++ b/source/Irrlicht/SoftwareDriver2_helper.h @@ -145,12 +145,6 @@ REALINLINE u32 if_mask_a_else_b ( const u32 mask, const u32 a, const u32 b ) return ( mask & ( a ^ b ) ) ^ b; } -inline void setbits ( u32 &state, s32 condition, u32 mask ) -{ - state ^= ( ( -condition >> 31 ) ^ state ) & mask; -} - - // ------------------ Video--------------------------------------- /*! Pixel = dest * ( 1 - alpha ) + source * alpha diff --git a/source/Irrlicht/os.cpp b/source/Irrlicht/os.cpp index 69c98ecd..1d7535ce 100644 --- a/source/Irrlicht/os.cpp +++ b/source/Irrlicht/os.cpp @@ -21,7 +21,8 @@ #define bswap_32(X) ( (((X)&0x000000FF)<<24) | (((X)&0xFF000000) >> 24) | (((X)&0x0000FF00) << 8) | (((X) &0x00FF0000) >> 8)) #endif #else - #ifdef MACOSX + #if defined(_IRR_OSX_PLATFORM_) + #include #define bswap_16(X) OSReadSwapInt16(&X,0) #define bswap_32(X) OSReadSwapInt32(&X,0) #elif defined(__FreeBSD__)