⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 readerwritergif.cpp

📁 最新osg包
💻 CPP
📖 第 1 页 / 共 2 页
字号:
            cmentry = colormap ? &colormap->Colors[col] : NULL;            if (cmentry)            {                *ptr++ = cmentry->Red;                *ptr++ = cmentry->Green;                *ptr++ = cmentry->Blue;            }            else            {                *ptr++ = col;                *ptr++ = col;                *ptr++ = col;            }        }        *ptr++ = (col == transparent ? 0x00 : 0xff);    }}int gif_read_stream(GifFileType *gfile, GifByteType *gdata, int glength){    std::istream *stream = (std::istream*)gfile->UserData; //Get pointer to istream    stream->read((char*)gdata,glength); //Read requested amount of data    return stream->gcount();}unsigned char *simage_gif_load(std::istream& fin,int *width_ret,int *height_ret,int *numComponents_ret,GifImageStream** obj){    int i, j, n, row, col, width, height, extcode;    unsigned char * rowdata;    unsigned char * buffer, * ptr;    unsigned char bg;    int transparent, delaytime;    GifRecordType recordtype;    GifByteType * extension;    GifFileType * giffile;    GifColorType * bgcol;    /* The way an interlaced image should be read - offsets and jumps */    int interlacedoffset[] = { 0, 4, 2, 1 };    int interlacedjumps[] = { 8, 8, 4, 2 };    giffile = DGifOpen(&fin,gif_read_stream);    if (!giffile)    {        giferror = ERR_OPEN;        return NULL;    }    transparent = -1;            /* no transparent color by default */    delaytime = 8;               /* delay time of a frame  */    n = giffile->SHeight * giffile->SWidth;    buffer = new unsigned char [n * 4];    if (!buffer)    {        giferror = ERR_MEM;        return NULL;    }    rowdata = new unsigned char [giffile->SWidth];    if (!rowdata)    {        giferror = ERR_MEM;        delete [] buffer;        return NULL;    }    bg = giffile->SBackGroundColor;    if (giffile->SColorMap && bg < giffile->SColorMap->ColorCount)    {        bgcol = &giffile->SColorMap->Colors[bg];    }    else bgcol = NULL;    ptr = buffer;    for (i = 0; i < n; i++)    {        if (bgcol)        {            *ptr++ = bgcol->Red;            *ptr++ = bgcol->Green;            *ptr++ = bgcol->Blue;            *ptr++ = 0xff;        }        else        {            *ptr++ = 0x00;            *ptr++ = 0x00;            *ptr++ = 0x00;            *ptr++ = 0xff;        }    }    /* Scan the content of the GIF file and load the image(s) in: */    int gif_num=0;    do    {        if (DGifGetRecordType(giffile, &recordtype) == GIF_ERROR)        {            giferror = ERR_READ;            delete [] buffer;            delete [] rowdata;            return NULL;        }        switch (recordtype)        {            case IMAGE_DESC_RECORD_TYPE:                /* start recording image stream if more than one image found  */                gif_num++;                if ( gif_num==2 )                {                    *obj = new GifImageStream;                    (*obj)->addToImageStream( giffile->SWidth, giffile->SHeight, 1, 4, delaytime, buffer );                    unsigned char* destbuffer = new unsigned char [n * 4];                    buffer = (unsigned char*)memcpy( destbuffer, buffer, n*4 );                }                if (DGifGetImageDesc(giffile) == GIF_ERROR)                {                    giferror = ERR_READ;                    delete [] buffer;                    delete [] rowdata;                    return NULL;                }                /* subimage position in composite image */                row = giffile->Image.Top;                col = giffile->Image.Left;                width = giffile->Image.Width;                height = giffile->Image.Height;                if (giffile->Image.Left + giffile->Image.Width > giffile->SWidth ||                    giffile->Image.Top + giffile->Image.Height > giffile->SHeight)                {                    /* image is not confined to screen dimension */                    giferror = ERR_READ;                    delete [] buffer;                    delete [] rowdata;                    return NULL;                }                if (giffile->Image.Interlace)                {                    //fprintf(stderr,"interlace\n");                    /* Need to perform 4 passes on the images: */                    for (i = 0; i < 4; i++)                    {                        for (j = row + interlacedoffset[i]; j < row + height;                            j += interlacedjumps[i])                        {                            if (DGifGetLine(giffile, rowdata, width) == GIF_ERROR)                            {                                giferror = ERR_READ;                                delete [] buffer;                                delete [] rowdata;                                return NULL;                            }                            else decode_row(giffile, buffer, rowdata, col, j, width, transparent);                        }                    }                }                else                {                    for (i = 0; i < height; i++, row++)                    {                        if (DGifGetLine(giffile, rowdata, width) == GIF_ERROR)                        {                            giferror = ERR_READ;                            delete [] buffer;                            delete [] rowdata;                            return NULL;                        }                        else decode_row(giffile, buffer, rowdata, col, row, width, transparent);                    }                }                // Record gif image stream                 if ( *obj && obj )                {                    (*obj)->addToImageStream( giffile->SWidth, giffile->SHeight, 1, 4, delaytime, buffer );                    unsigned char* destbuffer = new unsigned char [n * 4];                    buffer = (unsigned char*)memcpy( destbuffer, buffer, n*4 );                }                break;            case EXTENSION_RECORD_TYPE:                /* Skip any extension blocks in file: */                if (DGifGetExtension(giffile, &extcode, &extension) == GIF_ERROR)                {                    giferror = ERR_READ;                    delete [] buffer;                    delete [] rowdata;                    return NULL;                }                /* transparent test from the gimp gif-plugin. Open Source rulez! */                else if (extcode == 0xf9)                {                    if (extension[0] >= 4 && extension[1] & 0x1) transparent = extension[4];                    else transparent = -1;                    delaytime = (extension[3]<<8)+extension[2];    // minimum unit 1/100s, so 8 here means 8/100s                 }                while (extension != NULL)                {                    if (DGifGetExtensionNext(giffile, &extension) == GIF_ERROR)                    {                        giferror = ERR_READ;                        delete [] buffer;                        delete [] rowdata;                        return NULL;                    }                }                break;            case TERMINATE_RECORD_TYPE:                break;            default:             /* Should be trapped by DGifGetRecordType. */                break;        }    }    while (recordtype != TERMINATE_RECORD_TYPE);    delete [] rowdata;    *width_ret = giffile->SWidth;    *height_ret = giffile->SHeight;    *numComponents_ret = 4;    DGifCloseFile(giffile);    return buffer;}class ReaderWriterGIF : public osgDB::ReaderWriter{    public:            ReaderWriterGIF()        {            supportsExtension("gif","GIF Image format");        }            virtual const char* className() const { return "GIF Image Reader"; }        ReadResult readGIFStream(std::istream& fin) const        {            unsigned char *imageData = NULL;            int width_ret;            int height_ret;            int numComponents_ret;            GifImageStream* gifStream = NULL;            imageData = simage_gif_load( fin,&width_ret,&height_ret,&numComponents_ret, &gifStream );            switch (giferror)            {                case ERR_OPEN:                    return ReadResult("GIF loader: Error opening file");                case ERR_READ:                    return ReadResult("GIF loader: Error reading file");                case ERR_MEM:                    return ReadResult("GIF loader: Out of memory error");            }            // Use GifImageStream to display animate GIFs             if ( gifStream )            {                osg::notify(osg::DEBUG_INFO)<<"Using GifImageStream ..."<<std::endl;                return gifStream;            }            if (imageData==NULL) return ReadResult::FILE_NOT_HANDLED;            int s = width_ret;            int t = height_ret;            int r = 1;            int internalFormat = numComponents_ret;            unsigned int pixelFormat =                numComponents_ret == 1 ? GL_LUMINANCE :            numComponents_ret == 2 ? GL_LUMINANCE_ALPHA :            numComponents_ret == 3 ? GL_RGB :            numComponents_ret == 4 ? GL_RGBA : (GLenum)-1;            unsigned int dataType = GL_UNSIGNED_BYTE;            osg::Image* pOsgImage = new osg::Image;            pOsgImage->setImage(s,t,r,                internalFormat,                pixelFormat,                dataType,                imageData,                osg::Image::USE_NEW_DELETE);            return pOsgImage;        }        virtual ReadResult readObject(std::istream& fin,const osgDB::ReaderWriter::Options* options =NULL) const        {            return readImage(fin, options);        }        virtual ReadResult readObject(const std::string& file, const osgDB::ReaderWriter::Options* options =NULL) const        {            return readImage(file, options);        }        virtual ReadResult readImage(std::istream& fin,const osgDB::ReaderWriter::Options* =NULL) const        {            return readGIFStream(fin);        }        virtual ReadResult readImage(const std::string& file, const osgDB::ReaderWriter::Options* options) const        {            std::string ext = osgDB::getLowerCaseFileExtension(file);            if (!acceptsExtension(ext)) return ReadResult::FILE_NOT_HANDLED;            std::string fileName = osgDB::findDataFile( file, options );            if (fileName.empty()) return ReadResult::FILE_NOT_FOUND;            std::ifstream istream(fileName.c_str(), std::ios::in | std::ios::binary);            if(!istream) return ReadResult::FILE_NOT_HANDLED;            ReadResult rr = readGIFStream(istream);            if(rr.validImage()) rr.getImage()->setFileName(file);            return rr;        }};// now register with Registry to instantiate the above// reader/writer.REGISTER_OSGPLUGIN(gif, ReaderWriterGIF)

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -