ndk用libpng加载图片问题,求助!

问题描述

ndk用libpng加载图片问题,求助!
  (请高手看一下啊,采纳答案可以再提高悬赏分)
        能够获取到图片长度以及png头。但执行到png_set_read_fn(png_ptr, &imageInfo, readFileCallback );回调里的参数length一直为8,这个长度应该是像素*高度*宽度(大概是这么个意思,可能不准确),图片总长度是6位数,所以length肯定不应该是8。请问这个length是怎么计算的?我对libpng的机制不太熟。现状是由于回调中数据源数据缺失,执行到png_read_info出错。我认为是因为length计算的不对,求帮助!

代码如下

jni

 extern "C" JNIEXPORT void JNICALL Java_com_android_gl2jni_GL2JNILib_readFromAssets(
        JNIEnv* env,jclass obj,jobject assetManager)
{
   LOGI("ReadAssets");
   AAssetManager* mgr = AAssetManager_fromJava(env, assetManager);
   if(mgr==NULL)
   {
      LOGI("AAssetManager==NULL");
      return ;
   }
   LOGI("AAssetManager111");
   string filename = "car.png";
   AAsset* asset = AAssetManager_open(mgr, filename.c_str(), AASSET_MODE_UNKNOWN);
   LOGI("AAssetManager222");
   if(asset==NULL)
   {
      LOGI(" %s","asset==NULL");
      return ;
   }
   off_t bufferSize = AAsset_getLength(asset);
    LOGI("file size         : %ldn",bufferSize);

   char *tmpInfo = new char [bufferSize+1];
   tmpInfo[bufferSize] = 0;

   int numBytesRead = AAsset_read(asset, tmpInfo, bufferSize);

   //LOGI("tmpInfo is %s", tmpInfo);
   LOGI("AAssetManager333");

   bufferInfo = (unsigned char*)CPNGHandler::LoadFromStream(tmpInfo, (int)bufferSize);
   LOGI("AAssetManager444");
   /*获取文件大小*/
   if(NULL == bufferInfo)
   {
       LOGI("bufferInfo is NULL");
   }
  // int numBytesRead = AAsset_read(asset, bufferInfo, bufferSize);
  // LOGI("bufferInfo        : %sn",bufferInfo+54);
   //LOGI("buffer: %s",buffer);
    /*关闭文件*/
   AAsset_close(asset);
}
/////

void CPNGHandler::readFileCallback(png_structp png_ptr, png_bytep destination, png_size_t length )
{
    LOGI("readFileCallback length is %d ", length);
    ImageInfo* info = (ImageInfo*)png_get_io_ptr(png_ptr);
    memcpy(destination, info->data, length);
}

char* CPNGHandler::LoadFromStream(char* pngDatastring, int size)
{
    LOGI("LoadFromStream111 ");
    const int PNG_SIG_BYTES = 8;
    char pngSignature[PNG_SIG_BYTES];
   // pngDataStream.read(pngSignature, PNG_SIG_BYTES); // sizeof(char)
    memcpy((unsigned char*)pngSignature, pngDatastring, PNG_SIG_BYTES);
    if(!png_check_sig( (png_bytep)pngSignature, PNG_SIG_BYTES))
    {
        return NULL;
    }

    imageInfo.data = (unsigned char*)(pngDatastring + 8);
    imageInfo.size = size;
    LOGI("LoadFromStream222 ");

    png_structp png_ptr = png_create_read_struct(PNG_LIBPNG_VER_STRING, NULL, NULL, NULL);
    if (png_ptr == NULL)
    {
        return NULL;
    }

    png_infop info_ptr = png_create_info_struct(png_ptr);
    if (info_ptr == NULL)
    {
        png_destroy_read_struct(&png_ptr, NULL, NULL);
        return NULL;
    }
    LOGI("LoadFromStream333 ");

    if (setjmp(png_jmpbuf(png_ptr))) {
        png_destroy_read_struct(&png_ptr, &info_ptr, NULL);
        return NULL;
    }
    LOGI("LoadFromStream333 ");

    png_set_read_fn(png_ptr, &imageInfo, readFileCallback );

    //png_set_sig_bytes( png_ptr, 8);
    LOGI("LoadFromStream345 ");
    png_read_info( png_ptr, info_ptr);

    LOGI("LoadFromStream444 ");
    int _width, _height, _depth;
    bool _hasAlpha;
    int color_type, interlace_type;

    png_get_IHDR( png_ptr, info_ptr, (png_uint_32*)&_width, (png_uint_32*)&_height, &_depth, &color_type, &interlace_type, NULL, NULL );
    LOGI("LoadFromStream555 ");
    switch(color_type)
    {
        case PNG_COLOR_TYPE_RGB:
            _hasAlpha = false;
            break;
        case PNG_COLOR_TYPE_RGBA:
            _hasAlpha = true;
            break;
        default:
            return NULL;
            break;
    }

    png_size_t cols = png_get_rowbytes(png_ptr, info_ptr);

    png_bytepp row_pp = new png_bytep[_height];
    char * bitmapData = new char[ cols * _height ];
    bitmapData = (char*)png_get_rows(png_ptr, info_ptr);

    for( int i = 0; i < _height; ++i )
    {
        row_pp[_height - i - 1] = (png_bytep)&((char *)bitmapData)[ i * cols ];
    }

    png_read_image( png_ptr, row_pp );
    png_read_end( png_ptr, info_ptr );

    png_destroy_read_struct( &png_ptr, &info_ptr, 0 );
    LOGI("LoadFromStream666 ");
    delete [] row_pp;

   // GLuint _textureID = LoadFromPixels32(_width, _height, _hasAlpha, (GLuint *)bitmapData);

  //  delete [] bitmapData;
    LOGI("LoadFromStream data is%s ", bitmapData);
    return bitmapData;
    //return _textureID;
}

解决方案

问题呢?

时间: 2024-11-01 21:10:39

ndk用libpng加载图片问题,求助!的相关文章

ajax异步加载图片实例分析_AJAX相关

本文实例讲述了ajax异步加载图片的方法.分享给大家供大家参考,具体如下: 图片一般比较大,所以他们都是在基本网页加载后才逐渐加载上的,整个加载的过程非常不雅观,或者是从模糊逐渐变清晰,或者是从上往下拓展开(当然你也可以认为这些都是不错的特效).如果是通过定时更换img的src属性来实现图片的动态更换,由此带来的闪烁更让它难以接受,这可不是用alt属性就能让人愉快的. 联系时下比较热门的,号称"无"刷新的AJAX技术,利用XMLHttpRequest对象发起异步请求,待图像加载完毕再动

ajax异步加载图片实例分析

本文实例讲述了ajax异步加载图片的方法.分享给大家供大家参考,具体如下: 图片一般比较大,所以他们都是在基本网页加载后才逐渐加载上的,整个加载的过程非常不雅观,或者是从模糊逐渐变清晰,或者是从上往下拓展开(当然你也可以认为这些都是不错的特效).如果是通过定时更换img的src属性来实现图片的动态更换,由此带来的闪烁更让它难以接受,这可不是用alt属性就能让人愉快的. 联系时下比较热门的,号称"无"刷新的AJAX技术,利用XMLHttpRequest对象发起异步请求,待图像加载完毕再动

模仿SDWebImage实现异步加载图片

模仿SDWebImage实现异步加载图片 SDWebImage想必大家都不陌生吧,要实现它的图片异步加载功能这个还是很简单的. 注意:此处我只实现了异步加载图片,并没有将文件缓存到本地的打算哦:) 源码: UIImageView+YXImageView.h // // UIImageView+YXImageView.h // PicDemo // // Copyright (c) 2014年 Y.X. All rights reserved. // #import <UIKit/UIKit.h>

android-Glide加载图片后,图片显示模糊,如何配置Glide?

问题描述 Glide加载图片后,图片显示模糊,如何配置Glide? 在项目中使用了Glide加载图片,但是有些图片显示的非常模糊,该如何处理?Glide应该也会像imageloader一样有个配置方法去控制加载图片的质量吧? 解决方案 Glide加载和显示图片 解决方案二: http://blog.csdn.net/fancylovejava/article/details/44747759 解决方案三: 确定不是图片本身很模糊?

自己定制加载图片并加上转圈圈

// // HYBLoadImageView.h // CloudShopping // // Created by ljy-335 on 14-8-1. // Copyright (c) 2014年 uni2uni. All rights reserved. // #import <UIKit/UIKit.h> /*! * @brief 加载图片时,给图片加上转圈圈的状态,让用户知道图片未出现是因为网络不给力而造成的而不是没有图片 * @author huangyibiao */ @inte

Flash相册加载图片完毕等比缩放的类

每次做相册类的flash的时候,图片加载完毕之后都要写等比缩放的函数来处理加载图片. 今天又遇到了,也不知道哪根筋不对了,弄了十几分钟老是算法有错误.好好的一个美女图片被搞的惨不忍睹.所以写了这个类 直接放到我的as包里,以后不要再这么麻烦了. 贴一下,能用的朋友就用一用.看不上眼的也不要拍砖啊. 下边是代码及注释说明: /*   等比缩放   as1984 - qq:38657783   20091221   请注意包路径,我的as包都放在tools目录下.所以包的路径是 tools   如果

WPF循环加载图片导致内存溢出如何解决

程序场景:一系列的图片,从第一张到最后一张依次加载图片,形成"动画". 生成BitmapImage的方法有多种: 1.var source=new BitmapImage(new Uri("图片路径",UriKind.xxx)); 一般的场景使用这种方法还是比较方便快捷,但是对于本场景,内存恐怕得爆.2. var data =File.ReadAllBytes("图片路径"); var ms = new System.IO.MemoryStrea

Android中如何异步加载图片

研究了android从网络上异步加载图像,现总结如下: (1)由于android UI更新支持单一线程原则,所以从网络上取数据并更新到界面上,为了不阻塞主线程首先可能会想到以下方法. 在主线程中new 一个Handler对象,加载图像方法如下所示 private void loadImage(final String url, final int id) { handler.post(new Runnable() { public void run() { Drawable drawable =

Android加载图片内存溢出问题解决方法

  这篇文章主要介绍了Android加载图片内存溢出问题解决方法,本文讲解使用BitmapFactory.Options解决内存溢出问题,需要的朋友可以参考下 1. 在Android软件开发过程中,图片处理是经常遇到的. 在将图片转换成Bitmap的时候,由于图片的大小不一样,当遇到很大的图片的时候会出现超出内存的问题,为了解决这个问题Android API提供了BitmapFactory.Options这个类. 2. 由于Android对图片使用内存有限制,若是加载几兆的大图片便内存溢出.Bi