LZScene

Форк
0
/
DXTC.pas 
1357 строк · 43.4 Кб
1
//
2
// This unit is part of the GLScene Engine https://github.com/glscene
3
//
4
{
5
   DXTC (also S3TC) decoding. 
6
   Adapted from DevIL image library (http://openil.sourceforge.net)
7

8
    History :  
9
       04/11/10 - DaStr - Restored Delphi5 and Delphi6 compatibility     
10
       23/08/10 - Yar - Replaced OpenGL1x to OpenGLTokens
11
       05/03/10 - Yar - Added float types in GLEnumToDDSHeader
12
       23/01/10 - Yar - Added more support DX9 DDS color formats
13
                           and DX11 DXGI constants to future
14
       31/03/07 - DaStr - Added $I GLScene.inc
15
       03/09/04 - SG - Delphi 5 compatibilty fixes (Ivan Lee Herring)
16
       01/09/04 - SG - Creation
17
    
18
}
19
unit DXTC;
20

21
interface
22

23
{$I GLScene.inc}
24
{$Z4}  // Minimum enum size = dword
25

26
uses
27
   SysUtils, GLCrossPlatform, OpenGLTokens, GLTextureFormat;
28

29
const
30
   DDSD_CAPS        = $00000001;
31
   DDSD_HEIGHT      = $00000002;
32
   DDSD_WIDTH       = $00000004;
33
   DDSD_PITCH       = $00000008;
34
   DDSD_PIXELFORMAT = $00001000;
35
   DDSD_MIPMAPCOUNT = $00020000;
36
   DDSD_LINEARSIZE  = $00080000;
37
   DDSD_DEPTH       = $00800000;
38

39
   DDPF_ALPHAPIXELS = $00000001;
40
   DDPF_A           = $00000002;
41
   DDPF_FOURCC      = $00000004;
42
   DDPF_RGB         = $00000040;
43
   DDPF_RGBA        = $00000041;
44
   DDPF_L           = $00020000;
45
   DDPF_LA          = $00020001;
46

47
   DDSCAPS_COMPLEX  = $00000008;
48
   DDSCAPS_TEXTURE  = $00001000;
49
   DDSCAPS_MIPMAP   = $00400000;
50

51
   DDSCAPS2_CUBEMAP           = $00000200;
52
   DDSCAPS2_CUBEMAP_POSITIVEX = $00000400;
53
   DDSCAPS2_CUBEMAP_NEGATIVEX = $00000800;
54
   DDSCAPS2_CUBEMAP_POSITIVEY = $00001000;
55
   DDSCAPS2_CUBEMAP_NEGATIVEY = $00002000;
56
   DDSCAPS2_CUBEMAP_POSITIVEZ = $00004000;
57
   DDSCAPS2_CUBEMAP_NEGATIVEZ = $00008000;
58
   DDSCAPS2_VOLUME            = $00200000;
59

60

61
type
62
   TDDPIXELFORMAT = record
63
      dwSize,
64
      dwFlags,
65
      dwFourCC,
66
      dwRGBBitCount,
67
      dwRBitMask,
68
      dwGBitMask,
69
      dwBBitMask,
70
      dwRGBAlphaBitMask : Cardinal;
71
   end;
72

73
   TDDSURFACEDESC2 = record
74
      dwSize,
75
      dwFlags,
76
      dwHeight,
77
      dwWidth,
78
      dwPitchOrLinearSize, { The number of bytes per scan line in an
79
                              uncompressed texture; the total number of bytes
80
                              in the top level texture for a compressed texture.}
81
      dwDepth,
82
      dwMipMapCount : Cardinal;
83
      dwReserved1 : array[0..10] of Cardinal;
84
      ddpf : TDDPIXELFORMAT;
85
      dwCaps,
86
      dwCaps2,
87
      dwCaps3,
88
      dwCaps4  : Cardinal;
89
      dwReserved2 : Cardinal;
90
   end;
91

92
   TDDSHeader = record
93
      Magic : Cardinal;
94
      SurfaceFormat : TDDSURFACEDESC2;
95
   end;
96

97
  DXTColBlock = record
98
    col0: GLushort;
99
    col1: GLushort;
100
    row: array[0..3] of GLubyte;
101
  end;
102
  PDXTColBlock = ^DXTColBlock;
103

104
  DXT3AlphaBlock = record
105
    row: array[0..3] of GLushort;
106
  end;
107
  PDXT3AlphaBlock = ^DXT3AlphaBlock;
108

109
  DXT5AlphaBlock = record
110
    alpha0 : GLubyte;
111
    alpha1 : GLubyte;
112
    row : array[0..5] of GLubyte;
113
  end;
114
  PDXT5AlphaBlock = ^DXT5AlphaBlock;
115

116
  const
117
//  TDXGI_FORMAT =
118
//  (
119
    DXGI_FORMAT_FORCE_UINT                  = -1;
120
    DXGI_FORMAT_UNKNOWN	                    = 0;
121
    DXGI_FORMAT_R32G32B32A32_TYPELESS       = 1;
122
    DXGI_FORMAT_R32G32B32A32_FLOAT          = 2;
123
    DXGI_FORMAT_R32G32B32A32_UINT           = 3;
124
    DXGI_FORMAT_R32G32B32A32_SINT           = 4;
125
    DXGI_FORMAT_R32G32B32_TYPELESS          = 5;
126
    DXGI_FORMAT_R32G32B32_FLOAT             = 6;
127
    DXGI_FORMAT_R32G32B32_UINT              = 7;
128
    DXGI_FORMAT_R32G32B32_SINT              = 8;
129
    DXGI_FORMAT_R16G16B16A16_TYPELESS       = 9;
130
    DXGI_FORMAT_R16G16B16A16_FLOAT          = 10;
131
    DXGI_FORMAT_R16G16B16A16_UNORM          = 11;
132
    DXGI_FORMAT_R16G16B16A16_UINT           = 12;
133
    DXGI_FORMAT_R16G16B16A16_SNORM          = 13;
134
    DXGI_FORMAT_R16G16B16A16_SINT           = 14;
135
    DXGI_FORMAT_R32G32_TYPELESS             = 15;
136
    DXGI_FORMAT_R32G32_FLOAT                = 16;
137
    DXGI_FORMAT_R32G32_UINT                 = 17;
138
    DXGI_FORMAT_R32G32_SINT                 = 18;
139
    DXGI_FORMAT_R32G8X24_TYPELESS           = 19;
140
    DXGI_FORMAT_D32_FLOAT_S8X24_UINT        = 20;
141
    DXGI_FORMAT_R32_FLOAT_X8X24_TYPELESS    = 21;
142
    DXGI_FORMAT_X32_TYPELESS_G8X24_UINT     = 22;
143
    DXGI_FORMAT_R10G10B10A2_TYPELESS        = 23;
144
    DXGI_FORMAT_R10G10B10A2_UNORM           = 24;
145
    DXGI_FORMAT_R10G10B10A2_UINT            = 25;
146
    DXGI_FORMAT_R11G11B10_FLOAT             = 26;
147
    DXGI_FORMAT_R8G8B8A8_TYPELESS           = 27;
148
    DXGI_FORMAT_R8G8B8A8_UNORM              = 28;
149
    DXGI_FORMAT_R8G8B8A8_UNORM_SRGB         = 29;
150
    DXGI_FORMAT_R8G8B8A8_UINT               = 30;
151
    DXGI_FORMAT_R8G8B8A8_SNORM              = 31;
152
    DXGI_FORMAT_R8G8B8A8_SINT               = 32;
153
    DXGI_FORMAT_R16G16_TYPELESS             = 33;
154
    DXGI_FORMAT_R16G16_FLOAT                = 34;
155
    DXGI_FORMAT_R16G16_UNORM                = 35;
156
    DXGI_FORMAT_R16G16_UINT                 = 36;
157
    DXGI_FORMAT_R16G16_SNORM                = 37;
158
    DXGI_FORMAT_R16G16_SINT                 = 38;
159
    DXGI_FORMAT_R32_TYPELESS                = 39;
160
    DXGI_FORMAT_D32_FLOAT                   = 40;
161
    DXGI_FORMAT_R32_FLOAT                   = 41;
162
    DXGI_FORMAT_R32_UINT                    = 42;
163
    DXGI_FORMAT_R32_SINT                    = 43;
164
    DXGI_FORMAT_R24G8_TYPELESS              = 44;
165
    DXGI_FORMAT_D24_UNORM_S8_UINT           = 45;
166
    DXGI_FORMAT_R24_UNORM_X8_TYPELESS       = 46;
167
    DXGI_FORMAT_X24_TYPELESS_G8_UINT        = 47;
168
    DXGI_FORMAT_R8G8_TYPELESS               = 48;
169
    DXGI_FORMAT_R8G8_UNORM                  = 49;
170
    DXGI_FORMAT_R8G8_UINT                   = 50;
171
    DXGI_FORMAT_R8G8_SNORM                  = 51;
172
    DXGI_FORMAT_R8G8_SINT                   = 52;
173
    DXGI_FORMAT_R16_TYPELESS                = 53;
174
    DXGI_FORMAT_R16_FLOAT                   = 54;
175
    DXGI_FORMAT_D16_UNORM                   = 55;
176
    DXGI_FORMAT_R16_UNORM                   = 56;
177
    DXGI_FORMAT_R16_UINT                    = 57;
178
    DXGI_FORMAT_R16_SNORM                   = 58;
179
    DXGI_FORMAT_R16_SINT                    = 59;
180
    DXGI_FORMAT_R8_TYPELESS                 = 60;
181
    DXGI_FORMAT_R8_UNORM                    = 61;
182
    DXGI_FORMAT_R8_UINT                     = 62;
183
    DXGI_FORMAT_R8_SNORM                    = 63;
184
    DXGI_FORMAT_R8_SINT                     = 64;
185
    DXGI_FORMAT_A8_UNORM                    = 65;
186
    DXGI_FORMAT_R1_UNORM                    = 66;
187
    DXGI_FORMAT_R9G9B9E5_SHAREDEXP          = 67;
188
    DXGI_FORMAT_R8G8_B8G8_UNORM             = 68;
189
    DXGI_FORMAT_G8R8_G8B8_UNORM             = 69;
190
    DXGI_FORMAT_BC1_TYPELESS                = 70;
191
    DXGI_FORMAT_BC1_UNORM                   = 71;
192
    DXGI_FORMAT_BC1_UNORM_SRGB              = 72;
193
    DXGI_FORMAT_BC2_TYPELESS                = 73;
194
    DXGI_FORMAT_BC2_UNORM                   = 74;
195
    DXGI_FORMAT_BC2_UNORM_SRGB              = 75;
196
    DXGI_FORMAT_BC3_TYPELESS                = 76;
197
    DXGI_FORMAT_BC3_UNORM                   = 77;
198
    DXGI_FORMAT_BC3_UNORM_SRGB              = 78;
199
    DXGI_FORMAT_BC4_TYPELESS                = 79;
200
    DXGI_FORMAT_BC4_UNORM                   = 80;
201
    DXGI_FORMAT_BC4_SNORM                   = 81;
202
    DXGI_FORMAT_BC5_TYPELESS                = 82;
203
    DXGI_FORMAT_BC5_UNORM                   = 83;
204
    DXGI_FORMAT_BC5_SNORM                   = 84;
205
    DXGI_FORMAT_B5G6R5_UNORM                = 85;
206
    DXGI_FORMAT_B5G5R5A1_UNORM              = 86;
207
    DXGI_FORMAT_B8G8R8A8_UNORM              = 87;
208
    DXGI_FORMAT_B8G8R8X8_UNORM              = 88;
209
    DXGI_FORMAT_R10G10B10_XR_BIAS_A2_UNORM  = 89;
210
    DXGI_FORMAT_B8G8R8A8_TYPELESS           = 90;
211
    DXGI_FORMAT_B8G8R8A8_UNORM_SRGB         = 91;
212
    DXGI_FORMAT_B8G8R8X8_TYPELESS           = 92;
213
    DXGI_FORMAT_B8G8R8X8_UNORM_SRGB         = 93;
214
    DXGI_FORMAT_BC6H_TYPELESS               = 94;
215
    DXGI_FORMAT_BC6H_UF16                   = 95;
216
    DXGI_FORMAT_BC6H_SF16                   = 96;
217
    DXGI_FORMAT_BC7_TYPELESS                = 97;
218
    DXGI_FORMAT_BC7_UNORM                   = 98;
219
    DXGI_FORMAT_BC7_UNORM_SRGB              = 99;
220
//  );
221

222
//  TD3D11_RESOURCE_DIMENSION =
223
//  (
224
    D3D11_RESOURCE_DIMENSION_UNKNOWN	  = 0;
225
	  D3D11_RESOURCE_DIMENSION_BUFFER	    = 1;
226
	  D3D11_RESOURCE_DIMENSION_TEXTURE1D	= 2;
227
	  D3D11_RESOURCE_DIMENSION_TEXTURE2D	= 3;
228
	  D3D11_RESOURCE_DIMENSION_TEXTURE3D	= 4;
229
//  );
230

231
type
232
  TDDS_HEADER_DXT10 = record
233
    dxgiFormat : Integer; //TDXGI_FORMAT;
234
    resourceDimension : Integer; //TD3D11_RESOURCE_DIMENSION;
235
    miscFlag : Cardinal;
236
    arraySize : Cardinal;
237
    reserved : Cardinal;
238
  end;
239

240
  TFOURCC = array[0..3] of AnsiChar;
241

242
const
243
    FOURCC_UNKNOWN       = 0;
244
    FOURCC_R8G8B8        = 20;
245
    FOURCC_A8R8G8B8      = 21;
246
    FOURCC_X8R8G8B8      = 22;
247
    FOURCC_R5G6B5        = 23;
248
    FOURCC_X1R5G5B5      = 24;
249
    FOURCC_A1R5G5B5      = 25;
250
    FOURCC_A4R4G4B4      = 26;
251
    FOURCC_R3G3B2        = 27;
252
    FOURCC_A8            = 28;
253
    FOURCC_A8R3G3B2      = 29;
254
    FOURCC_X4R4G4B4      = 30;
255
    FOURCC_A2B10G10R10   = 31;
256
    FOURCC_A8B8G8R8      = 32;
257
    FOURCC_X8B8G8R8      = 33;
258
    FOURCC_G16R16        = 34;
259
    FOURCC_A2R10G10B10   = 35;
260
    FOURCC_A16B16G16R16  = 36;
261

262
    FOURCC_L8            = 50;
263
    FOURCC_A8L8          = 51;
264
    FOURCC_A4L4          = 52;
265
    FOURCC_DXT1          = $31545844;
266
    FOURCC_DXT2          = $32545844;
267
    FOURCC_DXT3          = $33545844;
268
    FOURCC_DXT4          = $34545844;
269
    FOURCC_DXT5          = $35545844;
270
    FOURCC_ATI1          = $31495441;
271
    FOURCC_ATI2          = $32495441;
272

273
    FOURCC_D16_LOCKABLE  = 70;
274
    FOURCC_D32           = 71;
275
    FOURCC_D24X8         = 77;
276
    FOURCC_D16           = 80;
277

278
    FOURCC_D32F_LOCKABLE = 82;
279

280
    FOURCC_L16           = 81;
281

282
// Floating point surface formats
283

284
// s10e5 formats (16-bits per channel)
285
    FOURCC_R16F          = 111;
286
    FOURCC_G16R16F       = 112;
287
    FOURCC_A16B16G16R16F = 113;
288

289
// IEEE s23e8 formats (32-bits per channel)
290
    FOURCC_R32F          = 114;
291
    FOURCC_G32R32F       = 115;
292
    FOURCC_A32B32G32R32F = 116;
293

294
// DX10 header indicator
295
    FOURCC_DX10          = $47495844;
296

297
type
298
  TGLImageDataFormat = record
299
    ColorFlag: Cardinal;
300
    RBits, GBits, BBits, ABits: Cardinal;
301
    colorFormat: GLEnum;
302
    TexFormat: TGLInternalFormat;
303
    dType: GLenum;
304
  end;
305

306
const
307
  cImageDataFormat8bits: array[0..3] of TGLImageDataFormat = (
308
    (ColorFlag: DDPF_RGB;
309
     RBits: $E0;
310
     GBits: $1C;
311
     BBits: $03;
312
     ABits: $00;
313
     colorFormat: GL_RGB;
314
     TexFormat: tfR3_G3_B2;
315
     dType: GL_UNSIGNED_BYTE_3_3_2),
316

317
    (ColorFlag: DDPF_LA;
318
     RBits: $0F;
319
     GBits: $00;
320
     BBits: $00;
321
     ABits: $F0;
322
     colorFormat: GL_LUMINANCE_ALPHA;
323
     TexFormat: tfLUMINANCE4_ALPHA4;
324
     dType: GL_UNSIGNED_BYTE),
325

326
    (ColorFlag: DDPF_A;
327
     RBits: $00;
328
     GBits: $00;
329
     BBits: $00;
330
     ABits: $FF;
331
     colorFormat: GL_ALPHA;
332
     TexFormat: tfALPHA8;
333
     dType: GL_UNSIGNED_BYTE),
334

335
    (ColorFlag: DDPF_L;
336
     RBits: $FF;
337
     GBits: $00;
338
     BBits: $00;
339
     ABits: $00;
340
     colorFormat: GL_LUMINANCE;
341
     TexFormat: tfLUMINANCE8;
342
     dType: GL_UNSIGNED_BYTE)
343
  );
344

345
  cImageDataFormat16bits: array[0..4] of TGLImageDataFormat = (
346
    (ColorFlag: DDPF_RGBA;
347
     RBits: $0F00;
348
     GBits: $F0;
349
     BBits: $0F;
350
     ABits: $F000;
351
     colorFormat: GL_BGRA;
352
     TexFormat: tfRGBA4;
353
     dType: GL_UNSIGNED_SHORT_4_4_4_4_REV),
354

355
    (ColorFlag: DDPF_RGB;
356
     RBits: $F800;
357
     GBits: $07E0;
358
     BBits: $1F;
359
     ABits: $00;
360
     colorFormat: GL_RGB;
361
     TexFormat: tfRGB5;
362
     dType: GL_UNSIGNED_SHORT_5_6_5),
363

364
    (ColorFlag: DDPF_L;
365
     RBits: $FFFF;
366
     GBits: $00;
367
     BBits: $00;
368
     ABits: $00;
369
     colorFormat: GL_LUMINANCE;
370
     TexFormat: tfLUMINANCE16;
371
     dType: GL_UNSIGNED_SHORT),
372

373
    (ColorFlag: DDPF_LA;
374
     RBits: $FF;
375
     GBits: $00;
376
     BBits: $00;
377
     ABits: $FF00;
378
     colorFormat: GL_LUMINANCE_ALPHA;
379
     TexFormat: tfLUMINANCE8_ALPHA8;
380
     dType: GL_UNSIGNED_BYTE),
381

382
    (ColorFlag: DDPF_RGBA;
383
     RBits: $7C00;
384
     GBits: $03E0;
385
     BBits: $1F;
386
     ABits: $8000;
387
     colorFormat: GL_BGRA;
388
     TexFormat: tfRGB5_A1;
389
     dType: GL_UNSIGNED_SHORT_1_5_5_5_REV)
390
  );
391

392
  cImageDataFormat24bits: array[0..0] of TGLImageDataFormat = (
393
    (ColorFlag: DDPF_RGB;
394
     RBits: $FF0000;
395
     GBits: $FF00;
396
     BBits: $FF;
397
     ABits: $00;
398
     colorFormat: GL_BGR;
399
     TexFormat: tfRGB8;
400
     dType: GL_UNSIGNED_BYTE)
401
  );
402

403
  cImageDataFormat32bits: array[0..6] of TGLImageDataFormat = (
404
    (ColorFlag: DDPF_RGBA;
405
     RBits: $FF;
406
     GBits: $FF00;
407
     BBits: $FF0000;
408
     ABits: $FF000000;
409
     colorFormat: GL_RGBA;
410
     TexFormat: tfRGBA8;
411
     dType: GL_UNSIGNED_BYTE),
412

413
    (ColorFlag: DDPF_RGBA;
414
     RBits: $FF0000;
415
     GBits: $FF00;
416
     BBits: $FF;
417
     ABits: $FF000000;
418
     colorFormat: GL_BGRA;
419
     TexFormat: tfRGBA8;
420
     dType: GL_UNSIGNED_BYTE),
421

422
    (ColorFlag: DDPF_RGBA;
423
     RBits: $3FF00000;
424
     GBits: $0FFC00;
425
     BBits: $03FF;
426
     ABits: $0C0000000;
427
     colorFormat: GL_RGBA;
428
     TexFormat: tfRGB10_A2;
429
     dType: GL_UNSIGNED_INT_2_10_10_10_REV),
430

431
    (ColorFlag: DDPF_RGBA;
432
     RBits: $03FF;
433
     GBits: $FFC00;
434
     BBits: $3FF00000;
435
     ABits: $C0000000;
436
     colorFormat: GL_BGRA;
437
     TexFormat: tfRGB10_A2;
438
     dType: GL_UNSIGNED_INT_2_10_10_10_REV),
439

440
    (ColorFlag: DDPF_RGBA;
441
     RBits: $FF0000;
442
     GBits: $FF00;
443
     BBits: $FF;
444
     ABits: $FF000000;
445
     colorFormat: GL_BGRA;
446
     TexFormat: tfRGB8;
447
     dType: GL_UNSIGNED_INT_8_8_8_8),
448

449
    (ColorFlag: DDPF_RGBA;
450
     RBits: $FF;
451
     GBits: $FF00;
452
     BBits: $FF0000;
453
     ABits: $FF000000;
454
     colorFormat: GL_RGBA;
455
     TexFormat: tfRGB8;
456
     dType: GL_UNSIGNED_INT_8_8_8_8),
457

458
    (ColorFlag: DDPF_RGB;
459
     RBits: $FFFF;
460
     GBits: $FFFF0000;
461
     BBits: $00;
462
     ABits: $00;
463
     colorFormat: GL_RG;
464
     TexFormat: tfRG16;
465
     dType: GL_UNSIGNED_SHORT)
466
  );
467

468
procedure DecodeDXT1toBitmap32(
469
   encData, decData : PByteArray;
470
   w,h : Integer; var trans : Boolean);
471
procedure DecodeDXT3toBitmap32(encData, decData : PByteArray; w,h : Integer);
472
procedure DecodeDXT5toBitmap32(encData, decData : PByteArray; w,h : Integer);
473
procedure flip_blocks_dxtc1( data : PGLubyte; numBlocks: integer);
474
procedure flip_blocks_dxtc3( data : PGLubyte; numBlocks: integer);
475
procedure flip_blocks_dxtc5( data : PGLubyte; numBlocks: integer);
476
procedure flip_dxt5_alpha  ( block : PDXT5AlphaBlock);
477

478
function DDSHeaderToGLEnum(const DX9header: TDDSHeader;
479
                           const DX11header: TDDS_HEADER_DXT10;
480
                           const useDX11: Boolean;
481
                           out iFormat: TGLInternalFormat;
482
                           out colorFormat: GLEnum;
483
                           out dataType: GLenum;
484
                           out bpe: Integer): Boolean;
485

486
function GLEnumToDDSHeader(var DX9header: TDDSHeader;
487
                           var DX11header: TDDS_HEADER_DXT10;
488
                           const useDX11: Boolean;
489
                           const iFormat: TGLInternalFormat;
490
                           const colorFormat: GLEnum;
491
                           const dataType: GLenum;
492
                           const bpe: Integer): Boolean;
493

494
function FindDDSCompatibleDataFormat(const iFormat: TGLInternalFormat;
495
                                     out colorFormat: TGLEnum;
496
                                     out dataType: TGLEnum): Boolean;
497

498
implementation
499

500
procedure DecodeColor565(col : Word; var r,g,b : Byte);
501
begin
502
   r:=col and $1F;
503
   g:=(col shr 5) and $3F;
504
   b:=(col shr 11) and $1F;
505
end;
506

507
// DecodeDXT1toBitmap32
508
//
509
procedure DecodeDXT1toBitmap32(
510
   encData, decData : PByteArray;
511
   w,h : Integer; var trans : Boolean);
512
var
513
   x,y,i,j,k,select : Integer;
514
   col0, col1 : Word;
515
   colors : array[0..3] of array[0..3] of Byte;
516
   bitmask : Cardinal;
517
   temp : PGLubyte;
518
   r0,g0,b0,r1,g1,b1 : Byte;
519
begin
520
   trans:=False;
521

522
   if not (Assigned(encData) and Assigned(decData)) then exit;
523

524
   temp:=PGLubyte(encData);
525
   for y:=0 to (h div 4)-1 do begin
526
      for x:=0 to (w div 4)-1 do begin
527
         col0:=PWord(temp)^;        Inc(temp, 2);
528
         col1:=PWord(temp)^;        Inc(temp, 2);
529
         bitmask:=PCardinal(temp)^; Inc(temp, 4);
530

531
         DecodeColor565(col0,r0,g0,b0);
532
         DecodeColor565(col1,r1,g1,b1);
533

534
         colors[0][0]:=r0 shl 3;
535
         colors[0][1]:=g0 shl 2;
536
         colors[0][2]:=b0 shl 3;
537
         colors[0][3]:=$FF;
538
         colors[1][0]:=r1 shl 3;
539
         colors[1][1]:=g1 shl 2;
540
         colors[1][2]:=b1 shl 3;
541
         colors[1][3]:=$FF;
542

543
         if col0>col1 then begin
544
            colors[2][0]:=(2*colors[0][0]+colors[1][0]+1) div 3;
545
            colors[2][1]:=(2*colors[0][1]+colors[1][1]+1) div 3;
546
            colors[2][2]:=(2*colors[0][2]+colors[1][2]+1) div 3;
547
            colors[2][3]:=$FF;
548
            colors[3][0]:=(colors[0][0]+2*colors[1][0]+1) div 3;
549
            colors[3][1]:=(colors[0][1]+2*colors[1][1]+1) div 3;
550
            colors[3][2]:=(colors[0][2]+2*colors[1][2]+1) div 3;
551
            colors[3][3]:=$FF;
552
         end else begin
553
            trans:=True;
554
            colors[2][0]:=(colors[0][0]+colors[1][0]) div 2;
555
            colors[2][1]:=(colors[0][1]+colors[1][1]) div 2;
556
            colors[2][2]:=(colors[0][2]+colors[1][2]) div 2;
557
            colors[2][3]:=$FF;
558
            colors[3][0]:=(colors[0][0]+2*colors[1][0]+1) div 3;
559
            colors[3][1]:=(colors[0][1]+2*colors[1][1]+1) div 3;
560
            colors[3][2]:=(colors[0][2]+2*colors[1][2]+1) div 3;
561
            colors[3][3]:=0;
562
         end;
563

564
         k:=0;
565
         for j:=0 to 3 do begin
566
            for i:=0 to 3 do begin
567
               select:=(bitmask and (3 shl (k*2))) shr (k*2);
568
               if ((4*x+i)<w) and ((4*y+j)<h) then
569
                  PCardinal(@decData[((4*y+j)*w+(4*x+i))*4])^:=Cardinal(colors[select]);
570
               Inc(k);
571
            end;
572
         end;
573

574
      end;
575
   end;
576
end;
577

578
// DecodeDXT3toBitmap32
579
//
580
procedure DecodeDXT3toBitmap32(encData, decData : PByteArray; w,h : Integer);
581
var
582
   x,y,i,j,k,select : Integer;
583
   col0, col1, wrd : Word;
584
   colors : array[0..3] of array[0..3] of Byte;
585
   bitmask, offset : Cardinal;
586
   temp : PGLubyte;
587
   r0,g0,b0,r1,g1,b1 : Byte;
588
   alpha : array[0..3] of Word;
589
begin
590
   if not (Assigned(encData) and Assigned(decData)) then exit;
591

592
   temp:=PGLubyte(encData);
593
   for y:=0 to (h div 4)-1 do begin
594
      for x:=0 to (w div 4)-1 do begin
595
         alpha[0]:=PWord(temp)^;    Inc(temp, 2);
596
         alpha[1]:=PWord(temp)^;    Inc(temp, 2);
597
         alpha[2]:=PWord(temp)^;    Inc(temp, 2);
598
         alpha[3]:=PWord(temp)^;    Inc(temp, 2);
599
         col0:=PWord(temp)^;        Inc(temp, 2);
600
         col1:=PWord(temp)^;        Inc(temp, 2);
601
         bitmask:=PCardinal(temp)^; Inc(temp, 4);
602

603
         DecodeColor565(col0,r0,g0,b0);
604
         DecodeColor565(col1,r1,g1,b1);
605

606
         colors[0][0]:=r0 shl 3;
607
         colors[0][1]:=g0 shl 2;
608
         colors[0][2]:=b0 shl 3;
609
         colors[0][3]:=$FF;
610
         colors[1][0]:=r1 shl 3;
611
         colors[1][1]:=g1 shl 2;
612
         colors[1][2]:=b1 shl 3;
613
         colors[1][3]:=$FF;
614
         colors[2][0]:=(2*colors[0][0]+colors[1][0]+1) div 3;
615
         colors[2][1]:=(2*colors[0][1]+colors[1][1]+1) div 3;
616
         colors[2][2]:=(2*colors[0][2]+colors[1][2]+1) div 3;
617
         colors[2][3]:=$FF;
618
         colors[3][0]:=(colors[0][0]+2*colors[1][0]+1) div 3;
619
         colors[3][1]:=(colors[0][1]+2*colors[1][1]+1) div 3;
620
         colors[3][2]:=(colors[0][2]+2*colors[1][2]+1) div 3;
621
         colors[3][3]:=$FF;
622

623
         k:=0;
624
         for j:=0 to 3 do begin
625
            for i:=0 to 3 do begin
626
               select:=(bitmask and (3 shl (k*2))) shr (k*2);
627
               if ((4*x+i)<w) and ((4*y+j)<h) then
628
                  PCardinal(@decData[((4*y+j)*w+(4*x+i))*4])^:=Cardinal(colors[select]);
629
               Inc(k);
630
            end;
631
         end;
632

633
         for j:=0 to 3 do begin
634
            wrd:=alpha[j];
635
            for i:=0 to 3 do begin
636
               if (((4*x+i)<w) and ((4*y+j)<h)) then begin
637
                  offset:=((4*y+j)*w+(4*x+i))*4+3;
638
                  decData[offset]:=wrd and $0F;
639
                  decData[offset]:=decData[offset] or (decData[offset] shl 4);
640
               end;
641
               wrd:=wrd shr 4;
642
            end;
643
         end;
644

645
      end;
646
   end;
647
end;
648

649
// DecodeDXT5toBitmap32
650
//
651
procedure DecodeDXT5toBitmap32(encData, decData : PByteArray; w,h : Integer);
652
var
653
   x,y,i,j,k,select : Integer;
654
   col0, col1 : Word;
655
   colors : array[0..3] of array[0..3] of Byte;
656
   bits, bitmask, offset : Cardinal;
657
   temp, alphamask : PGLubyte;
658
   r0,g0,b0,r1,g1,b1 : Byte;
659
   alphas : array[0..7] of Byte;
660
begin
661
   if not (Assigned(encData) and Assigned(decData)) then exit;
662

663
   temp:=PGLubyte(encData);
664
   for y:=0 to (h div 4)-1 do begin
665
      for x:=0 to (w div 4)-1 do begin
666
         alphas[0]:=temp^; Inc(temp);
667
         alphas[1]:=temp^; Inc(temp);
668
         alphamask:=temp; Inc(temp, 6);
669
         col0:=PWord(temp)^;        Inc(temp, 2);
670
         col1:=PWord(temp)^;        Inc(temp, 2);
671
         bitmask:=PCardinal(temp)^; Inc(temp, 4);
672

673
         DecodeColor565(col0,r0,g0,b0);
674
         DecodeColor565(col1,r1,g1,b1);
675

676
         colors[0][0]:=r0 shl 3;
677
         colors[0][1]:=g0 shl 2;
678
         colors[0][2]:=b0 shl 3;
679
         colors[0][3]:=$FF;
680
         colors[1][0]:=r1 shl 3;
681
         colors[1][1]:=g1 shl 2;
682
         colors[1][2]:=b1 shl 3;
683
         colors[1][3]:=$FF;
684
         colors[2][0]:=(2*colors[0][0]+colors[1][0]+1) div 3;
685
         colors[2][1]:=(2*colors[0][1]+colors[1][1]+1) div 3;
686
         colors[2][2]:=(2*colors[0][2]+colors[1][2]+1) div 3;
687
         colors[2][3]:=$FF;
688
         colors[3][0]:=(colors[0][0]+2*colors[1][0]+1) div 3;
689
         colors[3][1]:=(colors[0][1]+2*colors[1][1]+1) div 3;
690
         colors[3][2]:=(colors[0][2]+2*colors[1][2]+1) div 3;
691
         colors[3][3]:=$FF;
692

693
         k:=0;
694
         for j:=0 to 3 do begin
695
            for i:=0 to 3 do begin
696
               select:=(bitmask and (3 shl (k*2))) shr (k*2);
697
               if ((4*x+i)<w) and ((4*y+j)<h) then
698
                  PCardinal(@decData[((4*y+j)*w+(4*x+i))*4])^:=Cardinal(colors[select]);
699
               Inc(k);
700
            end;
701
         end;
702

703
         if (alphas[0] > alphas[1]) then begin
704
            alphas[2]:=(6*alphas[0]+1*alphas[1]+3) div 7;
705
            alphas[3]:=(5*alphas[0]+2*alphas[1]+3) div 7;
706
            alphas[4]:=(4*alphas[0]+3*alphas[1]+3) div 7;
707
            alphas[5]:=(3*alphas[0]+4*alphas[1]+3) div 7;
708
            alphas[6]:=(2*alphas[0]+5*alphas[1]+3) div 7;
709
            alphas[7]:=(1*alphas[0]+6*alphas[1]+3) div 7;
710
         end else begin
711
            alphas[2]:=(4*alphas[0]+1*alphas[1]+2) div 5;
712
            alphas[3]:=(3*alphas[0]+2*alphas[1]+2) div 5;
713
            alphas[4]:=(2*alphas[0]+3*alphas[1]+2) div 5;
714
            alphas[5]:=(1*alphas[0]+4*alphas[1]+2) div 5;
715
            alphas[6]:=0;
716
            alphas[7]:=$FF;
717
         end;
718

719
         bits:=PCardinal(alphamask)^;
720
         for j:=0 to 1 do begin
721
            for i:=0 to 3 do begin
722
               if (((4*x+i)<w) and ((4*y+j)<h)) then begin
723
                  offset:=((4*y+j)*w+(4*x+i))*4+3;
724
                  decData[Offset]:=alphas[bits and 7];
725
               end;
726
               bits:=bits shr 3;
727
            end;
728
         end;
729

730
         Inc(alphamask, 3);
731
         bits:=PCardinal(alphamask)^;
732
         for j:=2 to 3 do begin
733
            for i:=0 to 3 do begin
734
               if (((4*x+i)<w) and ((4*y+j)<h)) then begin
735
                  offset:=((4*y+j)*w+(4*x+i))*4+3;
736
                  decData[offset]:=alphas[bits and 7];
737
               end;
738
               bits:=bits shr 3;
739
            end;
740
         end;
741

742
      end;
743
   end;
744
end;
745

746
// flip a DXT1 color block
747
////////////////////////////////////////////////////////////
748
procedure flip_blocks_dxtc1( data : PGLubyte; numBlocks: integer);
749
var
750
  curblock : PDXTColBlock;
751
  temp : GLubyte;
752
  i : integer;
753
begin
754
  curblock := PDXTColBlock( data );
755
  for i := 0 to  numBlocks-1 do begin
756
    temp := curblock.row[0];
757
    curblock.row[0] := curblock.row[3];
758
    curblock.row[3] := temp;
759
    temp := curblock.row[1];
760
    curblock.row[1] := curblock.row[2];
761
    curblock.row[2] := temp;
762

763
    Inc( curblock );
764
  end;
765
end;
766

767
// flip a DXT3 color block
768
////////////////////////////////////////////////////////////
769
procedure flip_blocks_dxtc3( data: PGLubyte; numBlocks: integer );
770
var
771
  curblock : PDXTColBlock;
772
  alphablock : PDXT3AlphaBlock;
773
  tempS : GLushort;
774
  tempB : GLubyte;
775
  i : integer;
776
begin
777
  curblock := PDXTColBlock( data );
778
  for i := 0 to numBlocks-1 do
779
  begin
780
    alphablock := PDXT3AlphaBlock( curblock );
781

782
    tempS := alphablock.row[0];
783
    alphablock.row[0] := alphablock.row[3];
784
    alphablock.row[3] := tempS;
785
    tempS := alphablock.row[1];
786
    alphablock.row[1] := alphablock.row[2];
787
    alphablock.row[2] := tempS;
788

789
    Inc( curblock );
790

791
    tempB := curblock.row[0];
792
    curblock.row[0] := curblock.row[3];
793
    curblock.row[3] := tempB;
794
    tempB := curblock.row[1];
795
    curblock.row[1] := curblock.row[2];
796
    curblock.row[2] := tempB;
797

798
    Inc( curblock );
799
  end;
800
end;
801

802
//
803
// flip a DXT5 alpha block
804
////////////////////////////////////////////////////////////
805
procedure flip_dxt5_alpha( block : PDXT5AlphaBlock);
806
const
807
  mask = $00000007;          // bits = 00 00 01 11
808
var
809
  gBits : array[0..3, 0..3] of GLubyte;
810
  bits  : Integer;
811
begin
812
  bits := 0;
813
  Move(block.row[0], bits, sizeof(GLubyte) * 3);
814

815
  gBits[0][0] := GLubyte(bits and mask);
816
  bits := bits shr 3;
817
  gBits[0][1] := GLubyte(bits and mask);
818
  bits := bits shr 3;
819
  gBits[0][2] := GLubyte(bits and mask);
820
  bits := bits shr 3;
821
  gBits[0][3] := GLubyte(bits and mask);
822
  bits := bits shr 3;
823
  gBits[1][0] := GLubyte(bits and mask);
824
  bits := bits shr 3;
825
  gBits[1][1] := GLubyte(bits and mask);
826
  bits := bits shr 3;
827
  gBits[1][2] := GLubyte(bits and mask);
828
  bits := bits shr 3;
829
  gBits[1][3] := GLubyte(bits and mask);
830

831
  bits := 0;
832
  Move(block.row[3], bits, sizeof(GLubyte) * 3);
833

834
  gBits[2][0] := GLubyte(bits and mask);
835
  bits := bits shr 3;
836
  gBits[2][1] := GLubyte(bits and mask);
837
  bits := bits shr 3;
838
  gBits[2][2] := GLubyte(bits and mask);
839
  bits := bits shr 3;
840
  gBits[2][3] := GLubyte(bits and mask);
841
  bits := bits shr 3;
842
  gBits[3][0] := GLubyte(bits and mask);
843
  bits := bits shr 3;
844
  gBits[3][1] := GLubyte(bits and mask);
845
  bits := bits shr 3;
846
  gBits[3][2] := GLubyte(bits and mask);
847
  bits := bits shr 3;
848
  gBits[3][3] := GLubyte(bits and mask);
849

850
  // clear existing alpha bits
851
  FillChar( block.row, sizeof(GLubyte) * 6, 0);
852

853
  bits := block.row[0]+block.row[1]*$100+block.row[2]*$10000;
854

855
  bits := bits or (gBits[3][0] shl 0);
856
  bits := bits or (gBits[3][1] shl 3);
857
  bits := bits or (gBits[3][2] shl 6);
858
  bits := bits or (gBits[3][3] shl 9);
859

860
  bits := bits or (gBits[2][0] shl 12);
861
  bits := bits or (gBits[2][1] shl 15);
862
  bits := bits or (gBits[2][2] shl 18);
863
  bits := bits or (gBits[2][3] shl 21);
864

865
  block.row[0] := bits and $FF;
866
  block.row[1] := (bits shr 8) and $FF;
867
  block.row[2] := (bits shr 16) and $FF;
868

869
  bits := block.row[3]+block.row[4]*$100+block.row[5]*$10000;
870

871
  bits := bits or (gBits[1][0] shl 0);
872
  bits := bits or (gBits[1][1] shl 3);
873
  bits := bits or (gBits[1][2] shl 6);
874
  bits := bits or (gBits[1][3] shl 9);
875

876
  bits := bits or (gBits[0][0] shl 12);
877
  bits := bits or (gBits[0][1] shl 15);
878
  bits := bits or (gBits[0][2] shl 18);
879
  bits := bits or (gBits[0][3] shl 21);
880

881
  block.row[3] := bits and $FF;
882
  block.row[4] := (bits shr 8) and $FF;
883
  block.row[5] := (bits shr 16) and $FF;
884
end;
885

886
//
887
// flip a DXT5 color block
888
////////////////////////////////////////////////////////////
889
procedure flip_blocks_dxtc5( data: PGLubyte; numBlocks: integer );
890
var
891
  curblock : PDXTColBlock;
892
  temp : GLubyte;
893
  i : integer;
894
begin
895
  curblock := PDXTColBlock( data );
896
  for i := 0 to numBlocks-1 do
897
  begin
898
    flip_dxt5_alpha( PDXT5AlphaBlock( curblock ) );
899
    Inc( curblock );
900
    temp := curblock.row[0];
901
    curblock.row[0] := curblock.row[3];
902
    curblock.row[3] := temp;
903
    temp := curblock.row[1];
904
    curblock.row[1] := curblock.row[2];
905
    curblock.row[2] := temp;
906
    Inc( curblock );
907
  end;
908
end;
909

910
function DDSHeaderToGLEnum(const DX9header: TDDSHeader;
911
                           const DX11header: TDDS_HEADER_DXT10;
912
                           const useDX11: Boolean;
913
                           out iFormat: TGLInternalFormat;
914
                           out colorFormat: GLEnum;
915
                           out dataType: GLenum;
916
                           out bpe: Integer): Boolean;
917
var
918
  i: Integer;
919
begin
920
  Result := true;
921
  if useDX11 then
922
  begin
923
    Assert(false, 'DXGI images not supported.');
924
  end
925
  // Use DX9 formats
926
  else begin
927
    // figure out what the image format is
928
    if (DX9header.SurfaceFormat.ddpf.dwFlags and DDPF_FOURCC)<>0 then
929
    begin
930
      case DX9header.SurfaceFormat.ddpf.dwFourCC of
931
        FOURCC_DXT1:
932
          begin
933
            colorFormat := GL_COMPRESSED_RGBA_S3TC_DXT1_EXT;
934
            iFormat := tfCOMPRESSED_RGBA_S3TC_DXT1;
935
            dataType := GL_COMPRESSED_RGBA_S3TC_DXT1_EXT;
936
            bpe := 8;
937
          end;
938
        FOURCC_DXT2, FOURCC_DXT3:
939
          begin
940
            colorFormat := GL_COMPRESSED_RGBA_S3TC_DXT3_EXT;
941
            iFormat := tfCOMPRESSED_RGBA_S3TC_DXT3;
942
            dataType := GL_COMPRESSED_RGBA_S3TC_DXT3_EXT;
943
            bpe := 16;
944
          end;
945
        FOURCC_DXT4, FOURCC_DXT5:
946
          begin
947
            colorFormat := GL_COMPRESSED_RGBA_S3TC_DXT5_EXT;
948
            iFormat := tfCOMPRESSED_RGBA_S3TC_DXT5;
949
            dataType := GL_COMPRESSED_RGBA_S3TC_DXT5_EXT;
950
            bpe := 16;
951
          end;
952
        FOURCC_ATI1:
953
          begin
954
            colorFormat := GL_COMPRESSED_RED_RGTC1;
955
            iFormat := tfCOMPRESSED_RED_RGTC1;
956
            dataType := GL_COMPRESSED_RED_RGTC1;
957
            bpe := 8;
958
          end;
959
        FOURCC_ATI2:
960
          begin
961
            colorFormat := GL_COMPRESSED_RG_RGTC2;
962
            iFormat := tfCOMPRESSED_RG_RGTC2;
963
            dataType := GL_COMPRESSED_RG_RGTC2;
964
            bpe := 16;
965
          end;
966
        FOURCC_R8G8B8:
967
          begin
968
            colorFormat := GL_BGR;
969
            iFormat := tfRGB8;
970
            dataType := GL_UNSIGNED_BYTE;
971
            bpe := 3;
972
          end;
973
        FOURCC_A8R8G8B8:
974
          begin
975
            colorFormat := GL_BGRA;
976
            iFormat := tfRGBA8;
977
            dataType := GL_UNSIGNED_BYTE;
978
            bpe := 4;
979
          end;
980
        FOURCC_X8R8G8B8:
981
          begin
982
            colorFormat := GL_BGRA;
983
            iFormat := tfRGB8;
984
            dataType := GL_UNSIGNED_INT_8_8_8_8;
985
            bpe := 4;
986
          end;
987
        FOURCC_R5G6B5:
988
          begin
989
            colorFormat := GL_RGB;
990
            iFormat := tfRGB5;
991
            dataType := GL_UNSIGNED_SHORT_5_6_5;
992
            bpe := 2;
993
          end;
994
        FOURCC_A8:
995
          begin
996
            colorFormat := GL_ALPHA;
997
            iFormat := tfALPHA8;
998
            dataType := GL_UNSIGNED_BYTE;
999
            bpe := 1;
1000
          end;
1001
        FOURCC_A2B10G10R10:
1002
          begin
1003
            colorFormat := GL_RGBA;
1004
            iFormat := tfRGB10_A2;
1005
            dataType := GL_UNSIGNED_INT_10_10_10_2;
1006
            bpe := 4;
1007
          end;
1008
        FOURCC_A8B8G8R8:
1009
          begin
1010
            colorFormat := GL_RGBA;
1011
            iFormat := tfRGBA8;
1012
            dataType := GL_UNSIGNED_BYTE;
1013
            bpe := 4;
1014
          end;
1015
        FOURCC_X8B8G8R8:
1016
          begin
1017
            colorFormat := GL_RGBA;
1018
            iFormat := tfRGB8;
1019
            dataType := GL_UNSIGNED_INT_8_8_8_8;
1020
            bpe := 4;
1021
          end;
1022
        FOURCC_A2R10G10B10:
1023
          begin
1024
            colorFormat := GL_BGRA;
1025
            iFormat := tfRGB10_A2;
1026
            dataType := GL_UNSIGNED_INT_10_10_10_2;
1027
            bpe := 4;
1028
          end;
1029
        FOURCC_A16B16G16R16:
1030
          begin
1031
            colorFormat := GL_RGBA;
1032
            iFormat := tfR16G16B16A16;
1033
            dataType := GL_UNSIGNED_SHORT;
1034
            bpe := 8;
1035
          end;
1036
        FOURCC_L8:
1037
          begin
1038
            colorFormat := GL_LUMINANCE;
1039
            iFormat := tfLUMINANCE8;
1040
            dataType := GL_UNSIGNED_BYTE;
1041
            bpe := 1;
1042
          end;
1043
        FOURCC_A8L8:
1044
          begin
1045
            colorFormat := GL_LUMINANCE_ALPHA;
1046
            iFormat := tfLUMINANCE8_ALPHA8;
1047
            dataType := GL_UNSIGNED_BYTE;
1048
            bpe := 2;
1049
          end;
1050
        FOURCC_L16:
1051
          begin
1052
            colorFormat := GL_LUMINANCE;
1053
            iFormat := tfLUMINANCE16;
1054
            dataType := GL_UNSIGNED_SHORT;
1055
            bpe := 2;
1056
          end;
1057
        FOURCC_R16F:
1058
          begin
1059
            colorFormat := GL_RED;
1060
            iFormat := tfLUMINANCE_FLOAT16;
1061
            dataType := GL_HALF_FLOAT_ARB;
1062
            bpe := 2;
1063
          end;
1064
        FOURCC_A16B16G16R16F:
1065
          begin
1066
            colorFormat := GL_RGBA;
1067
            iFormat := tfRGBA_FLOAT16;
1068
            dataType := GL_HALF_FLOAT_ARB;
1069
            bpe := 8;
1070
          end;
1071
        FOURCC_R32F:
1072
          begin
1073
            colorFormat := GL_RED;
1074
            iFormat := tfLUMINANCE_FLOAT32;
1075
            dataType := GL_FLOAT;
1076
            bpe := 4;
1077
          end;
1078
        FOURCC_G16R16:
1079
          begin
1080
            colorFormat := GL_RG;
1081
            iFormat := tfRG16;
1082
            dataType := GL_UNSIGNED_SHORT;
1083
            bpe := 4;
1084
          end;
1085
        FOURCC_G16R16F:
1086
          begin
1087
            colorFormat := GL_RG;
1088
            iFormat := tfRG16F;
1089
            dataType := GL_HALF_FLOAT;
1090
            bpe := 4;
1091
          end;
1092
        FOURCC_G32R32F:
1093
          begin
1094
            colorFormat := GL_RG;
1095
            iFormat := tfRG32F;
1096
            dataType := GL_FLOAT;
1097
            bpe := 8;
1098
          end;
1099
        FOURCC_UNKNOWN,
1100
        FOURCC_X1R5G5B5,
1101
        FOURCC_A1R5G5B5,
1102
        FOURCC_A4R4G4B4,
1103
        FOURCC_R3G3B2,
1104
        FOURCC_A8R3G3B2,
1105
        FOURCC_X4R4G4B4,
1106
        FOURCC_A4L4,
1107
        FOURCC_D16_LOCKABLE,
1108
        FOURCC_D32,
1109
        FOURCC_D24X8,
1110
        FOURCC_D16,
1111
        FOURCC_D32F_LOCKABLE: Result := false; //these are unsupported for now
1112
      end; // of case
1113
    end // not FOURCC
1114

1115
    else
1116
      with DX9header.SurfaceFormat.ddpf do
1117
        case dwRGBBitCount of
1118
        8: begin
1119
          for i := 0 to High(cImageDataFormat8bits) do
1120
            if  (cImageDataFormat8bits[i].ColorFlag = dwFlags)
1121
            and (cImageDataFormat8bits[i].RBits = dwRBitMask)
1122
            and (cImageDataFormat8bits[i].GBits = dwGBitMask)
1123
            and (cImageDataFormat8bits[i].BBits = dwBBitMask)
1124
            and (cImageDataFormat8bits[i].ABits = dwRGBAlphaBitMask) then
1125
            begin
1126
              colorFormat := cImageDataFormat8bits[i].colorFormat;
1127
              iFormat := cImageDataFormat8bits[i].TexFormat;
1128
              dataType := cImageDataFormat8bits[i].dType;
1129
              Result := true;
1130
              Break;
1131
            end;
1132
          bpe := 1;
1133
        end;
1134
        16: begin
1135
          for i := 0 to High(cImageDataFormat16bits) do
1136
            if  (cImageDataFormat16bits[i].ColorFlag = dwFlags)
1137
            and (cImageDataFormat16bits[i].RBits = dwRBitMask)
1138
            and (cImageDataFormat16bits[i].GBits = dwGBitMask)
1139
            and (cImageDataFormat16bits[i].BBits = dwBBitMask)
1140
            and (cImageDataFormat16bits[i].ABits = dwRGBAlphaBitMask) then
1141
            begin
1142
              colorFormat := cImageDataFormat16bits[i].colorFormat;
1143
              iFormat := cImageDataFormat16bits[i].TexFormat;
1144
              dataType := cImageDataFormat16bits[i].dType;
1145
              Result := true;
1146
              Break;
1147
            end;
1148
          bpe := 2;
1149
        end;
1150
        24: begin
1151
          for i := 0 to High(cImageDataFormat24bits) do
1152
            if  (cImageDataFormat24bits[i].ColorFlag = dwFlags)
1153
            and (cImageDataFormat24bits[i].RBits = dwRBitMask)
1154
            and (cImageDataFormat24bits[i].GBits = dwGBitMask)
1155
            and (cImageDataFormat24bits[i].BBits = dwBBitMask)
1156
            and (cImageDataFormat24bits[i].ABits = dwRGBAlphaBitMask) then
1157
            begin
1158
              colorFormat := cImageDataFormat24bits[i].colorFormat;
1159
              iFormat := cImageDataFormat24bits[i].TexFormat;
1160
              dataType := cImageDataFormat24bits[i].dType;
1161
              Result := true;
1162
              Break;
1163
            end;
1164
          bpe := 3;
1165
        end;
1166
        32: begin
1167
          for i := 0 to High(cImageDataFormat32bits) do
1168
            if  (cImageDataFormat32bits[i].ColorFlag = dwFlags)
1169
            and (cImageDataFormat32bits[i].RBits = dwRBitMask)
1170
            and (cImageDataFormat32bits[i].GBits = dwGBitMask)
1171
            and (cImageDataFormat32bits[i].BBits = dwBBitMask)
1172
            and (cImageDataFormat32bits[i].ABits = dwRGBAlphaBitMask) then
1173
            begin
1174
              colorFormat := cImageDataFormat32bits[i].colorFormat;
1175
              iFormat := cImageDataFormat32bits[i].TexFormat;
1176
              dataType := cImageDataFormat32bits[i].dType;
1177
              Result := true;
1178
              Break;
1179
            end;
1180
          bpe := 4;
1181
        end;
1182
        else Result := false;
1183
      end; // of case
1184
  end;
1185
end;
1186

1187
function GLEnumToDDSHeader(var DX9header: TDDSHeader;
1188
                           var DX11header: TDDS_HEADER_DXT10;
1189
                           const useDX11: Boolean;
1190
                           const iFormat: TGLInternalFormat;
1191
                           const colorFormat: GLEnum;
1192
                           const dataType: GLenum;
1193
                           const bpe: Integer): Boolean;
1194
var
1195
  i: Integer;
1196
begin
1197
  Result := true;
1198
  if useDX11 then
1199
  begin
1200
    Assert(false, 'DXGI images not supported.');
1201
  end;
1202

1203
  if IsCompressedFormat(iFormat) then
1204
  begin
1205
    with DX9header.SurfaceFormat.ddpf do
1206
    begin
1207
      dwFlags := DDPF_FOURCC;
1208
      case iFormat of
1209
        tfCOMPRESSED_RGB_S3TC_DXT1:         dwFourCC := FOURCC_DXT1;
1210
        tfCOMPRESSED_RGBA_S3TC_DXT1:        dwFourCC := FOURCC_DXT1;
1211
        tfCOMPRESSED_RGBA_S3TC_DXT3:        dwFourCC := FOURCC_DXT3;
1212
        tfCOMPRESSED_RGBA_S3TC_DXT5:        dwFourCC := FOURCC_DXT5;
1213
        tfCOMPRESSED_LUMINANCE_LATC1:       dwFourCC := FOURCC_ATI1;
1214
        tfCOMPRESSED_LUMINANCE_ALPHA_LATC2: dwFourCC := FOURCC_ATI2;
1215
        else Result := false;
1216
      end;
1217
    end;
1218
  end
1219
  else if IsFloatFormat(iFormat) then
1220
  begin
1221
    with DX9header.SurfaceFormat.ddpf do
1222
    begin
1223
      dwFlags := DDPF_FOURCC;
1224
      case iFormat of
1225
        tfINTENSITY_FLOAT16,
1226
        tfLUMINANCE_FLOAT16,
1227
        tfR16F:                             dwFourCC := FOURCC_R16F;
1228
        tfRGBA_FLOAT16:                     dwFourCC := FOURCC_A16B16G16R16F;
1229
        tfINTENSITY_FLOAT32,
1230
        tfLUMINANCE_FLOAT32,
1231
        tfR32F:                             dwFourCC := FOURCC_R32F;
1232
        tfLUMINANCE_ALPHA_FLOAT16,
1233
        tfRG16F:                            dwFourCC := FOURCC_G16R16F;
1234
        tfLUMINANCE_ALPHA_FLOAT32,
1235
        tfRG32F:                            dwFourCC := FOURCC_G32R32F;
1236
        tfRGBA_FLOAT32:                     dwFourCC := FOURCC_A32B32G32R32F
1237
        else Result := false;
1238
      end;
1239
    end;
1240
  end
1241
  else with DX9header.SurfaceFormat.ddpf do
1242
  begin
1243
    dwFourCC := 0;
1244
    dwRGBBitCount := bpe * 8;
1245
    case bpe of
1246
      1: begin
1247
        for i := 0 to High(cImageDataFormat8bits) do
1248
          if (cImageDataFormat8bits[i].colorFormat = colorFormat)
1249
          and (cImageDataFormat8bits[i].TexFormat = iFormat)
1250
          and (cImageDataFormat8bits[i].dType = dataType) then
1251
          begin
1252
            dwFlags := cImageDataFormat8bits[i].ColorFlag;
1253
            dwRBitMask := cImageDataFormat8bits[i].RBits;
1254
            dwGBitMask := cImageDataFormat8bits[i].GBits;
1255
            dwBBitMask := cImageDataFormat8bits[i].BBits;
1256
            dwRGBAlphaBitMask := cImageDataFormat8bits[i].ABits;
1257
            Break;
1258
          end;
1259
      end;
1260

1261
      2: begin
1262
        for i := 0 to High(cImageDataFormat16bits) do
1263
          if (cImageDataFormat16bits[i].colorFormat = colorFormat)
1264
          and (cImageDataFormat16bits[i].TexFormat = iFormat)
1265
          and (cImageDataFormat16bits[i].dType = dataType) then
1266
          begin
1267
            dwFlags := cImageDataFormat16bits[i].ColorFlag;
1268
            dwRBitMask := cImageDataFormat16bits[i].RBits;
1269
            dwGBitMask := cImageDataFormat16bits[i].GBits;
1270
            dwBBitMask := cImageDataFormat16bits[i].BBits;
1271
            dwRGBAlphaBitMask := cImageDataFormat16bits[i].ABits;
1272
            Break;
1273
          end;
1274
      end;
1275

1276
      3: begin
1277
        for i := 0 to High(cImageDataFormat24bits) do
1278
          if (cImageDataFormat24bits[i].colorFormat = colorFormat)
1279
          and (cImageDataFormat24bits[i].TexFormat = iFormat)
1280
          and (cImageDataFormat24bits[i].dType = dataType) then
1281
          begin
1282
            dwFlags := cImageDataFormat24bits[i].ColorFlag;
1283
            dwRBitMask := cImageDataFormat24bits[i].RBits;
1284
            dwGBitMask := cImageDataFormat24bits[i].GBits;
1285
            dwBBitMask := cImageDataFormat24bits[i].BBits;
1286
            dwRGBAlphaBitMask := cImageDataFormat24bits[i].ABits;
1287
            Break;
1288
          end;
1289
      end;
1290

1291
      4: begin
1292
        for i := 0 to High(cImageDataFormat32bits) do
1293
          if (cImageDataFormat32bits[i].colorFormat = colorFormat)
1294
          and (cImageDataFormat32bits[i].TexFormat = iFormat)
1295
          and (cImageDataFormat32bits[i].dType = dataType) then
1296
          begin
1297
            dwFlags := cImageDataFormat32bits[i].ColorFlag;
1298
            dwRBitMask := cImageDataFormat32bits[i].RBits;
1299
            dwGBitMask := cImageDataFormat32bits[i].GBits;
1300
            dwBBitMask := cImageDataFormat32bits[i].BBits;
1301
            dwRGBAlphaBitMask := cImageDataFormat32bits[i].ABits;
1302
            Break;
1303
          end;
1304
      end;
1305

1306
      else Result := false;
1307
    end; // of case
1308
  end;
1309

1310
end;
1311

1312
function FindDDSCompatibleDataFormat(const iFormat: TGLInternalFormat;
1313
                                     out colorFormat: TGLEnum;
1314
                                     out dataType: TGLEnum): Boolean;
1315
var
1316
  i: Integer;
1317
begin
1318
  Result := false;
1319
  // 32 bits data format
1320
  for i := 0 to High(cImageDataFormat32bits) do
1321
    if cImageDataFormat32bits[i].TexFormat = iFormat then
1322
    begin
1323
      colorFormat := cImageDataFormat32bits[i].colorFormat;
1324
      dataType := cImageDataFormat32bits[i].dType;
1325
      Result := true;
1326
      Exit;
1327
    end;
1328
  // 24 bits data format
1329
  for i := 0 to High(cImageDataFormat24bits) do
1330
    if cImageDataFormat24bits[i].TexFormat = iFormat then
1331
    begin
1332
      colorFormat := cImageDataFormat24bits[i].colorFormat;
1333
      dataType := cImageDataFormat24bits[i].dType;
1334
      Result := true;
1335
      Exit;
1336
    end;
1337
  // 16 bits data format
1338
  for i := 0 to High(cImageDataFormat16bits) do
1339
    if cImageDataFormat16bits[i].TexFormat = iFormat then
1340
    begin
1341
      colorFormat := cImageDataFormat16bits[i].colorFormat;
1342
      dataType := cImageDataFormat16bits[i].dType;
1343
      Result := true;
1344
      Exit;
1345
    end;
1346
  // 8 bits data format
1347
  for i := 0 to High(cImageDataFormat8bits) do
1348
    if cImageDataFormat8bits[i].TexFormat = iFormat then
1349
    begin
1350
      colorFormat := cImageDataFormat8bits[i].colorFormat;
1351
      dataType := cImageDataFormat8bits[i].dType;
1352
      Result := true;
1353
      Exit;
1354
    end;
1355
end;
1356

1357
end.

Использование cookies

Мы используем файлы cookie в соответствии с Политикой конфиденциальности и Политикой использования cookies.

Нажимая кнопку «Принимаю», Вы даете АО «СберТех» согласие на обработку Ваших персональных данных в целях совершенствования нашего веб-сайта и Сервиса GitVerse, а также повышения удобства их использования.

Запретить использование cookies Вы можете самостоятельно в настройках Вашего браузера.