前往小程序,Get更优阅读体验!
立即前往
首页
学习
活动
专区
工具
TVP
发布
社区首页 >专栏 >libjpeg的问题

libjpeg的问题

作者头像
meteoric
发布2018-11-20 11:39:35
1.2K0
发布2018-11-20 11:39:35
举报
文章被收录于专栏:游戏杂谈游戏杂谈

游戏项目是基于cocos2d-x开发的,但线上发现一个bug就是玩家在设置完自定义头像后直接闪退。凡是在设置该玩家头像的地方,游戏就直接闪退。最终定位到的问题是图片数据源有问题,我的机器是win7,图片能预览,但同事xp系统该图片是无法预览的,默认的系统自带的图片查看工具也无法显示图片。

把图片拉到sublime text中,查看文件二进制,发现它并非一个完整的jpeg格式

image
image

没有jpeg格式的结束标识0xff  0xd9

我在windows下调试代码,发现是在CCImageCommon_cpp.h中的_initWithJpgData方法调用jpeg_finish_decompress函数时程序直接退出了

代码语言:javascript
复制
bool CCImage::_initWithJpgData(void * data, int nSize, bool bNeedDecode /*= false*/)
{
    int nRandomBytes = 0;
    if (bNeedDecode) nRandomBytes = RANDOM_BYTES;

    if (bNeedDecode)
    {
        data = (unsigned char *)data + nRandomBytes;
        nSize = nSize - nRandomBytes;
    }

    /* these are standard libjpeg structures for reading(decompression) */
    struct jpeg_decompress_struct cinfo;
    struct jpeg_error_mgr jerr;
    /* libjpeg data structure for storing one row, that is, scanline of an image */
    JSAMPROW row_pointer[1] = {0};
    unsigned long location = 0;
    unsigned int i = 0;

    bool bRet = false;
    do 
    {
        /* here we set up the standard libjpeg error handler */
        cinfo.err = jpeg_std_error( &jerr );

        /* setup decompression process and source, then read JPEG header */
        jpeg_create_decompress( &cinfo );

        jpeg_mem_src( &cinfo, (unsigned char *) data, nSize );

        /* reading the image header which contains image information */
        jpeg_read_header( &cinfo, true );

        // we only support RGB or grayscale
        if (cinfo.jpeg_color_space != JCS_RGB)
        {
            if (cinfo.jpeg_color_space == JCS_GRAYSCALE || cinfo.jpeg_color_space == JCS_YCbCr)
            {
                cinfo.out_color_space = JCS_RGB;
            }
        }
        else
        {
            break;
        }

        /* Start decompression jpeg here */
        jpeg_start_decompress( &cinfo );

        /* init image info */
        m_nWidth  = (short)(cinfo.image_width);
        m_nHeight = (short)(cinfo.image_height);
        m_bHasAlpha = false;
        m_bPreMulti = false;
        m_nBitsPerComponent = 8;
        row_pointer[0] = new unsigned char[cinfo.output_width*cinfo.output_components];
        CC_BREAK_IF(! row_pointer[0]);

        m_pData = new unsigned char[cinfo.output_width*cinfo.output_height*cinfo.output_components];
        CC_BREAK_IF(! m_pData);

        /* now actually read the jpeg into the raw buffer */
        /* read one scan line at a time */
        while( cinfo.output_scanline < cinfo.image_height )
        {
            jpeg_read_scanlines( &cinfo, row_pointer, 1 );
            for( i=0; i<cinfo.image_width*cinfo.output_components;i++) 
            {
                m_pData[location++] = row_pointer[0][i];
            }
        }

        jpeg_finish_decompress( &cinfo );
        jpeg_destroy_decompress( &cinfo );
        /* wrap up decompression, destroy objects, free pointers and close open files */        
        bRet = true;
    } while (0);

    CC_SAFE_DELETE_ARRAY(row_pointer[0]);
    return bRet;
}

后面我用jpegtran(https://github.com/imagemin/jpegtran-bin)工具复制有问题的图片时, 也提示错误了

image
image

参考文章:

[1] 小议libjpeg解压损坏文件时的错误处理

[2] JPEG File Layout and Format

解决方案可以参考这篇文章:libjpeg解压损坏文件时的错误处理

本文参与 腾讯云自媒体分享计划,分享自作者个人站点/博客。
原始发表:2014-09-28 ,如有侵权请联系 cloudcommunity@tencent.com 删除

本文分享自 作者个人站点/博客 前往查看

如有侵权,请联系 cloudcommunity@tencent.com 删除。

本文参与 腾讯云自媒体分享计划  ,欢迎热爱写作的你一起参与!

评论
登录后参与评论
0 条评论
热度
最新
推荐阅读
领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档