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

📄 readerwritertiff.cpp

📁 最新osg包
💻 CPP
📖 第 1 页 / 共 2 页
字号:
    uint32 row;    int format;    unsigned char *buffer;    int width;    int height;    unsigned char *currPtr;    TIFFSetErrorHandler(tiff_error);    TIFFSetWarningHandler(tiff_warn);    in = TIFFClientOpen("inputstream", "r", (thandle_t)&fin,            libtiffStreamReadProc, //Custom read function            libtiffStreamWriteProc, //Custom write function            libtiffStreamSeekProc, //Custom seek function            libtiffStreamCloseProc, //Custom close function            libtiffStreamSizeProc, //Custom size function            libtiffStreamMapProc, //Custom map function            libtiffStreamUnmapProc); //Custom unmap function    if (in == NULL)    {        tifferror = ERR_OPEN;        return NULL;    }    if (TIFFGetField(in, TIFFTAG_PHOTOMETRIC, &photometric) == 1)    {        if (photometric != PHOTOMETRIC_RGB && photometric != PHOTOMETRIC_PALETTE &&            photometric != PHOTOMETRIC_MINISWHITE &&            photometric != PHOTOMETRIC_MINISBLACK)        {            osg::notify(osg::NOTICE) << "Photometric type "<<photometric<<" not handled; can only handle Grayscale, RGB and Palette images" << std::endl;            TIFFClose(in);            tifferror = ERR_UNSUPPORTED;            return NULL;        }    }    else    {        tifferror = ERR_READ;        TIFFClose(in);        return NULL;    }    if (TIFFGetField(in, TIFFTAG_SAMPLESPERPIXEL, &samplesperpixel) == 1)    {        if (samplesperpixel != 1 &&            samplesperpixel != 2 &&            samplesperpixel != 3 &&            samplesperpixel != 4)        {            osg::notify(osg::DEBUG_INFO) << "Bad samples/pixel" << std::endl;            tifferror = ERR_UNSUPPORTED;            TIFFClose(in);            return NULL;        }    }    else    {        tifferror = ERR_READ;        TIFFClose(in);        return NULL;    }    if (TIFFGetField(in, TIFFTAG_BITSPERSAMPLE, &bitspersample) == 1)    {         if (bitspersample != 8 && bitspersample != 16 && bitspersample != 32)        {            osg::notify(osg::NOTICE) << "can only handle 8, 16 and 32 bit samples" << std::endl;            TIFFClose(in);            tifferror = ERR_UNSUPPORTED;            return NULL;        }    }    else    {        tifferror = ERR_READ;        TIFFClose(in);        return NULL;    }        if (TIFFGetField(in, TIFFTAG_IMAGEWIDTH, &w) != 1 ||        TIFFGetField(in, TIFFTAG_IMAGELENGTH, &h) != 1 ||        TIFFGetField(in, TIFFTAG_PLANARCONFIG, &config) != 1)    {        TIFFClose(in);        tifferror = ERR_READ;        return NULL;    }            TIFFGetField(in, TIFFTAG_DATATYPE, &dataType);    osg::notify(osg::INFO)<<"TIFFTAG_DATATYPE="<<dataType<<std::endl;    /*    if (photometric == PHOTOMETRIC_MINISWHITE ||        photometric == PHOTOMETRIC_MINISBLACK)        format = 1;    else        format = 3;    */    // if it has a palette, data returned is 3 byte rgb    // so set format to 3.    if (photometric == PHOTOMETRIC_PALETTE)        format = 3;     else        format = samplesperpixel * bitspersample / 8;            int bytespersample = bitspersample / 8;    int bytesperpixel = bytespersample * samplesperpixel;        osg::notify(osg::INFO)<<"format="<<format<<std::endl;    osg::notify(osg::INFO)<<"bytespersample="<<bytespersample<<std::endl;    osg::notify(osg::INFO)<<"bytesperpixel="<<bytesperpixel<<std::endl;        buffer = new unsigned char [w*h*format];    if (!buffer)    {        tifferror = ERR_MEM;        TIFFClose(in);        return NULL;    }    // initialize memory    for(unsigned char* ptr=buffer;ptr<buffer+w*h*format;++ptr) *ptr = 0;    width = w;    height = h;    currPtr = buffer + (h-1)*w*format;    tifferror = ERR_NO_ERROR;    switch (pack(photometric, config))    {        case pack(PHOTOMETRIC_MINISWHITE, PLANARCONFIG_CONTIG):        case pack(PHOTOMETRIC_MINISBLACK, PLANARCONFIG_CONTIG):        case pack(PHOTOMETRIC_MINISWHITE, PLANARCONFIG_SEPARATE):        case pack(PHOTOMETRIC_MINISBLACK, PLANARCONFIG_SEPARATE):            inbuf = new unsigned char [TIFFScanlineSize(in)];            for (row = 0; row < h; row++)            {                if (TIFFReadScanline(in, inbuf, row, 0) < 0)                {                    tifferror = ERR_READ;                    break;                }                invert_row(currPtr, inbuf, w, photometric == PHOTOMETRIC_MINISWHITE, bitspersample);                currPtr -= format*w;            }            break;        case pack(PHOTOMETRIC_PALETTE, PLANARCONFIG_CONTIG):        case pack(PHOTOMETRIC_PALETTE, PLANARCONFIG_SEPARATE):            if (TIFFGetField(in, TIFFTAG_COLORMAP, &red, &green, &blue) != 1)                tifferror = ERR_READ;            /* */            /* Convert 16-bit colormap to 8-bit (unless it looks */            /* like an old-style 8-bit colormap). */            /* */            if (!tifferror && checkcmap(1<<bitspersample, red, green, blue) == 16)            {                int i;                for (i = (1<<bitspersample)-1; i >= 0; i--)                {                    red[i] = CVT(red[i]);                    green[i] = CVT(green[i]);                    blue[i] = CVT(blue[i]);                }            }            inbuf = new unsigned char [TIFFScanlineSize(in)];            for (row = 0; row < h; row++)            {                if (TIFFReadScanline(in, inbuf, row, 0) < 0)                {                    tifferror = ERR_READ;                    break;                }                remap_row(currPtr, inbuf, w, red, green, blue);                currPtr -= format*w;            }            break;        case pack(PHOTOMETRIC_RGB, PLANARCONFIG_CONTIG):            inbuf = new unsigned char [TIFFScanlineSize(in)];            for (row = 0; row < h; row++)            {                if (TIFFReadScanline(in, inbuf, row, 0) < 0)                {                    tifferror = ERR_READ;                    break;                }                memcpy(currPtr, inbuf, format*w);                currPtr -= format*w;            }            break;        case pack(PHOTOMETRIC_RGB, PLANARCONFIG_SEPARATE):            rowsize = TIFFScanlineSize(in);            inbuf = new unsigned char [format*rowsize];            for (row = 0; !tifferror && row < h; row++)            {                int s;                for (s = 0; s < format; s++)                {                    if (TIFFReadScanline(in, (tdata_t)(inbuf+s*rowsize), (uint32)row, (tsample_t)s) < 0)                    {                        tifferror = ERR_READ; break;                    }                }                if (!tifferror)                {                    if (format==3) interleave_row(currPtr, inbuf, inbuf+rowsize, inbuf+2*rowsize, w, format, bitspersample);                    else if (format==4) interleave_row(currPtr, inbuf, inbuf+rowsize, inbuf+2*rowsize, inbuf+3*rowsize, w, format, bitspersample);                    currPtr -= format*w;                }            }            break;        default:            tifferror = ERR_UNSUPPORTED;            break;    }    if (inbuf) delete [] inbuf;    TIFFClose(in);    if (tifferror)    {        if (buffer) delete [] buffer;        return NULL;    }    width_ret = width;    height_ret = height;    if (photometric == PHOTOMETRIC_PALETTE)        numComponents_ret = format;    else        numComponents_ret = samplesperpixel;    return buffer;}#undef CVT#undef packclass ReaderWriterTIFF : public osgDB::ReaderWriter{    public:            ReaderWriterTIFF()        {            supportsExtension("tiff","Tiff image format");            supportsExtension("tif","Tiff image format");        }                virtual const char* className() const { return "TIFF Image Reader"; }        virtual bool acceptsExtension(const std::string& extension) const        {             if( osgDB::equalCaseInsensitive(extension,"tiff")) return true;            if( osgDB::equalCaseInsensitive(extension,"tif") ) return true;            return false;        }        ReadResult readTIFStream(std::istream& fin) const        {            unsigned char *imageData = NULL;            int width_ret = -1;            int height_ret = -1;            int numComponents_ret = -1;            uint16 bitspersample_ret = 0;            imageData = simage_tiff_load(fin, width_ret, height_ret, numComponents_ret, bitspersample_ret);            if (imageData==NULL)             {                char err_msg[256];                simage_tiff_error( err_msg, sizeof(err_msg));                 osg::notify(osg::WARN) << err_msg << std::endl;                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 =                 bitspersample_ret == 8 ? GL_UNSIGNED_BYTE :                 bitspersample_ret == 16 ? GL_UNSIGNED_SHORT :                bitspersample_ret == 32 ? GL_FLOAT : (GLenum)-1;            osg::Image* pOsgImage = new osg::Image;            pOsgImage->setImage(s,t,r,                internalFormat,                pixelFormat,                dataType,                imageData,                osg::Image::USE_NEW_DELETE);            return pOsgImage;        }        WriteResult::WriteStatus writeTIFStream(std::ostream& fout, const osg::Image& img) const        {            //Code is based from the following article on CodeProject.com            //http://www.codeproject.com/bitmap/BitmapsToTiffs.asp            TIFF *image;            int samplesPerPixel;            int bitsPerSample;            uint16 photometric;            image = TIFFClientOpen("outputstream", "w", (thandle_t)&fout,                                    libtiffOStreamReadProc, //Custom read function                                    libtiffOStreamWriteProc, //Custom write function                                    libtiffOStreamSeekProc, //Custom seek function                                    libtiffStreamCloseProc, //Custom close function                                    libtiffOStreamSizeProc, //Custom size function                                    libtiffStreamMapProc, //Custom map function                                    libtiffStreamUnmapProc); //Custom unmap function                        if(image == NULL)            {                return WriteResult::ERROR_IN_WRITING_FILE;            }            switch(img.getPixelFormat()) {                case GL_LUMINANCE:                case GL_ALPHA:                    photometric = PHOTOMETRIC_MINISBLACK;                    samplesPerPixel = 1;                    break;                case GL_LUMINANCE_ALPHA:                    photometric = PHOTOMETRIC_MINISBLACK;                    samplesPerPixel = 2;                    break;                case GL_RGB:                    photometric = PHOTOMETRIC_RGB;                    samplesPerPixel = 3;                    break;                case GL_RGBA:                    photometric = PHOTOMETRIC_RGB;                    samplesPerPixel = 4;                    break;                default:                    return WriteResult::ERROR_IN_WRITING_FILE;                    break;            }            switch(img.getDataType()){                case GL_FLOAT:                    TIFFSetField(image, TIFFTAG_SAMPLEFORMAT, SAMPLEFORMAT_IEEEFP);                    TIFFSetField(image, TIFFTAG_ROWSPERSTRIP, 1);                    bitsPerSample = 32;                    break;                default:                    bitsPerSample = 8;                    break;            }            TIFFSetField(image, TIFFTAG_IMAGEWIDTH,img.s());            TIFFSetField(image, TIFFTAG_IMAGELENGTH,img.t());            TIFFSetField(image, TIFFTAG_BITSPERSAMPLE,bitsPerSample);            TIFFSetField(image, TIFFTAG_SAMPLESPERPIXEL,samplesPerPixel);            TIFFSetField(image, TIFFTAG_PHOTOMETRIC, photometric);            TIFFSetField(image, TIFFTAG_COMPRESSION, COMPRESSION_PACKBITS);             TIFFSetField(image, TIFFTAG_FILLORDER, FILLORDER_MSB2LSB);            TIFFSetField(image, TIFFTAG_PLANARCONFIG, PLANARCONFIG_CONTIG);            //uint32 rowsperstrip = TIFFDefaultStripSize(image, -1);             //TIFFSetField(image, TIFFTAG_ROWSPERSTRIP, rowsperstrip);                        // Write the information to the file            for(int i = 0; i < img.t(); ++i) {                TIFFWriteScanline(image,(tdata_t)img.data(0,img.t()-i-1),i,0);            }            // Close the file            TIFFClose(image);            return WriteResult::FILE_SAVED;        }        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 readTIFStream(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 = readTIFStream(istream);            if(rr.validImage()) rr.getImage()->setFileName(file);            return rr;        }        virtual WriteResult writeImage(const osg::Image& img,std::ostream& fout,const osgDB::ReaderWriter::Options* /*options*/) const        {            WriteResult::WriteStatus ws = writeTIFStream(fout,img);            return ws;        }        virtual WriteResult writeImage(const osg::Image &img,const std::string& fileName, const osgDB::ReaderWriter::Options *options) const        {            std::string ext = osgDB::getFileExtension(fileName);            if (!acceptsExtension(ext)) return WriteResult::FILE_NOT_HANDLED;            std::ofstream fout(fileName.c_str(), std::ios::out | std::ios::binary);            if(!fout) return WriteResult::ERROR_IN_WRITING_FILE;            return writeImage(img,fout,options);        }};// now register with Registry to instantiate the above// reader/writer.REGISTER_OSGPLUGIN(tiff, ReaderWriterTIFF)

⌨️ 快捷键说明

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