#include "MAXProxyHeaders.hpp" #include // //############################################################################ //############################# MAXTexture ############################## //############################################################################ // MemoryBlock* MAXTexture::AllocatedMemory = NULL; MAXTexture::ClassData* MAXTexture::DefaultData = NULL; //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // void MAXTexture::InitializeClass() { Verify(!AllocatedMemory); AllocatedMemory = new MemoryBlock( sizeof(MAXTexture), 10, 10, "MAXTexture" ); Register_Object(AllocatedMemory); Verify(!DefaultData); DefaultData = new ClassData( MAXTextureClassID, "MAXTexture", TextureProxy::DefaultData ); Register_Object(DefaultData); } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // void MAXTexture::TerminateClass() { Unregister_Object(DefaultData); delete DefaultData; DefaultData = NULL; Unregister_Object(AllocatedMemory); delete AllocatedMemory; AllocatedMemory = NULL; } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // void MAXTexture::Destroy() { Check_Object(this); Verify(referenceCount == 1); // Abort_Program("Not implemented"); DetachReference(); } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // MAXTexture::MAXTexture( MAXTextureLibrary *library, MAXScene *scene, int texture_index ): TextureProxy(DefaultData, library), proxiedScene(scene), textureIndex(texture_index) { Check_Object(this); textureName = NULL; origtextureName = NULL; textureSize.x = 0; textureSize.y = 0; redDepth = 0; greenDepth = 0; blueDepth = 0; alphaDepth = 0; formatHint = 0; textureFormat = Proxies::TextureProxy::AlphaTexture; } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // MAXTexture::~MAXTexture() { Check_Object(this); if (textureName) { Unregister_Pointer(textureName); delete[] textureName; } if (origtextureName) { Unregister_Pointer(origtextureName); delete[] origtextureName; } } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // void MAXTexture::TestInstance() const { Verify(IsDerivedFrom(DefaultData)); } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Proxies::TextureProxy* MAXTexture::UseNextTextureProxyInLibrary() { Check_Object(this); MAXTextureLibrary *library = GetTextureLibrary(); Check_Object(library); Verify(textureIndex != 0xFFFFFFFF); return library->UseTextureProxy(textureIndex+1); } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Proxies::TextureProxy* MAXTexture::UsePreviousTextureProxyInLibrary() { Check_Object(this); MAXTextureLibrary *library = GetTextureLibrary(); Check_Object(library); Verify(textureIndex != 0xFFFFFFFF); if (!textureIndex) return NULL; return library->UseTextureProxy(textureIndex-1); } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // bool MAXTexture::GetName(MString *filename) { Check_Object(this); Check_Pointer(filename); Check_Pointer(proxiedScene); // if (NULL == textureName) // { BitmapTex *bitmap = proxiedScene->bmpList.GetBitmap(textureIndex); if (NULL == bitmap) return false; Check_Pointer(bitmap); TCHAR *string = (char *)bitmap->GetMapName(); int len = strlen(string); MString name; if (len != 0) { name = string; } Verify(name); name.StripDirectory().StripExtension(); // // If we already stored this one... // if (origtextureName == NULL || name != origtextureName) { if (textureName) { Unregister_Pointer(textureName); delete[] textureName; textureName = NULL; } if (origtextureName) { Unregister_Pointer(origtextureName); delete[] origtextureName; origtextureName = NULL; } origtextureName = strdup(name); Page *page = proxiedScene->FindHint(name); if (page) { const char *entry; if (page->GetEntry("Alias",&entry)) { name = entry; } } else { int x=1; Verify(false); } textureName = strdup(name); Register_Pointer(textureName); } //} *filename = textureName; //Unregister_Pointer(textureName); return true; } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // void MAXTexture::SetName(const char* filename) { Check_Object(this); Check_Pointer(filename); Check_Pointer(proxiedScene); BitmapTex *bitmap = proxiedScene->bmpList.GetBitmap(textureIndex); Check_Pointer(bitmap); if (textureName) { Unregister_Pointer(textureName); delete[] textureName; } if (origtextureName) { Unregister_Pointer(origtextureName); delete[] origtextureName; } origtextureName = strdup(filename); textureName = strdup(filename); Register_Pointer(textureName); Register_Pointer(origtextureName); TCHAR *string = (TCHAR *)textureName; bitmap->SetMapName(string); } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // void MAXTexture::GetImageSize(Vector2DOf *size) { Check_Object(this); Check_Pointer(size); Check_Pointer(proxiedScene); BitmapTex *bitmap = proxiedScene->bmpList.GetBitmap(textureIndex); Check_Pointer(bitmap); Bitmap *bitmapinfo = bitmap->GetBitmap(proxiedScene->GetTime()); if (bitmapinfo) { Check_Pointer(bitmapinfo); size->x = bitmapinfo->Width(); size->y = bitmapinfo->Height(); textureSize.x = size->x; textureSize.y = size->y; } else { textureSize.x = 0; textureSize.y = 0; } } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // void MAXTexture::GetChannelDepth( unsigned *red_depth, unsigned *blue_depth, unsigned *green_depth, unsigned *alpha_depth ) { Check_Object(this); Check_Pointer(red_depth); Check_Pointer(blue_depth); Check_Pointer(green_depth); Check_Pointer(alpha_depth); Check_Pointer(proxiedScene); BitmapTex *bitmap = proxiedScene->bmpList.GetBitmap(textureIndex); Check_Pointer(bitmap); Bitmap *bitmapinfo = bitmap->GetBitmap(proxiedScene->GetTime()); if (bitmapinfo) { Check_Pointer(bitmapinfo); *red_depth = *blue_depth = *green_depth = 8; Bitmap *map = bitmap->GetBitmap(proxiedScene->GetTime()); if (map->HasAlpha()) { *alpha_depth = 8; } else { *alpha_depth = 0; } } else { *red_depth = *blue_depth = *green_depth = *alpha_depth = 0; } } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // void MAXTexture::GetChannels( Stuff::DynamicArrayOf *red, Stuff::DynamicArrayOf *green, Stuff::DynamicArrayOf *blue, Stuff::DynamicArrayOf *alpha ) { Check_Object(this); Verify(GetClassID() == MAXTextureClassID); Check_Object(red); Check_Object(green); Check_Object(blue); // //---------------------------------------------------- // Read the channels if they haven't already been read //---------------------------------------------------- // if (!redDepth) { ReadTexture(); } // //--------------------- // Now copy the channel //--------------------- // *red = redChannel; *green = greenChannel; *blue = blueChannel; if (alpha) { Check_Object(alpha); *alpha = alphaChannel; } } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // void MAXTexture::SetChannels( const DynamicArrayOf *red, const DynamicArrayOf *green, const DynamicArrayOf *blue, const DynamicArrayOf *alpha ) { Check_Object(this); Verify(GetClassID() == MAXTextureClassID); Check_Object(red); Check_Object(green); Check_Object(blue); // //--------------------- // Now copy the channel //--------------------- // Verify(red->GetLength() == textureSize.x*textureSize.y); redChannel = *red; redDepth = 8; Verify(green->GetLength() == textureSize.x*textureSize.y); greenChannel = *green; greenDepth = 8; Verify(blue->GetLength() == textureSize.x*textureSize.y); blueChannel = *blue; blueDepth = 8; if (alpha) { Check_Object(alpha); alphaChannel = *alpha; alphaDepth = 8; } else { alphaChannel.SetLength(0); alphaDepth = 0; } } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // void MAXTexture::ReadTexture() { Check_Object(this); Check_Pointer(proxiedScene); BitmapTex *bitmap = proxiedScene->bmpList.GetBitmap(textureIndex); Check_Pointer(bitmap); Bitmap *bitmapinfo = bitmap->GetBitmap(proxiedScene->GetTime()); if (!bitmapinfo) return; Check_Pointer(bitmapinfo); int width = bitmapinfo->Width(); int height = bitmapinfo->Height(); int num_pixels = width*height; int current_pixel = 0; bool has_alpha = false; Bitmap *map = bitmap->GetBitmap(proxiedScene->GetTime()); if (map->HasAlpha()) { has_alpha = true; } // // set the lenght of the arrays to hold the // color pixels // redChannel.SetLength(num_pixels); greenChannel.SetLength(num_pixels); blueChannel.SetLength(num_pixels); if (has_alpha) { alphaChannel.SetLength(num_pixels); } else { alphaChannel.SetLength(0); } // // get the pixel data from the bitmap and copy the data // to the array // BMM_Color_32 pixel_32; BMM_Color_64 pixel_64; int start_height = height-1; int start_width = width-1; for (int h=0;hGetPixels(w,h,1,&pixel_64); pixel_32.r = (BYTE)(pixel_64.r >> 8); pixel_32.g = (BYTE)(pixel_64.g >> 8); pixel_32.b = (BYTE)(pixel_64.b >> 8); if (has_alpha) { pixel_32.a = (BYTE)(pixel_64.a >> 8); } redChannel[current_pixel] = pixel_32.r; greenChannel[current_pixel] = pixel_32.g; blueChannel[current_pixel] = pixel_32.b; if (has_alpha) { alphaChannel[current_pixel] = pixel_32.a; } current_pixel++; } } if (!redDepth) { GetChannelDepth(&redDepth, &blueDepth, &greenDepth, &alphaDepth ); } } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // bool MAXTexture:: GetFormat(Proxies::TextureProxy::FormatType* format) { Check_Object(this); if (0==formatHint) { formatHint=1; Stuff::MString name; GetName(&name); MAXTextureLibrary *library = Cast_Object(MAXTextureLibrary*, GetTextureLibrary()); Check_Object(library); MAXStateLibrary *max_states = library->GetStateLibrary(); Check_Object(max_states); MAXScene *scene = max_states->GetSceneProxy(); Page *page = scene->FindHint(name); if (page) { const char *entry; if (page->GetEntry("Format",&entry)) { if (stricmp(entry,"Alpha")==0) { textureFormat = AlphaTexture; formatHint++; } else if (stricmp(entry,"Keyed")==0) { textureFormat = KeyedTexture; formatHint++; } } } } if (formatHint) { if (formatHint>1) { *format = textureFormat; return true; } } return false; } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // void MAXTexture:: SetFormat(Proxies::TextureProxy::FormatType format) { Check_Object(this); } // //############################################################################ //############################ MAXTexture ############################## //############################################################################ // MAXTextureLibrary::ClassData* MAXTextureLibrary::DefaultData = NULL; //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // void MAXTextureLibrary::InitializeClass() { Verify(!DefaultData); DefaultData = new ClassData( MAXTextureLibraryClassID, "MAXTextureLibrary", TextureLibrary::DefaultData ); Register_Object(DefaultData); } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // void MAXTextureLibrary::TerminateClass() { Unregister_Object(DefaultData); delete DefaultData; DefaultData = NULL; } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // void MAXTextureLibrary::Destroy() { Check_Object(this); Verify(referenceCount == 1); Verify(activeTextureProxies.IsEmpty()); STOP(("Not implemented")); DetachReference(); } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // MAXTextureLibrary::MAXTextureLibrary(MAXStateLibrary *states): Proxies::TextureLibrary(DefaultData, states) { Check_Pointer(this); MAXScene *scene = states->GetSceneProxy(); Check_Pointer(scene); textureCount = scene->GetBitmapCount(); textureProxies.SetLength(textureCount); lastTextureSearched = -1; MString name; for (unsigned i=0; iDestroy(); } } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // void MAXTextureLibrary::TestInstance() const { Verify(IsDerivedFrom(DefaultData)); } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // unsigned MAXTextureLibrary::GetTextureCount() { Check_Object(this); return textureCount; } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Proxies::TextureProxy* MAXTextureLibrary::UseNewTextureProxy() { Check_Object(this); STOP(("Not supported")); return NULL; } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Proxies::TextureProxy* MAXTextureLibrary::UseMatchingTextureProxy(Proxies::TextureProxy *texture) { Check_Object(this); Check_Object(texture); // //-------------------------------------------------- // Look to see if the last texture we found matches //-------------------------------------------------- // MAXTexture *proxy; if (lastTextureSearched != -1) { proxy = textureProxies[lastTextureSearched]; if (proxy->IsEqualTo(texture)) { Return_Proxy: proxy->AttachReference(); return proxy; } } // //------------------------------------------------------------------------- // Spin through our textures and check each one for a match. Skip the one // we have already checked //------------------------------------------------------------------------- // int i; unsigned count = GetTextureCount(); for (i=0; iIsEqualTo(texture)) { lastTextureSearched = i; goto Return_Proxy; } } // Didn't find the texture so we have to add it MAXScene *scene = GetStateLibrary()->GetSceneProxy(); i = textureCount; textureCount++; textureProxies.SetLength(textureCount); lastTextureSearched = -1; MString name; proxy = textureProxies[i] = MAXTexture::MakeProxy(this, scene, i); Register_Object(textureProxies[i]); if (proxy) goto Return_Proxy; return NULL; } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Proxies::TextureProxy* MAXTextureLibrary::UseTextureProxy(const char* texture_name) { return NULL; } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Proxies::TextureProxy* MAXTextureLibrary::UseFirstTextureProxy() { Check_Object(this); if (GetTextureCount() > 0) { textureProxies[0]->AttachReference(); return textureProxies[0]; } return NULL; } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Proxies::TextureProxy* MAXTextureLibrary::UseLastTextureProxy() { Check_Object(this); unsigned count = GetTextureCount(); if (count > 0) { textureProxies[count-1]->AttachReference(); return textureProxies[count-1]; } return NULL; } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // void MAXTextureLibrary::CloseLibrary() { Check_Object(this); unsigned count = GetTextureCount(); for (unsigned i=0; iGetReferenceCount() == 1); textureProxies[i]->DetachReference(); } Verify(GetReferenceCount() == 1); } //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // MAXTexture* MAXTextureLibrary::UseTextureProxy(int index) { Check_Object(this); // //------------------------------------------------------- // If we just looked off the end of the list, return NULL //------------------------------------------------------- // if (index >= GetTextureCount()) return NULL; // if this is just the next texture in the list and we haven't created it yet, then create it if (index == textureCount) { MAXScene *scene = GetStateLibrary()->GetSceneProxy(); textureCount++; textureProxies.SetLength(textureCount); lastTextureSearched = -1; textureProxies[index] = MAXTexture::MakeProxy(this, scene, index); Register_Object(textureProxies[index]); } // //------------------- // Return a new proxy //------------------- // textureProxies[index]->AttachReference(); return textureProxies[index]; }