📄 readerwriterdds.cpp
字号:
// Only do the check on the first mipmap level unsigned int numBlocks = mipmaps.size()>0 ? mipmaps[0] / 8 : size / 8; for (int i=numBlocks; i>0; --i, ++texelsBlock) { if (texelsBlock->color_0<=texelsBlock->color_1) { // Texture is using the 1-bit alpha encoding, so we need to update the assumed pixel format internalFormat = GL_COMPRESSED_RGBA_S3TC_DXT1_EXT; pixelFormat = GL_COMPRESSED_RGBA_S3TC_DXT1_EXT; break; } } } osgImage->setImage(s,t,r, internalFormat, pixelFormat, dataType, imageData, osg::Image::USE_NEW_DELETE); if (mipmaps.size()>0) osgImage->setMipmapLevels(mipmaps); // Return Image. return osgImage.release();}/*osg::Image::MipmapDataType mipmaps;osgImage->setMipmapData(mipmaps);osgImage->setImage(s,t,r, internalFormat, pixelFormat, dataType, 0, osg::Image::USE_NEW_DELETE);printf("INVENTO===> gtsibim:%d grsib:%d mi_size:%d lPitch%d\n", osgImage->getTotalSizeInBytesIncludingMipmaps(), osgImage->getRowSizeInBytes(), size, ddsd.lPitch);printf("CORRECTO**> gtsibim:%d grsib:%d mi_size:%d lPitch%d\n", osgImage->getTotalSizeInBytesIncludingMipmaps(), osgImage->getRowSizeInBytes(), size, ddsd.lPitch); */bool WriteDDSFile(const osg::Image *img, std::ostream& fout){ // Initialize ddsd structure and its members DDSURFACEDESC2 ddsd; DDPIXELFORMAT ddpf; //DDCOLORKEY ddckCKDestOverlay; //DDCOLORKEY ddckCKDestBlt; //DDCOLORKEY ddckCKSrcOverlay; //DDCOLORKEY ddckCKSrcBlt; DDSCAPS2 ddsCaps; ddsd.dwSize = sizeof(ddsd); ddpf.dwSize = sizeof(ddpf); // Default values and initialization of structures' flags unsigned int SD_flags = DDSD_CAPS | DDSD_HEIGHT | DDSD_WIDTH | DDSD_PIXELFORMAT; unsigned int CAPS_flags = DDSCAPS_TEXTURE; unsigned int PF_flags = 0; unsigned int CAPS2_flags = 0; // Get image properties unsigned int dataType = img->getDataType(); unsigned int pixelFormat = img->getPixelFormat(); //unsigned int internalFormat = img->getInternalTextureFormat(); //unsigned int components = osg::Image::computeNumComponents(pixelFormat); unsigned int pixelSize = osg::Image::computePixelSizeInBits(pixelFormat, dataType); unsigned int imageSize = img->getImageSizeInBytes(); bool is3dImage = false; ddsd.dwWidth = img->s(); ddsd.dwHeight = img->t(); int r = img->r(); if(r > 1) /* check for 3d image */ { is3dImage = true; ddsd.dwDepth = r; SD_flags |= DDSD_DEPTH; CAPS_flags |= DDSCAPS_COMPLEX; CAPS2_flags |= DDSCAPS2_VOLUME; } // Determine format - set flags and ddsd, ddpf properties switch (pixelFormat) { //Uncompressed case GL_RGBA: { ddpf.dwRBitMask = 0x000000ff; ddpf.dwGBitMask = 0x0000ff00; ddpf.dwBBitMask = 0x00ff0000; ddpf.dwRGBAlphaBitMask = 0xff000000; PF_flags |= (DDPF_ALPHAPIXELS | DDPF_RGB); ddpf.dwRGBBitCount = pixelSize; ddsd.lPitch = img->getRowSizeInBytes(); SD_flags |= DDSD_PITCH; } break; case GL_BGRA: { ddpf.dwBBitMask = 0x000000ff; ddpf.dwGBitMask = 0x0000ff00; ddpf.dwRBitMask = 0x00ff0000; ddpf.dwRGBAlphaBitMask = 0xff000000; PF_flags |= (DDPF_ALPHAPIXELS | DDPF_RGB); ddpf.dwRGBBitCount = pixelSize; ddsd.lPitch = img->getRowSizeInBytes(); SD_flags |= DDSD_PITCH; } break; case GL_LUMINANCE_ALPHA: { ddpf.dwRBitMask = 0x00ff0000; ddpf.dwRGBAlphaBitMask = 0x000000ff; PF_flags |= (DDPF_ALPHAPIXELS | DDPF_LUMINANCE); ddpf.dwRGBBitCount = pixelSize; ddsd.lPitch = img->getRowSizeInBytes(); SD_flags |= DDSD_PITCH; } break; case GL_RGB: { ddpf.dwRBitMask = 0x000000ff; ddpf.dwGBitMask = 0x0000ff00; ddpf.dwBBitMask = 0x00ff0000; PF_flags |= DDPF_RGB; ddpf.dwRGBBitCount = pixelSize; ddsd.lPitch = img->getRowSizeInBytes(); SD_flags |= DDSD_PITCH; } break; case GL_LUMINANCE: { ddpf.dwRBitMask = 0x00ff0000; PF_flags |= DDPF_LUMINANCE; ddpf.dwRGBBitCount = pixelSize; ddsd.lPitch = img->getRowSizeInBytes(); SD_flags |= DDSD_PITCH; } break; case GL_ALPHA: { ddpf.dwRGBAlphaBitMask = 0x000000ff; PF_flags |= DDPF_ALPHA; ddpf.dwRGBBitCount = pixelSize; ddsd.lPitch = img->getRowSizeInBytes(); SD_flags |= DDSD_PITCH; } break; //Compressed case GL_COMPRESSED_RGBA_S3TC_DXT1_EXT: { ddpf.dwFourCC = FOURCC_DXT1; PF_flags |= (DDPF_ALPHAPIXELS | DDPF_FOURCC); ddsd.dwLinearSize = imageSize; SD_flags |= DDSD_LINEARSIZE; } break; case GL_COMPRESSED_RGBA_S3TC_DXT3_EXT: { ddpf.dwFourCC = FOURCC_DXT3; PF_flags |= (DDPF_ALPHAPIXELS | DDPF_FOURCC); ddsd.dwLinearSize = imageSize; SD_flags |= DDSD_LINEARSIZE; } break; case GL_COMPRESSED_RGBA_S3TC_DXT5_EXT: { ddpf.dwFourCC = FOURCC_DXT5; PF_flags |= (DDPF_ALPHAPIXELS | DDPF_FOURCC); ddsd.dwLinearSize = imageSize; SD_flags |= DDSD_LINEARSIZE; } break; case GL_COMPRESSED_RGB_S3TC_DXT1_EXT: { ddpf.dwFourCC = FOURCC_DXT1; PF_flags |= DDPF_FOURCC; /* No alpha here */ ddsd.dwLinearSize = imageSize; SD_flags |= DDSD_LINEARSIZE; } break; default: osg::notify(osg::WARN)<<"Warning:: unhandled pixel format in image, file cannot be written."<<std::endl; return false; } // set even more flags if(img->isMipmap() && !is3dImage) { SD_flags |= DDSD_MIPMAPCOUNT; CAPS_flags |= DDSCAPS_COMPLEX | DDSCAPS_MIPMAP; ddsd.dwMipMapCount = img->getNumMipmapLevels(); osg::notify(osg::NOTICE)<<"writing out with mipmaps ddsd.dwMipMapCount"<<ddsd.dwMipMapCount<<std::endl; } else { osg::notify(osg::NOTICE)<<"no mipmaps to write out."<<std::endl; } // Assign flags and structure members of ddsd ddsd.dwFlags = SD_flags; ddpf.dwFlags = PF_flags; ddsCaps.dwCaps = CAPS_flags; ddsCaps.dwCaps2 = CAPS2_flags; ddsd.ddpfPixelFormat = ddpf; ddsd.ddsCaps = ddsCaps; // Write DDS file fout.write("DDS ", 4); /* write FOURCC */ fout.write(reinterpret_cast<char*>(&ddsd), sizeof(ddsd)); /* write file header */ // int isize = img->getTotalSizeInBytesIncludingMipmaps(); if(!is3dImage) { fout.write(reinterpret_cast<const char*>(img->data()), img->getTotalSizeInBytesIncludingMipmaps()); } else /* 3d image */ { for(int i = 0; i < r; ++i) { fout.write(reinterpret_cast<const char*>(img->data(0, 0, i)), imageSize); } } // Check for correct saving if (fout.fail()) { return false; } // If we get that far the file was saved properly // return true; }class ReaderWriterDDS : public osgDB::ReaderWriter{public: ReaderWriterDDS() { supportsExtension("dds","DDS image format"); } virtual const char* className() const { return "DDS Image Reader/Writer"; } virtual ReadResult readObject(const std::string& file, const osgDB::ReaderWriter::Options* options) const { return readImage(file,options); } virtual ReadResult readObject(std::istream& fin, const Options* options) const { return readImage(fin,options); } 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; osgDB::ifstream stream(fileName.c_str(), std::ios::in | std::ios::binary); if(!stream) return ReadResult::FILE_NOT_HANDLED; ReadResult rr = readImage(stream, options); if(rr.validImage()) rr.getImage()->setFileName(file); return rr; } virtual ReadResult readImage(std::istream& fin, const Options* options) const { osg::Image* osgImage = ReadDDSFile(fin); if (osgImage==NULL) return ReadResult::FILE_NOT_HANDLED; if (options && options->getOptionString().find("dds_flip")!=std::string::npos) { osgImage->flipVertical(); } return osgImage; } virtual WriteResult writeObject(const osg::Object& object,const std::string& file, const osgDB::ReaderWriter::Options* options) const { const osg::Image* image = dynamic_cast<const osg::Image*>(&object); if (!image) return WriteResult::FILE_NOT_HANDLED; return writeImage(*image,file,options); } virtual WriteResult writeObject(const osg::Object& object,std::ostream& fout,const Options* options) const { const osg::Image* image = dynamic_cast<const osg::Image*>(&object); if (!image) return WriteResult::FILE_NOT_HANDLED; return writeImage(*image,fout,options); } virtual WriteResult writeImage(const osg::Image &image,const std::string& file, const osgDB::ReaderWriter::Options* options) const { std::string ext = osgDB::getFileExtension(file); if (!acceptsExtension(ext)) return WriteResult::FILE_NOT_HANDLED; osgDB::ofstream fout(file.c_str(), std::ios::out | std::ios::binary); if(!fout) return WriteResult::ERROR_IN_WRITING_FILE; return writeImage(image,fout,options); } virtual WriteResult writeImage(const osg::Image& image,std::ostream& fout,const Options*) const { bool success = WriteDDSFile(&image, fout); if(success) return WriteResult::FILE_SAVED; else return WriteResult::ERROR_IN_WRITING_FILE; }};// now register with Registry to instantiate the above// reader/writer.REGISTER_OSGPLUGIN(dds, ReaderWriterDDS)
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -