// TextureLibDiag.cpp : implementation file
//

#include "stdafx.h"
#include "ImageGrinder.h"
#include "TextureLibDiag.h"
#include "ModifyPath.h"
#include "ImageCache.h"
#include "ImageGrinderDoc.h"
#include <Compost\TexturePool.hpp>
#include "..\..\Libraries\ImageLib\Image.h"
#include <GameOS\ToolOS.hpp>


extern CImageGrinderApp theApp;

/////////////////////////////////////////////////////////////////////////////
// CTextureLibDiag dialog
bool IsPowerOf2(int num);


CTextureLibDiag::CTextureLibDiag(CWnd* pParent /*=NULL*/)
: CDialog(CTextureLibDiag::IDD, pParent)
{
	//{{AFX_DATA_INIT(CTextureLibDiag)
	m_TexturePath = _T("");
	m_TSpace = _T("");
	//}}AFX_DATA_INIT
ImgTot=0;
for(int i=0;i<MAXTEXTURES;i++) 
	ImgLoaded[i]=false;

}


void CTextureLibDiag::DoDataExchange(CDataExchange* pDX)
{
	CDialog::DoDataExchange(pDX);
	//{{AFX_DATA_MAP(CTextureLibDiag)
	DDX_Control(pDX, IDC_TEXTURELIST, m_TextureList);
	DDX_Text(pDX, IDC_TEXTPATH, m_TexturePath);
	DDX_Text(pDX, IDC_TSPACE, m_TSpace);
	//}}AFX_DATA_MAP
}


BEGIN_MESSAGE_MAP(CTextureLibDiag, CDialog)
//{{AFX_MSG_MAP(CTextureLibDiag)
ON_BN_CLICKED(IDC_ADD, OnAdd)
ON_NOTIFY(LVN_BEGINDRAG, IDC_TEXTURELIST, OnBegindragTexturelist)
ON_BN_CLICKED(IDC_CHANGEPATH, OnChangepath)
ON_BN_CLICKED(IDC_DELETE, OnDelete)
	ON_BN_CLICKED(IDC_ADD1BIT, OnAdd1bit)
	ON_BN_CLICKED(IDC_ADDMIPMASK, OnAddmipmask)
	ON_BN_CLICKED(IDC_UPDATE, OnUpdate)
	//}}AFX_MSG_MAP
END_MESSAGE_MAP()

/////////////////////////////////////////////////////////////////////////////
// CTextureLibDiag message handlers

void CTextureLibDiag::OnOK() 
{
	// TODO: Add extra validation here
	
	//	CDialog::OnOK();
}

void CTextureLibDiag::OnCancel() 
{
	// TODO: Add extra cleanup here
	
	//	CDialog::OnCancel();
}

void CTextureLibDiag::OnAdd() 
{
	CFileDialog dlg(TRUE,NULL,NULL,OFN_ALLOWMULTISELECT,"Targa Images (*.tga)|*.tga||",NULL);
	char *filebuf=new char[MAX_PATH*200];
	filebuf[0]=0;
	dlg.m_ofn.lpstrFile=filebuf;
	dlg.m_ofn.nMaxFile=MAX_PATH*200;
	
	
	if(dlg.DoModal()==IDOK)
	{
		
		POSITION pos;
		pos=dlg.GetStartPosition();
		CString fname,SPath;
		
		
		while(pos!=NULL)
		{
			fname=dlg.GetNextPathName(pos);
			Image img;
			img.GetTgaInfo((char *)(LPCSTR)fname);

/*	We now allow for special features to load now power-of-2 images
			if(!IsPowerOf2(img.GetWidth()) || !IsPowerOf2(img.GetHeight()) )
			{
				MessageBox("Image Size Not Power of 2","Image Dim Error",MB_OK|MB_ICONERROR);
				return;
			}
*/			
			
			SPath=fname.Left(fname.ReverseFind('\\')+1);
			fname=fname.Right(fname.GetLength()-(fname.ReverseFind('\\')+1));
			if(NULL==CopyFile(SPath+fname,m_TexturePath+"\\"+fname,FALSE))
			{	//Copy Failed
				
			}
			fname = fname.Left(fname.ReverseFind('.'));
			
			Compost::Feature_Texture::TextureMode tmde;
			
			
			if(img.GetIType()==ITYPE_INDEXED)
			{
				tmde = Compost::Feature_Texture::FTT_1;
			}
			else
			{
				if(img.HasAlpha())
					tmde = Compost::Feature_Texture::FTT_4444;
				else
					tmde = Compost::Feature_Texture::FTT_555;
			}
			
			Compost::TexturePool::Instance->Add(
				Stuff::MString((LPCSTR)fname),
				img.GetWidth(),
				img.GetHeight(),
				tmde
				);	
		}
		
		
		delete filebuf;
	}
	RefreshList();
}

BOOL CTextureLibDiag::OnInitDialog() 
{
CDialog::OnInitDialog();
CDC *pDC=GetDC(),memdc;

UnLoadedBmp.CreateCompatibleBitmap(pDC,PREVIEWSZE,PREVIEWSZE);
memdc.CreateCompatibleDC(pDC);
memdc.SelectObject(UnLoadedBmp);
BOOL res=memdc.BitBlt(0,0,PREVIEWSZE,PREVIEWSZE,NULL,0,0,WHITENESS);
Verify(res!=0);
memdc.DeleteDC();
ReleaseDC(pDC);


	ImgLst.Create(PREVIEWSZE,PREVIEWSZE,ILC_COLOR24,16,16);
	m_TextureList.SetImageList(&ImgLst,LVSIL_NORMAL);   
	
	CString AppName;
	AppName.LoadString(AFX_IDS_APP_TITLE);
	CString tpath;
	tpath=theApp.GetProfileString("Settings","TexturePath","");
	if(tpath.GetLength()==0)
	{
		OnChangepath();
	}
	else
	{
		m_TexturePath=tpath;
		Compost::TexturePool::Instance->SetTexturePath(m_TexturePath);
		Compost::TexturePool::Instance->LoadIndex();
		RefreshList();
		UpdateData(FALSE);
	}

	if(gos_DoesFileExist(m_TexturePath+"\\Material.txt"))
	{
		Stuff::NotationFile mat_file(m_TexturePath+"\\Material.txt");
		Stuff::Page *page = mat_file.GetPage("Materials");
		Check_Object(page);

		Stuff::Page::NoteIterator *note_list=page->MakeNoteIterator();

		note_list->First();

		Stuff::Note *note;
		Compost::MaterialEntriesCount = 0;
		Stuff::RGBColor color;
		DWORD mat_color;
		while((note=note_list->ReadAndNext())!=NULL && Compost::MaterialEntriesCount<128)
		{
			Compost::MaterialEntries[Compost::MaterialEntriesCount].MatName=note->GetName();
			note->GetEntry(&color);

			Stuff::Scalar f;
			f = color.red * 255.99f;
			Clamp(f, 0.0f, 255.f);
			mat_color = Stuff::Truncate_Float_To_Byte (f);

			f = color.green * 255.99f;
			Clamp(f, 0.0f, 255.f);
			mat_color = (mat_color << 8) | Stuff::Truncate_Float_To_Byte (f);

			f = color.blue * 255.99f;
			Clamp(f, 0.0f, 255.f);
			mat_color = (mat_color << 8) | Stuff::Truncate_Float_To_Byte (f);

			Compost::MaterialEntries[Compost::MaterialEntriesCount].color = mat_color;
			Compost::MaterialEntries[Compost::MaterialEntriesCount].darkEntryIndex = Compost::MaterialEntriesCount;
			Compost::MaterialEntriesCount++;
		}

		page = mat_file.GetPage("Darkening");
		Check_Object(page);

		note_list=page->MakeNoteIterator();

		note_list->First();

		Stuff::MString name;
		const char *dark_name;

		while((note=note_list->ReadAndNext())!=NULL && Compost::MaterialEntriesCount<128)
		{
			name = note->GetName();

			if(!strcmp(name, "darkfactor"))
			{
				note->GetEntry(&Compost::DarkFactor);
			}
			else
			{
				note->GetEntry(&dark_name);
				for(int i=0;i<Compost::MaterialEntriesCount;i++)
				{
					if(name == Compost::MaterialEntries[i].MatName)
					{
						for(int j=0;j<Compost::MaterialEntriesCount;j++)
						{
							if(NULL==strcmp(dark_name, Compost::MaterialEntries[j].MatName))
							{
								Compost::MaterialEntries[i].darkEntryIndex = j;
								break;
							}
						}
						break;
					}
				}
			}
		}

	}
	else
	{
		Compost::MaterialEntriesCount=1;
		Compost::MaterialEntries[0].MatName="none";
		Compost::MaterialEntries[0].color = 0;
		Compost::MaterialEntries[0].darkEntryIndex = 0;
	}
	
//	while(LoadNextImage());
	return TRUE;  // return TRUE unless you set the focus to a control
	// EXCEPTION: OCX Property Pages should return FALSE
}

void CTextureLibDiag::OnBegindragTexturelist(NMHDR* pNMHDR, LRESULT* pResult) 
{
	NM_LISTVIEW* pNMListView = (NM_LISTVIEW*)pNMHDR;
	
	*pResult = 0;
}

void CTextureLibDiag::OnChangepath() 
{
	CModifyPath dlg;
	
	dlg.m_path=m_TexturePath;
	if(dlg.DoModal()==IDOK)
	{
		m_TexturePath=dlg.m_path;
		
		CString AppName;
		AppName.LoadString(AFX_IDS_APP_TITLE);
		theApp.WriteProfileString("Settings","TexturePath",m_TexturePath);
		Compost::TexturePool::Instance->SetTexturePath(m_TexturePath);
		Compost::TexturePool::Instance->LoadIndex();

		UpdateData(FALSE);
		RefreshList();
	}	
	
}

void CTextureLibDiag::RefreshList()
{
	Compost::Feature_Texture *FTexture;
	int CurImg=0,DataTotal=0,SubTot;
	m_TextureList.DeleteAllItems();
//	Image img2,img;
//	img.CreateBlank(PREVIEWSZE,PREVIEWSZE,ITYPE_RGB,24);
	CString fname;
	

	
	
	{	
		Stuff::TableIteratorOf<Compost::Feature_Texture*, int> imageTableIterator(Compost::TexturePool::Instance->GetImageTable());
		while(NULL!=(FTexture=imageTableIterator.ReadAndNext()))
		{
			LVITEM itm;
			fname=m_TexturePath;
			fname+="\\";
			fname+=(char *)(*(FTexture->GetName()));
			fname+=".tga";
			
			ZeroMemory(&itm,sizeof(LVITEM));
			itm.mask=LVIF_TEXT|LVIF_IMAGE|LVIF_PARAM;
			itm.iItem=1;
			itm.lParam=(long)FTexture;
			itm.pszText=(char *)(*(FTexture->GetName()));
			itm.iImage=GetIndex(fname);
			
			SubTot=FTexture->width*FTexture->height;
			if(FTexture->GetTextureMode() != Compost::Feature_Texture::TextureMode::FTT_1) 
			{	SubTot*=2; }
			DataTotal+=SubTot;
			CurImg++;
			m_TextureList.InsertItem(&itm);
		}
	}
	if(DataTotal<1000000)
		m_TSpace.Format("%3.2f KB",DataTotal/1000.0);
	else
		m_TSpace.Format("%3.2f MB",DataTotal/1000000.0);
	
	UpdateData(FALSE);
	if(!Compost::TexturePool::Instance->SaveIndex(NULL)) 
	{
		MessageBox("Index file is Read only, Texture Lib Changes will not be saved","Texture Lib Error",MB_OK|MB_ICONHAND);
	}
}


void
Compost::FetchTextureData(Compost::Feature_Texture *tex, int index, int type)
{
	tex->data = NULL;
	tex->handle = NULL;
	
	return;
}

void
Compost::FetchTextureData(Compost::Feature_Texture *tex, const char *name, int type)
{
	CString str(name);
	str+=".Tga";
	Image img, mip1, mip2;
	
	img.LoadTga((char *)(LPCSTR)str);
	
	switch(type & Compost::Feature_Texture::TextureTypeMask)
	{
		case Compost::Feature_Texture::TextureMode::FTT_555:
		{
			mip1.CreateBlank(img.GetWidth()/2,img.GetHeight()/2,ITYPE_RGB,32);
			mip1.Blt(img,CRect(0,0,mip1.GetWidth(),mip1.GetHeight()),CRect(0,0,img.GetWidth(),img.GetHeight()));
	//		mip1.SaveTiff("c:\\mp1.Tif");
			mip1.Pad(1);
			
			mip2.CreateBlank(img.GetWidth()/4,img.GetHeight()/4,ITYPE_RGB,32);
			mip2.Blt(img,CRect(0,0, mip2.GetWidth(), mip2.GetHeight()),CRect(0,0,img.GetWidth(),img.GetHeight()));
	//		mip2.SaveTiff("c:\\mp2.Tif");
			mip2.Pad(1);
		}
		break;
		case Compost::Feature_Texture::TextureMode::FTT_4444:
		{
			mip1.CreateBlank(img.GetWidth()/2,img.GetHeight()/2,ITYPE_RGB,32,RGBMask(0x00ff0000,0x0000ff00,0x000000ff,0xff000000));
			mip1.Blt(img,CRect(0,0,mip1.GetWidth(),mip1.GetHeight()),CRect(0,0,img.GetWidth(),img.GetHeight()));
//			mip1.SaveTiff("c:\\mp1.Tif");
			mip1.Pad(1);
			
			mip2.CreateBlank(img.GetWidth()/4,img.GetHeight()/4,ITYPE_RGB,32,RGBMask(0x00ff0000,0x0000ff00,0x000000ff,0xff000000));
			mip2.Blt(img,CRect(0,0, mip2.GetWidth(), mip2.GetHeight()),CRect(0,0,img.GetWidth(),img.GetHeight()));
//			mip2.SaveTiff("c:\\mp2.Tif");
			mip2.Pad(1);
		}
		break;
		case Compost::Feature_Texture::TextureMode::FTT_1_M:
		{
			mip1.CreateBlank(img.GetWidth()/2,img.GetHeight()/2,ITYPE_INDEXED, 8);
			mip1.Blt(img,CRect(0,0,mip1.GetWidth(),mip1.GetHeight()),CRect(0,0,img.GetWidth(),img.GetHeight()));

			mip1.MakeGrayscalePalette();
			mip1.Pad(1);
//			mip1.SaveGif("c:\\mp1.gif");
			
			mip2.CreateBlank(img.GetWidth()/4,img.GetHeight()/4,ITYPE_INDEXED, 8);
			mip2.Blt(img,CRect(0,0, mip2.GetWidth(), mip2.GetHeight()),CRect(0,0,img.GetWidth(),img.GetHeight()));

			mip2.MakeGrayscalePalette();
			mip2.Pad(1);
//			mip2.SaveGif("c:\\mp2.gif");
		}
		break;

		case Compost::Feature_Texture::TextureMode::FTT_1:
		case Compost::Feature_Texture::TextureMode::FTT_1_1:
		break;
	}

	if(type != Compost::Feature_Texture::TextureMode::FTT_1_1)
	{
		img.Pad(1);
	}
	
	switch(type & Compost::Feature_Texture::TextureTypeMask)
	{
		case Compost::Feature_Texture::TextureMode::FTT_555:
		{
			img.MakeRGB16(RGBMask(0x007C00,0x0003E0,0x00001f,0x00));
			mip1.MakeRGB16(RGBMask(0x007C00,0x0003E0,0x00001f,0x00));
			mip2.MakeRGB16(RGBMask(0x007C00,0x0003E0,0x00001f,0x00));
			//		img.MaskTo(RGBMask(0xff0000,0x00ff00,0x0000ff,0x00));
		}
		break;
		case Compost::Feature_Texture::TextureMode::FTT_4444:
		{
			img.MakeRGB16(RGBMask(0xF000,0xF00,0xF0,0xF));
			mip1.MakeRGB16(RGBMask(0xF000,0xF00,0xF0,0xF));
			mip2.MakeRGB16(RGBMask(0xF000,0xF00,0xF0,0xF));
			//		img.MaskTo(RGBMask(0xff000000,0x00ff0000,0x0000ff00,0x000000ff));
		}
		break;
		case Compost::Feature_Texture::TextureMode::FTT_1:
		break;
		case Compost::Feature_Texture::TextureMode::FTT_1_1:
		break;
	}
	
	int dsize;
	unsigned char *tdat = NULL;
	
	switch(type & Compost::Feature_Texture::TextureTypeMask)
	{
		case Compost::Feature_Texture::TextureMode::FTT_555:
		case Compost::Feature_Texture::TextureMode::FTT_4444:
		case Compost::Feature_Texture::TextureMode::FTT_1_M:
		{
			int dsize1, dsize2;
			
			dsize = (img.GetBpp()>>3)*img.GetWidth()*img.GetHeight();
			dsize1 = (mip1.GetBpp()>>3)*mip1.GetWidth()*mip1.GetHeight();
			dsize2 = (mip2.GetBpp()>>3)*mip2.GetWidth()*mip2.GetHeight();
		
			tex->dataSize = dsize + dsize1 + dsize2;
			tdat = new unsigned char[tex->dataSize];
			
			CopyMemory(tdat, img.Lock() , dsize);
			img.UnLock();
			
			CopyMemory(tdat+dsize, mip1.Lock() , dsize1);
			mip1.UnLock();
			
			CopyMemory(tdat+dsize+dsize1, mip2.Lock() , dsize2);
			mip2.UnLock();
		}
		break;
		case Compost::Feature_Texture::TextureMode::FTT_1:
		{
			dsize = (img.GetBpp()>>3)*img.GetWidth()*img.GetHeight();
			tex->dataSize = dsize;

			tdat = new unsigned char[tex->dataSize];
			CopyMemory(tdat, img.Lock() , dsize);
			img.UnLock();
		}	
		break;
		case Compost::Feature_Texture::TextureMode::FTT_1_1:
		{
			dsize = (img.GetBpp()>>3)*(2+ (img.GetWidth()>>3))*(2+img.GetHeight());
			tex->dataSize = dsize;

			tdat = new unsigned char[tex->dataSize];

			int i, j, k, mask=0;
			unsigned char *imgptr = img.Lock();
			unsigned char *tdatptr = tdat + (2+(img.GetWidth()>>3));

			for(i=0;i<img.GetHeight();i++)
			{
				if(*imgptr > 0x80)
				{
					*tdatptr = 0xff;
				}
				else
				{
					*tdatptr = 0x00;
				}
				tdatptr++;
				for(j=0;j<img.GetWidth();j+=8)
				{

					*tdatptr = 0;
					mask = 1;
					for(k=0;k<8;k++)
					{
						if(*imgptr>0x80)
						{
							*tdatptr |= mask;
						}
						mask <<= 1;
						imgptr++;
					}
					tdatptr++;
				}

				if(*(imgptr-1) > 0x80)
				{
					*tdatptr = 0xff;
				}
				else
				{
					*tdatptr = 0x00;
				}
				tdatptr++;
			}

			img.UnLock();

			CopyMemory(tdat, tdat + (2+(img.GetWidth()>>3)), (2+(img.GetWidth()>>3)));
			CopyMemory(tdatptr, tdatptr - (2+(img.GetWidth()>>3)), (2+(img.GetWidth()>>3)));

		}
		break;
	}
	
	if(tex->data!=NULL)
	{
		delete [] tex->data;
	}
	tex->data = tdat;
	tex->handle = NULL;
	
	return;
}

void
Compost::DestroyTextureData(Compost::Feature_Texture *tex)
{
	delete [] tex->data;
}

void CTextureLibDiag::OnDelete() 
{
	
	POSITION pos;
	pos=m_TextureList.GetFirstSelectedItemPosition();
	
	while(pos!=NULL)
	{
		int nItem = m_TextureList.GetNextSelectedItem(pos);
		Compost::Feature_Texture *feature_Texture = (Compost::Feature_Texture *)m_TextureList.GetItemData(nItem);
		bool used=false;
		int i;
		for(i=0;i<DocCount;i++)
		{
			used = (NULL != DocList[i]->FPool->IsUsed(feature_Texture)) ? true : false;

			if(used==true)
			{
				break;
			}
		}

		if(used==true)
		{
			MessageBox("Texture is currently in use and cannot be deleted\n Close Documment and try again","Delete Error",MB_OK|MB_ICONSTOP);
		}
		else
		{	
			Compost::TexturePool::Instance->Remove(feature_Texture);
		}
	}
	
	RefreshList();	
}


int CTextureLibDiag::GetIndex(CString fname)
{
	int i;
	for(i=0;i<ImgTot;i++) 
		if(!fname.CompareNoCase(ImageName[i])) 
			return i;
		
		return AddImage(fname);
}

bool CTextureLibDiag::LoadNextImage()
{
int nidx;

for(nidx=0;nidx<ImgTot && ImgLoaded[nidx];nidx++);
if(nidx>=ImgTot) return false;


CString fname=ImageName[nidx];
	
	CDC *pDC=GetDC();
	
	ImageChain *imgchn=CImageCache::Instance->GetChain(fname);
	Image *img=imgchn->GetTNImage();
	if(!img)
	{
	imgchn->BuildTNImg(PREVIEWSZE,PREVIEWSZE);
	img=imgchn->GetTNImage();
	}

  CBitmap *bmp=new CBitmap;
	
	bmp->CreateCompatibleBitmap(pDC,img->GetWidth(),img->GetHeight());
	CDC memDC;
	memDC.CreateCompatibleDC(pDC);
	HBITMAP hBmpOld = (HBITMAP)SelectObject(memDC, *bmp);
	
	BITMAPINFO       binf;
	ZeroMemory(&binf,sizeof(binf));
	binf.bmiHeader.biSize=sizeof(BITMAPINFOHEADER);
	binf.bmiHeader.biWidth=img->GetWidth(); 
	binf.bmiHeader.biHeight=-img->GetHeight();
	binf.bmiHeader.biPlanes=1;
	binf.bmiHeader.biBitCount=img->GetBpp();
	binf.bmiHeader.biCompression=BI_RGB;
				
				int res;
				res=SetDIBitsToDevice(memDC,0,0,img->GetWidth(),img->GetHeight(),0,0,0,img->GetHeight(),img->Lock(),&binf,DIB_RGB_COLORS);
				img->UnLock();
				if(res==0)
				{
					DWORD err;
					err=GetLastError();
				}
				Verify(res!=0);
				
				SelectObject(memDC, hBmpOld);
				memDC.DeleteDC();
				
				ImgLst.Replace(nidx,bmp,NULL);
				ImgLoaded[nidx]=true;
				ReleaseDC(pDC);
				delete bmp;
m_TextureList.InvalidateRect(NULL);
				return true;
}

int CTextureLibDiag::AddImage(CString fname)
{
	
				int idx=ImgLst.Add(&UnLoadedBmp,(COLORREF)0);
				ImageName[idx]=fname;
				ImgLoaded[idx]=false;
				ImgTot++;
				return idx;
}


bool IsPowerOf2(int X)
{
	return !( X & ( X - 1 ) );
}

void CTextureLibDiag::OnAdd1bit() 
{
	CFileDialog dlg(TRUE,NULL,NULL,OFN_ALLOWMULTISELECT,"Targa Images (*.tga)|*.tga||",NULL);
	char *filebuf=new char[MAX_PATH*200];
	filebuf[0]=0;
	dlg.m_ofn.lpstrFile=filebuf;
	dlg.m_ofn.nMaxFile=MAX_PATH*200;
	
	
	if(dlg.DoModal()==IDOK)
	{
		
		POSITION pos;
		pos=dlg.GetStartPosition();
		CString fname,SPath;
		
		
		while(pos!=NULL)
		{
			fname=dlg.GetNextPathName(pos);
			Image img;
			img.GetTgaInfo((char *)(LPCSTR)fname);
			
			if(img.GetBpp()!=8) 
			{
				MessageBox("Image is not 8 Bit","Image Depth Error",MB_OK|MB_ICONERROR);
				return;
			}
			
/*	We now allow for special features to load now power-of-2 images
			if(!IsPowerOf2(img.GetWidth()) || !IsPowerOf2(img.GetHeight()) )
			{
				MessageBox("Image Size Not Power of 2","Image Dim Error",MB_OK|MB_ICONERROR);
				return;
			}
*/			
			
			SPath=fname.Left(fname.ReverseFind('\\')+1);
			fname=fname.Right(fname.GetLength()-(fname.ReverseFind('\\')+1));
			if(NULL==CopyFile(SPath+fname,m_TexturePath+"\\"+fname,FALSE))
			{	//Copy Failed
				
			}
			fname = fname.Left(fname.ReverseFind('.'));
			
			Compost::Feature_Texture::TextureMode tmde;
			
			
			if(img.GetIType()==ITYPE_INDEXED)
			{
				tmde = Compost::Feature_Texture::FTT_1_1;
			}
			else
			{
				MessageBox("Image is not 8 Bit","Image Depth Error",MB_OK|MB_ICONERROR);
				return;
			}
			
			Compost::TexturePool::Instance->Add(
				Stuff::MString((LPCSTR)fname),
				img.GetWidth(),
				img.GetHeight(),
				tmde
				);	
		}
		
		
		delete filebuf;
	}
	RefreshList();
	
}

void CTextureLibDiag::OnAddmipmask() 
{
	CFileDialog dlg(TRUE,NULL,NULL,OFN_ALLOWMULTISELECT,"Targa Images (*.tga)|*.tga||",NULL);
	char *filebuf=new char[MAX_PATH*200];
	filebuf[0]=0;
	dlg.m_ofn.lpstrFile=filebuf;
	dlg.m_ofn.nMaxFile=MAX_PATH*200;
	
	if(dlg.DoModal()==IDOK)
	{
		POSITION pos;
		pos=dlg.GetStartPosition();
		CString fname,SPath;
		
		while(pos!=NULL)
		{
			fname=dlg.GetNextPathName(pos);
			Image img;
			img.GetTgaInfo((char *)(LPCSTR)fname);
			
			if(img.GetBpp()!=8) 
			{
				MessageBox("Image is not 8 Bit","Image Depth Error",MB_OK|MB_ICONERROR);
				return;
			}
			
/*	We now allow for special features to load now power-of-2 images
			if(!IsPowerOf2(img.GetWidth()) || !IsPowerOf2(img.GetHeight()) )
			{
				MessageBox("Image Size Not Power of 2","Image Dim Error",MB_OK|MB_ICONERROR);
				return;
			}
*/
  
			SPath=fname.Left(fname.ReverseFind('\\')+1);
			fname=fname.Right(fname.GetLength()-(fname.ReverseFind('\\')+1));
			if(NULL==CopyFile(SPath+fname,m_TexturePath+"\\"+fname,FALSE))
			{	//Copy Failed
				
			}
			fname = fname.Left(fname.ReverseFind('.'));
			
			Compost::Feature_Texture::TextureMode tmde;
				
			if(img.GetIType()==ITYPE_INDEXED)
			{
				tmde = Compost::Feature_Texture::FTT_1_M;
			}
			else
			{
				MessageBox("Image is not 8 Bit","Image Depth Error",MB_OK|MB_ICONERROR);
				return;
			}
			
			Compost::TexturePool::Instance->Add(
				Stuff::MString((LPCSTR)fname),
				img.GetWidth(),
				img.GetHeight(),
				tmde
				);	
		}
		
		delete filebuf;
	}
	RefreshList();
}

void CTextureLibDiag::OnUpdate() 
{
	
	POSITION pos;
	pos=m_TextureList.GetFirstSelectedItemPosition();
	
	while(pos!=NULL)
	{
		int nItem = m_TextureList.GetNextSelectedItem(pos);
		Compost::Feature_Texture *feature_Texture = (Compost::Feature_Texture *)m_TextureList.GetItemData(nItem);
	
		feature_Texture->SetLoadedOff();
		Compost::TexturePool::Instance->Load(feature_Texture);
	}

	for(int i=0;i<DocCount;i++)
	{
		DocList[i]->SetDrawFlags();
		DocList[i]->UpdateAllViews(NULL);
	}

	RefreshList();	
}

BOOL CTextureLibDiag::OnIdle()
{
return LoadNextImage();

}
