3 * Copyright 2014 Google Inc.
5 * Use of this source code is governed by a BSD-style license that can be
6 * found in the LICENSE file.
10 #ifndef SkKTXFile_DEFINED
11 #define SkKTXFile_DEFINED
14 #include "SkTextureCompressor.h"
16 #include "SkTDArray.h"
21 class SkStreamRewindable;
26 // KTX is a general texture data storage file format ratified by the Khronos Group. As an
27 // overview, a KTX file contains all of the appropriate values needed to fully specify a
28 // texture in an OpenGL application, including the use of compressed data.
30 // A full format specification can be found here:
31 // http://www.khronos.org/opengles/sdk/tools/KTX/file_format_spec/
35 // The ownership of the data remains with the caller. This class is intended
36 // to be used as a logical wrapper around the data in order to properly
38 SkKTXFile(SkData* data)
39 : fData(data), fSwapBytes(false)
42 fValid = this->readKTXFile(fData->bytes(), fData->size());
45 bool valid() const { return fValid; }
47 int width() const { return static_cast<int>(fHeader.fPixelWidth); }
48 int height() const { return static_cast<int>(fHeader.fPixelHeight); }
50 const uint8_t *pixelData(int mipmap = 0) const {
51 SkASSERT(!this->valid() || mipmap < fPixelData.count());
52 return this->valid() ? fPixelData[mipmap].data() : NULL;
55 // If the decoded KTX file has the following key, then it will
56 // return the associated value. If not found, the empty string
58 SkString getValueForKey(const SkString& key) const;
60 int numMipmaps() const { return static_cast<int>(fHeader.fNumberOfMipmapLevels); }
62 bool isCompressedFormat(SkTextureCompressor::Format fmt) const;
66 static bool is_ktx(const uint8_t *data);
67 static bool is_ktx(SkStreamRewindable* stream);
69 static bool WriteETC1ToKTX(SkWStream* stream, const uint8_t *etc1Data,
70 uint32_t width, uint32_t height);
71 static bool WriteBitmapToKTX(SkWStream* stream, const SkBitmap& bitmap);
74 // The blob holding the file data.
75 SkAutoTUnref<SkData> fData;
77 // This header captures all of the data that describes the format
78 // of the image data in a KTX file.
83 uint32_t fGLInternalFormat;
84 uint32_t fGLBaseInternalFormat;
86 uint32_t fPixelHeight;
88 uint32_t fNumberOfArrayElements;
89 uint32_t fNumberOfFaces;
90 uint32_t fNumberOfMipmapLevels;
91 uint32_t fBytesOfKeyValueData;
93 Header() { memset(this, 0, sizeof(*this)); }
96 // A Key Value pair stored in the KTX file. There may be
97 // arbitrarily many of these.
100 KeyValue(size_t size) : fDataSz(size) { }
101 bool readKeyAndValue(const uint8_t *data);
102 size_t size() const { return fDataSz; }
103 const SkString& key() const { return fKey; }
104 const SkString& value() const { return fValue; }
105 bool writeKeyAndValueForKTX(SkWStream* strm);
107 const size_t fDataSz;
112 static KeyValue CreateKeyValue(const char *key, const char *value);
114 // The pixel data for a single mipmap level in an image. Based on how
115 // the rest of the data is stored, this may be compressed, a cubemap, etc.
116 // The header will describe the format of this data.
119 PixelData(const uint8_t *ptr, size_t sz) : fDataSz(sz), fDataPtr(ptr) { }
120 const uint8_t *data() const { return fDataPtr; }
121 size_t dataSize() const { return fDataSz; }
123 const size_t fDataSz;
124 const uint8_t *fDataPtr;
127 // This function is only called once from the constructor. It loads the data
128 // and populates the appropriate fields of this class
129 // (fKeyValuePairs, fPixelData, fSwapBytes)
130 bool readKTXFile(const uint8_t *data, size_t dataLen);
132 SkTArray<KeyValue> fKeyValuePairs;
133 SkTDArray<PixelData> fPixelData;
136 // If the endianness of the platform is different than the file,
137 // then we need to do proper byte swapping.
140 // Read an integer from a buffer, advance the buffer, and swap
141 // bytes if fSwapBytes is set
142 uint32_t readInt(const uint8_t** buf, size_t* bytesLeft) const;
145 #endif // SkKTXFile_DEFINED