extern "C" void gxpport_decodeimmutable_from_selfidentifying (unsigned char* srcBuffer, int length, int* imgWidth, int* imgHeight, gxpport_image_native_handle *newImmutableImagePtr, gxutl_native_image_error_codes* creationErrorPtr) { MIDP_ERROR err; gxutl_image_format format; unsigned int w, h; err = gxutl_image_get_info(srcBuffer, (unsigned int)length, &format, &w, &h); if (err != MIDP_ERROR_NONE || format == GXUTL_IMAGE_FORMAT_UNSUPPORTED) { *creationErrorPtr = GXUTL_NATIVE_IMAGE_UNSUPPORTED_FORMAT_ERROR; return; } /* Check resource limit */ int rscSize = ImgRegionRscSize(NULL, w, h); if (midpCheckResourceLimit(RSC_TYPE_IMAGE_IMMUT, rscSize) == 0) { /* Exceed Resource limit */ *creationErrorPtr = GXUTL_NATIVE_IMAGE_RESOURCE_LIMIT; return; } bool loadResult = FALSE; _Platform_ImmutableImage* immutableImage = (_Platform_ImmutableImage*)midpMalloc(sizeof(_Platform_ImmutableImage)); if (immutableImage == NULL) { *creationErrorPtr = GXUTL_NATIVE_IMAGE_OUT_OF_MEMORY_ERROR; return; } switch(format) { case GXUTL_IMAGE_FORMAT_JPEG: case GXUTL_IMAGE_FORMAT_PNG: immutableImage->qimage = new QImage(); if (NULL == immutableImage->qimage) { *creationErrorPtr = GXUTL_NATIVE_IMAGE_OUT_OF_MEMORY_ERROR; return; } if (immutableImage->qimage->loadFromData((uchar*)srcBuffer, (unsigned int)length)) { *imgWidth = immutableImage->qimage->width(); *imgHeight = immutableImage->qimage->height(); if ((0 == *imgWidth) || (0 == *imgHeight)) { delete immutableImage->qimage; } else { immutableImage->marker = 4; loadResult = TRUE; } } else { delete immutableImage->qimage; immutableImage->qimage = NULL; } break; case GXUTL_IMAGE_FORMAT_RAW: loadResult = load_raw(&immutableImage->qimage, (gxutl_image_buffer_raw*)srcBuffer, (unsigned int)length, KNI_FALSE, imgWidth, imgHeight); immutableImage->marker = 5; break; default: /* Shouldn't be here */ *creationErrorPtr = GXUTL_NATIVE_IMAGE_UNSUPPORTED_FORMAT_ERROR; return; } if (!loadResult) { midpFree(immutableImage); *creationErrorPtr = GXUTL_NATIVE_IMAGE_DECODING_ERROR; return; } /* Image creation succeeds */ if (midpIncResourceCount(RSC_TYPE_IMAGE_IMMUT, rscSize) == 0) { REPORT_ERROR(LC_LOWUI, "Error in updating resource limit" " for Immutable image"); } immutableImage->qpixmap = NULL; *newImmutableImagePtr = immutableImage; *creationErrorPtr = GXUTL_NATIVE_IMAGE_NO_ERROR; }
extern "C" void gxpport_decodeimmutable_to_platformbuffer (unsigned char* srcBuffer, long length, unsigned char** ret_dataBuffer, long* ret_length, gxutl_native_image_error_codes* creationErrorPtr) { gxutl_image_format format; MIDP_ERROR err; unsigned int w, h; err = gxutl_image_get_info(srcBuffer, (unsigned int)length, &format, &w, &h); switch (err) { case MIDP_ERROR_NONE: break; /* continue */ case MIDP_ERROR_IMAGE_CORRUPTED: *creationErrorPtr = GXUTL_NATIVE_IMAGE_DECODING_ERROR; return; default: *creationErrorPtr = GXUTL_NATIVE_IMAGE_UNSUPPORTED_FORMAT_ERROR; return; } switch (format) { case GXUTL_IMAGE_FORMAT_RAW: /* already in RAW format. make a copy */ { unsigned char* dataBuffer = (unsigned char*) midpMalloc(length); if (NULL == dataBuffer) { *creationErrorPtr = GXUTL_NATIVE_IMAGE_OUT_OF_MEMORY_ERROR; } else { memcpy(dataBuffer, srcBuffer, length); *ret_dataBuffer = dataBuffer; *ret_length = length; *creationErrorPtr = GXUTL_NATIVE_IMAGE_NO_ERROR; } } break; case GXUTL_IMAGE_FORMAT_JPEG: case GXUTL_IMAGE_FORMAT_PNG: { QImage qimage; if (qimage.loadFromData((uchar*)srcBuffer, (unsigned int)length)) { int imgWidth = qimage.width(); int imgHeight = qimage.height(); if ((0 == imgWidth) || (0 == imgHeight)) { *creationErrorPtr = GXUTL_NATIVE_IMAGE_DECODING_ERROR; } else { QImage image; if (IMAGE_DEPTH != qimage.depth()) { image = qimage.convertDepth(IMAGE_DEPTH); } else { image = qimage; } *ret_length = offsetof(gxutl_image_buffer_raw, data) + image.numBytes(); gxutl_image_buffer_raw *dataBuffer = (gxutl_image_buffer_raw *) midpMalloc(*ret_length); if (NULL == dataBuffer) { *creationErrorPtr = GXUTL_NATIVE_IMAGE_OUT_OF_MEMORY_ERROR; } else { dataBuffer->width = (unsigned int)imgWidth; dataBuffer->height = (unsigned int)imgHeight; dataBuffer->hasAlpha = (unsigned int)image.hasAlphaBuffer(); memcpy(dataBuffer->header, gxutl_raw_header, 4); memcpy(dataBuffer->data, image.bits(), image.numBytes()); *ret_dataBuffer = (unsigned char *)dataBuffer; *creationErrorPtr = GXUTL_NATIVE_IMAGE_NO_ERROR; } } } else { *creationErrorPtr = GXUTL_NATIVE_IMAGE_DECODING_ERROR; } } break; default: *creationErrorPtr = GXUTL_NATIVE_IMAGE_UNSUPPORTED_FORMAT_ERROR; break; } /* switch (format) */ }
/** * Decodes the given input data into a cache representation that can * be saved and loaded quickly. * The input data should be in a self-identifying format; that is, * the data must contain a description of the decoding process. * * @param srcBuffer input data to be decoded. * @param length length of the input data. * @param ret_dataBuffer pointer to the platform representation data that * be saved. * @param ret_length pointer to the length of the return data. * @return one of error codes: * MIDP_ERROR_NONE, * MIDP_ERROR_OUT_MEM, * MIDP_ERROR_UNSUPPORTED, * MIDP_ERROR_OUT_OF_RESOURCE, * MIDP_ERROR_IMAGE_CORRUPTED */ MIDP_ERROR gx_decode_data2cache(unsigned char* srcBuffer, unsigned int length, unsigned char** ret_dataBuffer, unsigned int* ret_length) { unsigned int pixelSize, alphaSize; gxutl_image_format format; MIDP_ERROR err; gxj_screen_buffer sbuf; gxutl_image_buffer_raw *rawBuffer; gxutl_native_image_error_codes creationError = GXUTL_NATIVE_IMAGE_NO_ERROR; err = gxutl_image_get_info(srcBuffer, length, &format, (unsigned int *)&sbuf.width, (unsigned int *)&sbuf.height); if (err != MIDP_ERROR_NONE) { return err; } pixelSize = sizeof(gxj_pixel_type) * sbuf.width * sbuf.height; alphaSize = sizeof(gxj_alpha_type) * sbuf.width * sbuf.height; switch (format) { case GXUTL_IMAGE_FORMAT_JPEG: /* JPEG does not contain alpha data */ alphaSize = 0; /* Fall through */ case GXUTL_IMAGE_FORMAT_PNG: /* Decode PNG/JPEG to screen buffer format */ rawBuffer = (gxutl_image_buffer_raw *) midpMalloc(offsetof(gxutl_image_buffer_raw, data)+pixelSize+alphaSize); if (rawBuffer == NULL) { return MIDP_ERROR_OUT_MEM; } sbuf.pixelData = (gxj_pixel_type *)rawBuffer->data; if (format == GXUTL_IMAGE_FORMAT_PNG) { sbuf.alphaData = rawBuffer->data + pixelSize; rawBuffer->hasAlpha = decode_png(srcBuffer, length, &sbuf, &creationError); if (!rawBuffer->hasAlpha) { sbuf.alphaData = NULL; alphaSize = 0; /* Exclude alpha data */ } } else { sbuf.alphaData = NULL; rawBuffer->hasAlpha = KNI_FALSE; decode_jpeg(srcBuffer, length, &sbuf, &creationError); } if (GXUTL_NATIVE_IMAGE_NO_ERROR != creationError) { midpFree(rawBuffer); return MIDP_ERROR_IMAGE_CORRUPTED; } memcpy(rawBuffer->header, gxutl_raw_header, 4); rawBuffer->width = sbuf.width; /* Use default endian */ rawBuffer->height = sbuf.height; /* Use default endian */ *ret_dataBuffer = (unsigned char *)rawBuffer; *ret_length = offsetof(gxutl_image_buffer_raw, data)+pixelSize+alphaSize; return MIDP_ERROR_NONE; case GXUTL_IMAGE_FORMAT_RAW: /* Already in screen buffer format, simply copy the data */ *ret_dataBuffer = (unsigned char *)midpMalloc(length); if (*ret_dataBuffer == NULL) { return MIDP_ERROR_OUT_MEM; } else { memcpy(*ret_dataBuffer, srcBuffer, length); *ret_length = length; return MIDP_ERROR_NONE; } default: return MIDP_ERROR_UNSUPPORTED; } /* switch (image_type) */ }