1 /*
2 * HLLib
3 * Copyright (C) 2006-2010 Ryan Gregg
4
5 * This library is free software; you can redistribute it and/or
6 * modify it under the terms of the GNU Lesser General Public
7 * License as published by the Free Software Foundation; either
8 * version 2.1 of the License, or (at your option) any later
9 * version.
10 */
11
12 #include "HLLib.h"
13 #include "WADFile.h"
14 #include "Streams.h"
15
16 using namespace HLLib;
17
18 const char *CWADFile::lpAttributeNames[] = { "Version" };
19 const char *CWADFile::lpItemAttributeNames[] = { "Width", "Height", "Palette Entries", "Mipmaps", "Compressed", "Type" };
20
CWADFile()21 CWADFile::CWADFile() : CPackage(), pHeaderView(0), pLumpView(0), pHeader(0), lpLumps(0), lpLumpInfo(0)
22 {
23
24 }
25
~CWADFile()26 CWADFile::~CWADFile()
27 {
28 this->Close();
29 }
30
GetType() const31 HLPackageType CWADFile::GetType() const
32 {
33 return HL_PACKAGE_WAD;
34 }
35
GetExtension() const36 const hlChar *CWADFile::GetExtension() const
37 {
38 return "wad";
39 }
40
GetDescription() const41 const hlChar *CWADFile::GetDescription() const
42 {
43 return "Half-Life Texture Package File";
44 }
45
MapDataStructures()46 hlBool CWADFile::MapDataStructures()
47 {
48 if(sizeof(WADHeader) > this->pMapping->GetMappingSize())
49 {
50 LastError.SetErrorMessage("Invalid file: the file map is too small for it's header.");
51 return hlFalse;
52 }
53
54 if(!this->pMapping->Map(this->pHeaderView, 0, sizeof(WADHeader)))
55 {
56 return hlFalse;
57 }
58 this->pHeader = (WADHeader *)this->pHeaderView->GetView();
59
60 if(memcmp(this->pHeader->lpSignature, "WAD3", 4) != 0)
61 {
62 LastError.SetErrorMessage("Invalid file: the file's signature does not match.");
63 return hlFalse;
64 }
65
66 if(!this->pMapping->Map(this->pLumpView, this->pHeader->uiLumpOffset, this->pHeader->uiLumpCount * sizeof(WADLump)))
67 {
68 return hlFalse;
69 }
70 this->lpLumps = (WADLump *)this->pLumpView->GetView();
71
72 this->lpLumpInfo = new WADLumpInfo[this->pHeader->uiLumpCount];
73 memset(this->lpLumpInfo, 0, sizeof(WADLumpInfo) * this->pHeader->uiLumpCount);
74
75 return hlTrue;
76 }
77
UnmapDataStructures()78 hlVoid CWADFile::UnmapDataStructures()
79 {
80 delete []this->lpLumpInfo;
81
82 this->lpLumps = 0;
83 this->pMapping->Unmap(this->pLumpView);
84
85 this->pHeader = 0;
86 this->pMapping->Unmap(this->pHeaderView);
87 }
88
CreateRoot()89 CDirectoryFolder *CWADFile::CreateRoot()
90 {
91 CDirectoryFolder *pRoot = new CDirectoryFolder(this);
92
93 // Loop through each lump in the WAD file.
94 for(hlUInt i = 0; i < this->pHeader->uiLumpCount; i++)
95 {
96 hlChar lpName[64];
97 sprintf(lpName, "%s.bmp", this->lpLumps[i].lpName);
98
99 // Add the lump as a bitmap.
100 pRoot->AddFile(lpName, i);
101 }
102
103 return pRoot;
104 }
105
GetAttributeCountInternal() const106 hlUInt CWADFile::GetAttributeCountInternal() const
107 {
108 return HL_WAD_PACKAGE_COUNT;
109 }
110
GetAttributeNameInternal(HLPackageAttribute eAttribute) const111 const hlChar *CWADFile::GetAttributeNameInternal(HLPackageAttribute eAttribute) const
112 {
113 if(eAttribute < HL_WAD_PACKAGE_COUNT)
114 {
115 return this->lpAttributeNames[eAttribute];
116 }
117
118 return 0;
119 }
120
GetAttributeInternal(HLPackageAttribute eAttribute,HLAttribute & Attribute) const121 hlBool CWADFile::GetAttributeInternal(HLPackageAttribute eAttribute, HLAttribute &Attribute) const
122 {
123 switch(eAttribute)
124 {
125 case HL_WAD_PACKAGE_VERSION:
126 hlAttributeSetUnsignedInteger(&Attribute, this->lpAttributeNames[eAttribute], this->pHeader->lpSignature[3] - '0', hlFalse);
127 return hlTrue;
128 default:
129 return hlFalse;
130 }
131 }
132
GetItemAttributeCountInternal() const133 hlUInt CWADFile::GetItemAttributeCountInternal() const
134 {
135 return HL_WAD_ITEM_COUNT;
136 }
137
GetItemAttributeNameInternal(HLPackageAttribute eAttribute) const138 const hlChar *CWADFile::GetItemAttributeNameInternal(HLPackageAttribute eAttribute) const
139 {
140 if(eAttribute < HL_WAD_ITEM_COUNT)
141 {
142 return this->lpItemAttributeNames[eAttribute];
143 }
144
145 return 0;
146 }
147
GetItemAttributeInternal(const CDirectoryItem * pItem,HLPackageAttribute eAttribute,HLAttribute & Attribute) const148 hlBool CWADFile::GetItemAttributeInternal(const CDirectoryItem *pItem, HLPackageAttribute eAttribute, HLAttribute &Attribute) const
149 {
150 switch(pItem->GetType())
151 {
152 case HL_ITEM_FILE:
153 {
154 const CDirectoryFile *pFile = static_cast<const CDirectoryFile *>(pItem);
155 const WADLump *pLump = this->lpLumps + pFile->GetID();
156 switch(eAttribute)
157 {
158 case HL_WAD_ITEM_WIDTH:
159 {
160 hlUInt uiWidth = 0, uiHeight = 0, uiPaletteSize = 0;
161 this->GetLumpInfo(*pFile, uiWidth, uiHeight, uiPaletteSize);
162 hlAttributeSetUnsignedInteger(&Attribute, this->lpItemAttributeNames[eAttribute], uiWidth, hlFalse);
163 return hlTrue;
164 }
165 case HL_WAD_ITEM_HEIGHT:
166 {
167 hlUInt uiWidth = 0, uiHeight = 0, uiPaletteSize = 0;
168 this->GetLumpInfo(*pFile, uiWidth, uiHeight, uiPaletteSize);
169 hlAttributeSetUnsignedInteger(&Attribute, this->lpItemAttributeNames[eAttribute], uiHeight, hlFalse);
170 return hlTrue;
171 }
172 case HL_WAD_ITEM_PALETTE_ENTRIES:
173 {
174 hlUInt uiWidth = 0, uiHeight = 0, uiPaletteSize = 0;
175 this->GetLumpInfo(*pFile, uiWidth, uiHeight, uiPaletteSize);
176 hlAttributeSetUnsignedInteger(&Attribute, this->lpItemAttributeNames[eAttribute], uiPaletteSize, hlFalse);
177 return hlTrue;
178 }
179 case HL_WAD_ITEM_MIPMAPS:
180 {
181 hlUInt uiMipmaps = 0;
182 if(pLump->iType == 0x42)
183 {
184 uiMipmaps = 1;
185 }
186 else if(pLump->iType == 0x43)
187 {
188 uiMipmaps = 4;
189 }
190 hlAttributeSetUnsignedInteger(&Attribute, this->lpItemAttributeNames[eAttribute], uiMipmaps, hlFalse);
191 return hlTrue;
192 }
193 case HL_WAD_ITEM_COMPRESSED:
194 {
195 hlAttributeSetBoolean(&Attribute, this->lpItemAttributeNames[eAttribute], pLump->iCompression != 0);
196 return hlTrue;
197 }
198 case HL_WAD_ITEM_TYPE:
199 {
200 hlAttributeSetUnsignedInteger(&Attribute, this->lpItemAttributeNames[eAttribute], (hlUInt)pLump->iType, hlTrue);
201 return hlTrue;
202 }
203 }
204 break;
205 }
206 }
207
208 return hlFalse;
209 }
210
GetFileExtractableInternal(const CDirectoryFile * pFile,hlBool & bExtractable) const211 hlBool CWADFile::GetFileExtractableInternal(const CDirectoryFile *pFile, hlBool &bExtractable) const
212 {
213 const WADLump *pLump = this->lpLumps + pFile->GetID();
214
215 bExtractable = (pLump->iType == 0x42 || pLump->iType == 0x43) && pLump->iCompression == 0;
216
217 return hlTrue;
218 }
219
GetFileSizeInternal(const CDirectoryFile * pFile,hlUInt & uiSize) const220 hlBool CWADFile::GetFileSizeInternal(const CDirectoryFile *pFile, hlUInt &uiSize) const
221 {
222 hlUInt uiWidth, uiHeight, uiPaletteSize;
223 if(!const_cast<CWADFile *>(this)->GetLumpInfo(*pFile, uiWidth, uiHeight, uiPaletteSize))
224 {
225 return hlFalse;
226 }
227
228 uiSize = sizeof(BITMAPFILEHEADER) + sizeof(BITMAPINFOHEADER) + uiPaletteSize * 4 + uiWidth * uiHeight;
229
230 return hlTrue;
231 }
232
GetFileSizeOnDiskInternal(const CDirectoryFile * pFile,hlUInt & uiSize) const233 hlBool CWADFile::GetFileSizeOnDiskInternal(const CDirectoryFile *pFile, hlUInt &uiSize) const
234 {
235 uiSize = this->lpLumps[pFile->GetID()].uiDiskLength;
236
237 return hlTrue;
238 }
239
GetImageSize(const CDirectoryFile * pFile,hlUInt & uiPaletteDataSize,hlUInt & uiPixelDataSize)240 hlBool CWADFile::GetImageSize(const CDirectoryFile *pFile, hlUInt &uiPaletteDataSize, hlUInt &uiPixelDataSize)
241 {
242 uiPaletteDataSize = uiPixelDataSize = 0;
243
244 if(!this->GetOpened() || pFile == 0 || pFile->GetPackage() != this)
245 {
246 LastError.SetErrorMessage("File does not belong to package.");
247 return hlFalse;
248 }
249
250 hlUInt uiWidth, uiHeight, uiPaletteSize;
251 if(!const_cast<CWADFile *>(this)->GetLumpInfo(*pFile, uiWidth, uiHeight, uiPaletteSize))
252 {
253 return hlFalse;
254 }
255
256 uiPaletteDataSize = uiPaletteSize * 3;
257 uiPixelDataSize = uiWidth * uiHeight;
258
259 return hlTrue;
260 }
261
GetImageData(const CDirectoryFile * pFile,hlUInt & uiWidth,hlUInt & uiHeight,hlByte * lpPaletteData,hlByte * lpPixelData)262 hlBool CWADFile::GetImageData(const CDirectoryFile *pFile, hlUInt &uiWidth, hlUInt &uiHeight, hlByte *lpPaletteData, hlByte *lpPixelData)
263 {
264 uiWidth = uiHeight = 0;
265
266 if(!this->GetOpened() || pFile == 0 || pFile->GetPackage() != this)
267 {
268 LastError.SetErrorMessage("File does not belong to package.");
269 return hlFalse;
270 }
271
272 hlUInt uiPaletteSize;
273 const hlByte *lpPalette, *lpPixels;
274 Mapping::CView *pView = 0;
275
276 if(!const_cast<CWADFile *>(this)->GetLumpInfo(*pFile, uiWidth, uiHeight, uiPaletteSize, lpPalette, lpPixels, pView))
277 {
278 return hlFalse;
279 }
280
281 memcpy(lpPaletteData, lpPalette, uiPaletteSize * 3);
282 memcpy(lpPixelData, lpPixels, uiWidth * uiHeight);
283
284 this->pMapping->Unmap(pView);
285
286 return hlTrue;
287 }
288
GetImageSize(const CDirectoryFile * pFile,hlUInt & uiPixelDataSize)289 hlBool CWADFile::GetImageSize(const CDirectoryFile *pFile, hlUInt &uiPixelDataSize)
290 {
291 uiPixelDataSize = 0;
292
293 if(!this->GetOpened() || pFile == 0 || pFile->GetPackage() != this)
294 {
295 LastError.SetErrorMessage("File does not belong to package.");
296 return hlFalse;
297 }
298
299 hlUInt uiWidth, uiHeight, uiPaletteSize;
300 if(!const_cast<CWADFile *>(this)->GetLumpInfo(*pFile, uiWidth, uiHeight, uiPaletteSize))
301 {
302 return hlFalse;
303 }
304
305 uiPixelDataSize = uiWidth * uiHeight * 3;
306
307 return hlTrue;
308 }
309
GetImageData(const CDirectoryFile * pFile,hlUInt & uiWidth,hlUInt & uiHeight,hlByte * lpPixelData)310 hlBool CWADFile::GetImageData(const CDirectoryFile *pFile, hlUInt &uiWidth, hlUInt &uiHeight, hlByte *lpPixelData)
311 {
312 uiWidth = uiHeight = 0;
313
314 if(!this->GetOpened() || pFile == 0 || pFile->GetPackage() != this)
315 {
316 LastError.SetErrorMessage("File does not belong to package.");
317 return hlFalse;
318 }
319
320 hlUInt uiPaletteSize;
321 const hlByte *lpPalette, *lpPixels;
322 Mapping::CView *pView = 0;
323
324 if(!const_cast<CWADFile *>(this)->GetLumpInfo(*pFile, uiWidth, uiHeight, uiPaletteSize, lpPalette, lpPixels, pView))
325 {
326 return hlFalse;
327 }
328
329 for(hlUInt i = 0; i < uiWidth; i++)
330 {
331 for(hlUInt j = 0; j < uiHeight; j++)
332 {
333 hlUInt uiPixelIndex = i + j * uiWidth;
334 hlUInt uiPaletteIndex = (hlUInt)lpPixels[uiPixelIndex] * 3;
335
336 uiPixelIndex *= 3;
337 lpPixelData[uiPixelIndex + 0] = lpPalette[uiPaletteIndex + 0];
338 lpPixelData[uiPixelIndex + 1] = lpPalette[uiPaletteIndex + 1];
339 lpPixelData[uiPixelIndex + 2] = lpPalette[uiPaletteIndex + 2];
340 }
341 }
342
343 this->pMapping->Unmap(pView);
344
345 return hlTrue;
346 }
347
CreateStreamInternal(const CDirectoryFile * pFile,Streams::IStream * & pStream) const348 hlBool CWADFile::CreateStreamInternal(const CDirectoryFile *pFile, Streams::IStream *&pStream) const
349 {
350 hlUInt uiWidth, uiHeight, uiPaletteSize;
351 const hlByte *lpPalette, *lpPixels;
352 Mapping::CView *pView = 0;
353
354 if(!const_cast<CWADFile *>(this)->GetLumpInfo(*pFile, uiWidth, uiHeight, uiPaletteSize, lpPalette, lpPixels, pView))
355 {
356 return hlFalse;
357 }
358
359 hlUInt uiBufferSize = sizeof(BITMAPFILEHEADER) + sizeof(BITMAPINFOHEADER) + uiPaletteSize * 4 + uiWidth * uiHeight;
360 hlByte *lpBuffer = new hlByte[uiBufferSize];
361
362 //
363 // Allocate data.
364 //
365
366 BITMAPFILEHEADER *pFileHeader = (BITMAPFILEHEADER *)lpBuffer;
367 BITMAPINFOHEADER *pInfoHeader = (BITMAPINFOHEADER *)((hlByte *)pFileHeader + sizeof(BITMAPFILEHEADER));
368 hlByte *lpPaletteData = (hlByte *)pInfoHeader + sizeof(BITMAPINFOHEADER);
369 hlByte *lpPixelData = lpPaletteData + uiPaletteSize * 4;
370
371 memset(pFileHeader, 0, sizeof(BITMAPFILEHEADER));
372 memset(pInfoHeader, 0, sizeof(BITMAPINFOHEADER));
373
374 //
375 // Fill in headers.
376 //
377
378 pFileHeader->bfType = ('M' << 8) | 'B';
379 pFileHeader->bfSize = sizeof(BITMAPFILEHEADER) + sizeof(BITMAPINFOHEADER) + uiPaletteSize * 4 + uiWidth * uiHeight;
380 pFileHeader->bfOffBits = sizeof(BITMAPFILEHEADER) + sizeof(BITMAPINFOHEADER) + uiPaletteSize * 4;
381
382 pInfoHeader->biSize = sizeof(BITMAPINFOHEADER);
383 pInfoHeader->biWidth = uiWidth;
384 pInfoHeader->biHeight = uiHeight;
385 pInfoHeader->biPlanes = 1;
386 pInfoHeader->biBitCount = 8;
387 pInfoHeader->biSizeImage = 0;
388 pInfoHeader->biClrUsed = uiPaletteSize;
389 pInfoHeader->biClrImportant = uiPaletteSize;
390
391 //
392 // Fill in Palette data.
393 //
394
395 for(hlUInt i = 0; i < uiPaletteSize; i++)
396 {
397 lpPaletteData[i * 4 + 0] = lpPalette[i * 3 + 2];
398 lpPaletteData[i * 4 + 1] = lpPalette[i * 3 + 1];
399 lpPaletteData[i * 4 + 2] = lpPalette[i * 3 + 0];
400 lpPaletteData[i * 4 + 3] = 0;
401 }
402
403 //
404 // Fill in Index data.
405 //
406
407 for(hlUInt i = 0; i < uiWidth; i++)
408 {
409 for(hlUInt j = 0; j < uiHeight; j++)
410 {
411 lpPixelData[i + (uiHeight - 1 - j) * uiWidth] = lpPixels[i + j * uiWidth];
412 }
413 }
414
415 this->pMapping->Unmap(pView);
416
417 pStream = new Streams::CMemoryStream(lpBuffer, uiBufferSize);
418
419 return hlTrue;
420 }
421
ReleaseStreamInternal(Streams::IStream & Stream) const422 hlVoid CWADFile::ReleaseStreamInternal(Streams::IStream &Stream) const
423 {
424 delete [](hlByte *)static_cast<Streams::CMemoryStream &>(Stream).GetBuffer();
425 }
426
GetLumpInfo(const CDirectoryFile & File,hlUInt & uiWidth,hlUInt & uiHeight,hlUInt & uiPaletteSize,hlUInt uiMipmap) const427 hlBool CWADFile::GetLumpInfo(const CDirectoryFile &File, hlUInt &uiWidth, hlUInt &uiHeight, hlUInt &uiPaletteSize, hlUInt uiMipmap) const
428 {
429 const WADLump &Lump = this->lpLumps[File.GetID()];
430
431 if(Lump.iCompression)
432 {
433 LastError.SetErrorMessageFormated("Error reading lump: compression format %#.2x not supported.", Lump.iCompression);
434 return hlFalse;
435 }
436
437 if(Lump.iType == 0x42)
438 {
439 if(uiMipmap > 0)
440 {
441 LastError.SetErrorMessageFormated("Error reading lump: invalid mipmap level %u.", uiMipmap);
442 return hlFalse;
443 }
444 }
445 else if(Lump.iType == 0x43)
446 {
447 if(uiMipmap > 3)
448 {
449 LastError.SetErrorMessageFormated("Error reading lump: invalid mipmap level %u.", uiMipmap);
450 return hlFalse;
451 }
452 }
453 else
454 {
455 LastError.SetErrorMessageFormated("Error reading lump: lump type %#.2x not supported.", Lump.iType);
456 return hlFalse;
457 }
458
459 WADLumpInfo &Info = this->lpLumpInfo[File.GetID()];
460
461 if(Info.uiWidth && Info.uiHeight && Info.uiPaletteSize)
462 {
463 uiWidth = Info.uiWidth;
464 uiHeight = Info.uiHeight;
465 uiPaletteSize = Info.uiPaletteSize;
466 }
467 else
468 {
469 Mapping::CView *pView = 0;
470
471 if(!this->pMapping->Map(pView, Lump.uiOffset, Lump.uiDiskLength))
472 {
473 return hlFalse;
474 }
475
476 hlByte *lpData = (hlByte *)pView->GetView();
477
478 // Type 0x42 has no name, type 0x43 does. Are these flags?
479 if(Lump.iType == 0x42)
480 {
481 // Get Width.
482 uiWidth = *(hlUInt *)lpData;
483 lpData += 4;
484
485 // Get Height.
486 uiHeight = *(hlUInt *)lpData;
487 lpData += 4;
488
489 // Scan past pixel data.
490 lpData += (uiWidth * uiHeight);
491
492 // Get palette size.
493 uiPaletteSize = (hlUInt)(*(hlUInt16 *)lpData);
494 }
495 else if(Lump.iType == 0x43)
496 {
497 // Scan past name.
498 lpData += 16;
499
500 // Get Width.
501 uiWidth = *(hlUInt *)lpData;
502 lpData += 4;
503
504 // Get Height.
505 uiHeight = *(hlUInt *)lpData;
506 lpData += 4;
507
508 // Scan past pixel offset.
509 lpData += 16;
510
511 hlUInt uiPixelSize = uiWidth * uiHeight;
512
513 switch(uiMipmap)
514 {
515 case 1:
516 lpData += (uiPixelSize);
517 break;
518 case 2:
519 lpData += (uiPixelSize) + (uiPixelSize / 4);
520 break;
521 case 3:
522 lpData += (uiPixelSize) + (uiPixelSize / 4) + (uiPixelSize / 16);
523 break;
524 }
525
526 // Scan past data.
527 lpData += (uiPixelSize) + (uiPixelSize / 4) + (uiPixelSize / 16) + (uiPixelSize / 64);
528
529 // Get palette size.
530 uiPaletteSize = (hlUInt)(*(hlUInt16 *)lpData);
531 }
532
533 this->pMapping->Unmap(pView);
534
535 Info.uiWidth = uiWidth;
536 Info.uiHeight = uiHeight;
537 Info.uiPaletteSize = uiPaletteSize;
538 }
539
540 switch(uiMipmap)
541 {
542 case 1:
543 uiWidth /= 2;
544 uiHeight /= 2;
545 break;
546 case 2:
547 uiWidth /= 4;
548 uiHeight /= 4;
549 break;
550 case 3:
551 uiWidth /= 8;
552 uiHeight /= 8;
553 break;
554 }
555
556 return hlTrue;
557 }
558
GetLumpInfo(const CDirectoryFile & File,hlUInt & uiWidth,hlUInt & uiHeight,hlUInt & uiPaletteSize,const hlByte * & lpPalette,const hlByte * & lpPixels,Mapping::CView * & pView,hlUInt uiMipmap) const559 hlBool CWADFile::GetLumpInfo(const CDirectoryFile &File, hlUInt &uiWidth, hlUInt &uiHeight, hlUInt &uiPaletteSize, const hlByte *&lpPalette, const hlByte *&lpPixels, Mapping::CView *&pView, hlUInt uiMipmap) const
560 {
561 const WADLump &Lump = this->lpLumps[File.GetID()];
562
563 pView = 0;
564
565 if(Lump.iCompression)
566 {
567 LastError.SetErrorMessageFormated("Error reading lump: compression format %#.2x not supported.", Lump.iCompression);
568 return hlFalse;
569 }
570
571 if(Lump.iType == 0x42)
572 {
573 if(uiMipmap > 0)
574 {
575 LastError.SetErrorMessageFormated("Error reading lump: invalid mipmap level %u.", uiMipmap);
576 return hlFalse;
577 }
578 }
579 else if(Lump.iType == 0x43)
580 {
581 if(uiMipmap > 3)
582 {
583 LastError.SetErrorMessageFormated("Error reading lump: invalid mipmap level %u.", uiMipmap);
584 return hlFalse;
585 }
586 }
587 else
588 {
589 LastError.SetErrorMessageFormated("Error reading lump: lump type %#.2x not supported.", Lump.iType);
590 return hlFalse;
591 }
592
593 if(!this->pMapping->Map(pView, Lump.uiOffset, Lump.uiDiskLength))
594 {
595 return hlFalse;
596 }
597
598 hlByte *lpData = (hlByte *)pView->GetView();
599
600 // Type 0x42 has no name, type 0x43 does. Are these flags?
601 if(Lump.iType == 0x42)
602 {
603 // Get Width.
604 uiWidth = *(hlUInt *)lpData;
605 lpData += sizeof(hlUInt);
606
607 // Get Height.
608 uiHeight = *(hlUInt *)lpData;
609 lpData += sizeof(hlUInt);
610
611 // Get pixel data.
612 lpPixels = lpData;
613 lpData += (uiWidth * uiHeight);
614
615 // Get palette size.
616 uiPaletteSize = (hlUInt)(*(hlUInt16 *)lpData);
617 lpData += sizeof(hlUInt16);
618
619 // Get palette.
620 lpPalette = lpData;
621 }
622 else if(Lump.iType == 0x43)
623 {
624 // Scan past name.
625 lpData += 16;
626
627 // Get Width.
628 uiWidth = *(hlUInt *)lpData;
629 lpData += sizeof(hlUInt);
630
631 // Get Height.
632 uiHeight = *(hlUInt *)lpData;
633 lpData += sizeof(hlUInt);
634
635 // Get pixel offset.
636 hlUInt uiPixelOffset = *(hlUInt *)lpData;
637 lpData += 16;
638
639 lpPixels = (hlByte *)pView->GetView() + uiPixelOffset;
640
641 hlUInt uiPixelSize = uiWidth * uiHeight;
642
643 switch(uiMipmap)
644 {
645 case 1:
646 lpData += (uiPixelSize);
647 break;
648 case 2:
649 lpData += (uiPixelSize) + (uiPixelSize / 4);
650 break;
651 case 3:
652 lpData += (uiPixelSize) + (uiPixelSize / 4) + (uiPixelSize / 16);
653 break;
654 }
655
656 // Scan past data.
657 lpData += (uiPixelSize) + (uiPixelSize / 4) + (uiPixelSize / 16) + (uiPixelSize / 64);
658
659 // Get palette size.
660 uiPaletteSize = (hlUInt)(*(hlUInt16 *)lpData);
661 lpData += sizeof(hlUInt16);
662
663 // Get palette.
664 lpPalette = lpData;
665 }
666
667 //this->pMapping->Unmap(pView);
668
669 switch(uiMipmap)
670 {
671 case 1:
672 uiWidth /= 2;
673 uiHeight /= 2;
674 break;
675 case 2:
676 uiWidth /= 4;
677 uiHeight /= 4;
678 break;
679 case 3:
680 uiWidth /= 8;
681 uiHeight /= 8;
682 break;
683 }
684
685 return hlTrue;
686 }
687