예제 #1
0
    void onDraw(SkCanvas* canvas) override {
        SkBitmap bm;
        SkString pkmFilename = GetResourcePath("mandrill_128.pkm");
        SkAutoDataUnref fileData(SkData::NewFromFileName(pkmFilename.c_str()));
        if (nullptr == fileData) {
            SkDebugf("Could not open the file. Did you forget to set the resourcePath?\n");
            return;
        }

        SkAutoMalloc am(fileData->size());
        memcpy(am.get(), fileData->data(), fileData->size());

        int width, height;
        if (!slice_etc1_data(am.get(), &width, &height)) {
            SkDebugf("ETC1 Data is poorly formatted.\n");
            return;
        }

        SkASSERT(124 == width);
        SkASSERT(124 == height);

        size_t dataSz = etc1_get_encoded_data_size(width, height) + ETC_PKM_HEADER_SIZE;
        SkAutoDataUnref nonPOTData(SkData::NewWithCopy(am.get(), dataSz));

        if (!SkInstallDiscardablePixelRef(nonPOTData, &bm)) {
            SkDebugf("Could not install discardable pixel ref.\n");
            return;
        }

        canvas->drawBitmap(bm, 0, 0);
    }
예제 #2
0
JNIEXPORT jobject JNICALL Java_com_badlogic_gdx_graphics_glutils_ETC1_encodeImage
  (JNIEnv *env, jclass, jobject imageData, jint offset, jint width, jint height, jint pixelSize) {
	etc1_byte* imgPtr = (etc1_byte*)env->GetDirectBufferAddress(imageData) + offset;
	int compressedSize = etc1_get_encoded_data_size(width, height);
	etc1_byte* comprPtr = (etc1_byte*)malloc(compressedSize);
	etc1_encode_image(imgPtr, width, height, pixelSize, width * pixelSize, comprPtr);
	return env->NewDirectByteBuffer(comprPtr, compressedSize);
}
	 JNIEXPORT jint JNICALL Java_com_badlogic_gdx_graphics_glutils_ETC1_getCompressedDataSize(JNIEnv* env, jclass clazz, jint width, jint height) {


//@line:204

		return etc1_get_encoded_data_size(width, height);
	

}
static inline jobject wrapped_Java_com_badlogic_gdx_graphics_glutils_ETC1_encodeImage
(JNIEnv* env, jclass clazz, jobject obj_imageData, jint offset, jint width, jint height, jint pixelSize, char* imageData) {

//@line:260

		int compressedSize = etc1_get_encoded_data_size(width, height);
		etc1_byte* compressedData = (etc1_byte*)malloc(compressedSize);
		etc1_encode_image((etc1_byte*)imageData + offset, width, height, pixelSize, width * pixelSize, compressedData);
		return env->NewDirectByteBuffer(compressedData, compressedSize);
	
}
예제 #5
0
bool SkKTXFile::WriteETC1ToKTX(SkWStream* stream, const uint8_t *etc1Data,
                               uint32_t width, uint32_t height) {
    // First thing's first, write out the magic identifier and endianness...
    if (!stream->write(KTX_FILE_IDENTIFIER, KTX_FILE_IDENTIFIER_SIZE)) {
        return false;
    }

    if (!stream->write(&kKTX_ENDIANNESS_CODE, 4)) {
        return false;
    }
    
    Header hdr;
    hdr.fGLType = 0;
    hdr.fGLTypeSize = 1;
    hdr.fGLFormat = 0;
    hdr.fGLInternalFormat = GR_GL_COMPRESSED_ETC1_RGB8;
    hdr.fGLBaseInternalFormat = GR_GL_RGB;
    hdr.fPixelWidth = width;
    hdr.fPixelHeight = height;
    hdr.fNumberOfArrayElements = 0;
    hdr.fNumberOfFaces = 1;
    hdr.fNumberOfMipmapLevels = 1;

    // !FIXME! The spec suggests that we put KTXOrientation as a
    // key value pair in the header, but that means that we'd have to
    // pipe through the bitmap's orientation to properly do that.
    hdr.fBytesOfKeyValueData = 0;

    // Write the header
    if (!stream->write(&hdr, sizeof(hdr))) {
        return false;
    }

    // Write the size of the image data
    etc1_uint32 dataSize = etc1_get_encoded_data_size(width, height);
    if (!stream->write(&dataSize, 4)) {
        return false;
    }

    // Write the actual image data
    if (!stream->write(etc1Data, dataSize)) {
        return false;
    }

    return true;
}
예제 #6
0
/**
 *  Remove the last row and column of ETC1 blocks, effectively
 *  making a texture that started as power of two into a texture
 *  that is no longer power of two...
 */
bool slice_etc1_data(void *data, int* width, int* height) {

    // First, parse the data and get to it...
    etc1_byte *origData = reinterpret_cast<etc1_byte *>(data);
    if (!etc1_pkm_is_valid(origData)) {
        return false;
    }

    int origW = etc1_pkm_get_width(origData);
    int origH = etc1_pkm_get_height(origData);

    int blockWidth = (origW + 3) >> 2;
    int blockHeight = (origH + 3) >> 2;

    // Make sure that we have blocks to trim off..
    if (blockWidth < 2 || blockHeight < 2) {
        return false;
    }

    int newWidth = (blockWidth - 1) << 2;
    int newHeight = (blockHeight - 1) << 2;

    size_t newDataSz = etc1_get_encoded_data_size(newWidth, newHeight) + ETC_PKM_HEADER_SIZE;
    SkAutoMalloc am(newDataSz);

    etc1_byte *newData = reinterpret_cast<etc1_byte *>(am.get());

    etc1_pkm_format_header(newData, newWidth, newHeight);
    newData += ETC_PKM_HEADER_SIZE;
    origData += ETC_PKM_HEADER_SIZE;

    for (int j = 0; j < blockHeight - 1; ++j) {
        memcpy(newData, origData, (blockWidth - 1)*ETC1_ENCODED_BLOCK_SIZE);
        origData += blockWidth*ETC1_ENCODED_BLOCK_SIZE;
        newData += (blockWidth - 1)*ETC1_ENCODED_BLOCK_SIZE;
    }

    // Stick the data back whence it came
    memcpy(data, am.get(), newDataSz);
    *width = newWidth;
    *height = newHeight;

    return true;
}
예제 #7
0
GLuint loadTextureFromPKM(const ResourcePtr& pkmData, int &width, int &height)
{
#ifdef GL_ETC1_RGB8_OES
	const unsigned ETC_PKM_HEADER_SIZE = 16;
	if (pkmData->data().size() <= ETC_PKM_HEADER_SIZE)
	{
		LOGE("pkmData is not the right size. expected > %u, is: %zu", ETC_PKM_HEADER_SIZE, pkmData->data().size());
		return TEXTURE_LOAD_ERROR;
	}

	etc1_byte* header = &pkmData->data()[0];

	if (!etc1_pkm_is_valid(header))
		return TEXTURE_LOAD_ERROR;

	width = etc1_pkm_get_width(header);
	height = etc1_pkm_get_height(header);

	size_t encodedDataSize = etc1_get_encoded_data_size(width, height);

	if (pkmData->data().size() != ETC_PKM_HEADER_SIZE + encodedDataSize)
	{
		LOGE("pkmData is not the right size. expected: %zu, is: %zu", ETC_PKM_HEADER_SIZE + encodedDataSize, pkmData->data().size());
		return TEXTURE_LOAD_ERROR;
	}

	//Now generate the OpenGL texture object
	GLuint texture = genTexture();
	bindTexture2D(texture);
	compressedTexImage2D(GL_ETC1_RGB8_OES, width, height, encodedDataSize, static_cast<GLvoid*> (&pkmData->data()[ETC_PKM_HEADER_SIZE]));
	texParameter(GL_TEXTURE_MIN_FILTER, GL_LINEAR);
	texParameter(GL_TEXTURE_MAG_FILTER, GL_NEAREST);

	return texture;
#else
	LOGE("PKM texture format not supported by this platform");
	return TEXTURE_LOAD_ERROR;
#endif
}