DDS 프로그래밍 가이드
Direct3D는 압축되지 않거나 압축된(DXTn) 텍스처를 저장하기 위한 DDS 파일 형식을 구현합니다. 파일 형식은 다양한 유형의 데이터를 저장하도록 설계된 몇 가지 약간 다른 형식을 구현하고 단일 레이어 텍스처, 밉맵이 있는 텍스처, 큐브 맵, 볼륨 맵 및 텍스처 배열(Direct3D 10/11)을 지원합니다. 이 섹션에서는 DDS 파일의 레이아웃에 대해 설명합니다.
Direct3D 11에서 텍스처를 만드는 방법에 대한 도움말은 방법: 텍스처 만들기를 참조하세요. Direct3D 9에 대한 도움말은 D3DX의 텍스처 지원(Direct3D 9)을 참조하세요.
DDS 파일 레이아웃
DDS 파일은 다음 정보를 포함하는 이진 파일입니다.
4문자 코드 값 'DDS ' (0x20534444)가 들어 있는 DWORD(매직 넘버).
파일의 데이터에 대한 설명.
데이터는 DDS_HEADER를 사용하여 헤더 설명으로 설명됩니다. 픽셀 형식은 DDS_PIXELFORMAT을 사용하여 정의됩니다. DDS_HEADER 및 DDS_PIXELFORMAT 구조는 사용되지 않는 DDSURFACEDESC2, DDSCAPS2 및 DDPIXELFORMAT DirectDraw 7 구조를 대체합니다. DDS_HEADER는 DDSURFACEDESC2 및 DDSCAPS2의 이진 값입니다. DDS_PIXELFORMAT은 DDPIXELFORMAT의 이진 값입니다.
DWORD dwMagic; DDS_HEADER header;
DDS_PIXELFORMAT dwFlags가 DDPF_FOURCC 설정되고 dwFourCC가 "DX10"으로 설정된 경우 부동 소수점 형식, sRGB 형식 등 RGB 픽셀 형식으로 표현할 수 없는 텍스처 배열 또는 DXGI 형식을 수용하기 위해 추가 DDS_HEADER_DXT10 구조가 존재합니다. DDS_HEADER_DXT10 구조체가 있으면 전체 데이터 설명은 다음과 같습니다.
DWORD dwMagic; DDS_HEADER header; DDS_HEADER_DXT10 header10;
주 표면 데이터를 포함하는 바이트 배열에 대한 포인터.
BYTE bdata[]
mipmap 수준, 큐브 맵의 표면, 볼륨 텍스처의 깊이 등, 나머지 표면을 포함하는 바이트 배열에 대한 포인터. 텍스처, 큐브 맵 또는 볼륨 텍스처의 DDS 파일 레이아웃에 대한 추가 정보는 각 링크를 참조하세요.
BYTE bdata2[]
광범위한 하드웨어 지원을 위해 DXGI_FORMAT_R8G8B8A8_UNORM, DXGI_FORMAT_R8G8B8A8_UNORM_SRGB, DXGI_FORMAT_R8G8B8A8_SNORM, DXGI_FORMAT_B8G8R8A8_UNORM, DXGI_FORMAT_R16G16_SNORM, DXGI_FORMAT_R8G8_SNORM, DXGI_FORMAT_R8_UNORM, DXGI_FORMAT_BC1_UNORM, DXGI_FORMAT_BC1_UNORM_SRGB, DXGI_FORMAT_BC2_UNORM, DXGI_FORMAT_BC2_UNORM_SRGB 사용하는 것이 좋습니다. DXGI_FORMAT_BC3_UNORM 또는 DXGI_FORMAT_BC3_UNORM_SRGB 형식입니다.
압축된 텍스처 형식에 대한 자세한 내용은 Direct3D 11의 텍스처 블록 압축 및 블록 압축(Direct3D 10)을 참조하세요.
D3DX 라이브러리(예: D3DX11.lib) 및 기타 유사한 라이브러리는 DDS_HEADER 구조체의 dwPitchOrLinearSize 멤버에서 피치 값을 안정적으로 또는 일관되지 않게 제공합니다. 따라서 DDS 파일을 읽고 쓸 때 표시된 형식에 대해 다음 방법 중 하나로 피치를 계산하는 것이 좋습니다.
블록 압축 형식의 경우 피치를 다음과 같이 계산합니다.
max( 1, ((width+3)/4) ) * 블록 크기
블록 크기는 DXT1, BC1 및 BC4 형식의 경우 8바이트, 다른 블록 압축 형식의 경우 16바이트입니다.
R8G8_B8G8, G8R8_G8B8, 레거시 UYVY로 가득 찬 및 레거시 YUY2로 구성된 형식의 경우 피치를 다음과 같이 계산합니다.
((width+1) >> 1) * 4
다른 형식의 경우 피치를 다음과 같이 계산합니다.
( width * bits-per-pixel + 7 ) / 8
바이트 맞춤을 위해 8로 나눕니다.
참고
계산하는 피치 값이 런타임이 제공하는 피치와 항상 같지는 않습니다. 이 피치는 일부 상황에서는 DWORD로 정렬되고 다른 상황에서는 바이트 정렬됩니다. 따라서 전체 이미지를 하나의 복사본으로 복사하는 대신 한 번에 스캔 줄을 복사하는 것이 좋습니다.
DDS 변형
DDS 파일을 만들고 사용하는 많은 도구가 있지만 헤더에 필요한 항목에 대한 세부 정보는 다를 수 있습니다. 작성기는 가능한 한 헤더를 완전히 채워야 하며 판독기는 최대 호환성을 위해 최소 값을 검사 합니다. DDS 파일의 유효성을 검사하려면 판독기는 매직 값과 기본 헤더를 수용하기 위해 파일이 128바이트 이상인지, 매직 값이 0x20534444("DDS"), DDS_HEADER 크기가 124이고 헤더 크기의 DDS_PIXELFORMAT 32인지 확인해야 합니다. DDS_PIXELFORMAT dwFlags가 DDPF_FOURCC 설정되고 dwFourCC가 "DX10"으로 설정된 경우 총 파일 크기는 148바이트 이상이어야 합니다.
픽셀 형식이 dwFourCC가 D3DFORMAT 또는 DXGI_FORMAT 열거형 값으로 설정된 DDPF_FOURCC 코드로 설정된 몇 가지 일반적인 변형이 있습니다. 열거형 값이 D3DFORMAT인지 DXGI_FORMAT 알 수 없으므로 기본 DDS_PIXELFORMAT 형식을 표현할 수 없는 경우 "DX10" 확장 및 DDS_HEADER_DXT10 헤더를 대신 사용하여 dxgiFormat을 저장하는 것이 좋습니다.
모든 DDS 도구가 DX10 확장을 지원하지 않으므로 RGB 압축되지 않은 데이터 및 DXT1-5 데이터를 저장하는 최대 호환성을 위해 표준 DDS_PIXELFORMAT 선호되어야 합니다.
Direct3D 10/11에서 텍스처 배열 사용
Direct3D 10/11의 새 DDS 구조체(DDS_HEADER 및 DDS_HEADER_DXT10)는 DDS 파일 형식을 확장하여 Direct3D 10/11의 새 리소스 형식인 텍스처 배열을 지원합니다. 다음은 새 헤더를 사용하여 텍스처 배열의 다양한 Mipmap 수준에 액세스하는 방법을 보여 주는 몇 가지 샘플 코드입니다.
DWORD dwMagic;
DDS_HEADER header;
DDS_HEADER_DXT10 header10;
for (int iArrayElement = 0; iArrayElement < header10.arraySize; iArrayElement++)
{
for (int iMipLevel = 0; iMipLevel < header.dwMipMapCount; iMipLevel++)
{
...
}
}
일반적인 DDS 파일 리소스 형식 및 연결된 헤더 콘텐츠
리소스 형식 | dwFlags | dwRGBBitCount | dwRBitMask | dwGBitMask | dwBBitMask | dwABitMask |
---|---|---|---|---|---|---|
DXGI_FORMAT_R8G8B8A8_UNORM D3DFMT_A8B8G8R8 |
DDS_RGBA | 32 | 0xff | 0xff00 | 0xff0000 | 0xff000000 |
DXGI_FORMAT_R16G16_UNORM D3DFMT_G16R16 |
DDS_RGBA | 32 | 0xffff | 0xffff0000 | ||
** DXGI_FORMAT_R10G10B10A2_UNORM D3DFMT_A2B10G10R10 |
DDS_RGBA | 32 | 0x3ff | 0xffc00 | 0x3ff00000 | |
DXGI_FORMAT_R16G16_UNORM D3DFMT_G16R16 |
DDS_RGB | 32 | 0xffff | 0xffff0000 | ||
DXGI_FORMAT_B5G5R5A1_UNORM D3DFMT_A1R5G5B5 |
DDS_RGBA | 16 | 0x7c00 | 0x3e0 | 0x1f | 0x8000 |
DXGI_FORMAT_B5G6R5_UNORM D3FMT_R5G6B5 |
DDS_RGB | 16 | 0xf800 | 0x7e0 | 0x1f | |
DXGI_A8_UNORM D3DFMT_A8 |
DDS_ALPHA | 8 | 0xff | |||
D3DFMT_A8R8G8B8 |
DDS_RGBA | 32 | 0xff0000 | 0xff00 | 0xff | 0xff000000 |
D3DFMT_X8R8G8B8 |
DDS_RGB | 32 | 0xff0000 | 0xff00 | 0xff | |
D3DFMT_X8B8G8R8 |
DDS_RGB | 32 | 0xff | 0xff00 | 0xff0000 | |
** D3DFMT_A2R10G10B10 |
DDS_RGBA | 32 | 0x3ff00000 | 0xffc00 | 0x3ff | 0xc0000000 |
D3DFMT_R8G8B8 |
DDS_RGB | 24 | 0xff0000 | 0xff00 | 0xff | |
D3DFMT_X1R5G5B5 |
DDS_RGB | 16 | 0x7c00 | 0x3e0 | 0x1f | |
D3DFMT_A4R4G4B4 |
DDS_RGBA | 16 | 0xf00 | 0xf0 | 0xf | 0xf000 |
D3DFMT_X4R4G4B4 |
DDS_RGB | 16 | 0xf00 | 0xf0 | 0xf | |
D3DFMT_A8R3G3B2 |
DDS_RGBA | 16 | 0xe0 | 0x1c | 0x3 | 0xff00 |
D3DFMT_A8L8 |
DDS_LUMINANCE | 16 | 0xff | 0xff00 | ||
D3DFMT_L16 |
DDS_LUMINANCE | 16 | 0xffff | |||
D3DFMT_L8 |
DDS_LUMINANCE | 8 | 0xff | |||
D3DFMT_A4L4 |
DDS_LUMINANCE | 8 | 0xf | 0xf0 |
리소스 형식 | dwFlags | dwFourCC |
---|---|---|
DXGI_FORMAT_BC1_UNORM D3DFMT_DXT1 |
DDS_FOURCC | "DXT1" |
DXGI_FORMAT_BC2_UNORM D3DFMT_DXT3 |
DDS_FOURCC | "DXT3" |
DXGI_FORMAT_BC3_UNORM D3DFMT_DXT5 |
DDS_FOURCC | "DXT5" |
* DXGI_FORMAT_BC4_UNORM |
DDS_FOURCC | "BC4U" |
* DXGI_FORMAT_BC4_SNORM |
DDS_FOURCC | "BC4S" |
* DXGI_FORMAT_BC5_UNORM |
DDS_FOURCC | "ATI2" |
* DXGI_FORMAT_BC5_SNORM |
DDS_FOURCC | "BC5S" |
DXGI_FORMAT_R8G8_B8G8_UNORM D3DFMT_R8G8_B8G8 |
DDS_FOURCC | "RGBG" |
DXGI_FORMAT_G8R8_G8B8_UNORM D3DFMT_G8R8_G8B8 |
DDS_FOURCC | "GRGB" |
* DXGI_FORMAT_R16G16B16A16_UNORM D3DFMT_A16B16G16R16 |
DDS_FOURCC | 36 |
* DXGI_FORMAT_R16G16B16A16_SNORM D3DFMT_Q16W16V16U16 |
DDS_FOURCC | 110 |
* DXGI_FORMAT_R16_FLOAT D3DFMT_R16F |
DDS_FOURCC | 111 |
* DXGI_FORMAT_R16G16_FLOAT D3DFMT_G16R16F |
DDS_FOURCC | 112 |
* DXGI_FORMAT_R16G16B16A16_FLOAT D3DFMT_A16B16G16R16F |
DDS_FOURCC | 113 |
* DXGI_FORMAT_R32_FLOAT D3DFMT_R32F |
DDS_FOURCC | 114 |
* DXGI_FORMAT_R32G32_FLOAT D3DFMT_G32R32F |
DDS_FOURCC | 115 |
* DXGI_FORMAT_R32G32B32A32_FLOAT D3DFMT_A32B32G32R32F |
DDS_FOURCC | 116 |
D3DFMT_DXT2 |
DDS_FOURCC | "DXT2" |
D3DFMT_DXT4 |
DDS_FOURCC | "DXT4" |
D3DFMT_UYVY |
DDS_FOURCC | "UYVY" |
D3DFMT_YUY2 |
DDS_FOURCC | "YUY2" |
D3DFMT_CxV8U8 |
DDS_FOURCC | 117 |
모든 DXGI 형식 | DDS_FOURCC | "DX10" |
* = 강력한 DDS 판독기는 이러한 레거시 형식 코드를 처리할 수 있어야 합니다. 그러나 이러한 DDS 판독기는 모호성을 방지하기 위해 이러한 형식 코드를 작성할 때 "DX10" 헤더 확장을 사용하는 것을 선호해야 합니다.
** = DDS 판독기 및 기록기의 일반적인 구현에서 몇 가지 오랜 문제로 인해 10:10:10:2 형식 데이터를 작성하는 가장 강력한 방법은 DXGI_FORMAT 코드 "24"(즉, DXGI_FORMAT_R10G10B10A2_UNORM 값)와 함께 "DX10" 헤더 확장을 사용하는 것입니다. D3DFMT_A2R10G10B10 데이터는 DXGI_FORMAT_R10G10B10A2_UNORM 형식 DDS 파일로 작성되기 전에 10:10:10:2 형식 데이터로 변환해야 합니다.