📄 qtimportexport.cpp
字号:
// Grab the SAFE_NEW version of the data ref from the data handler /*err = */ DataHGetDataRef(dataRefHandler, &dataRef); CloseComponent(dataRefHandler); return dataRef;}osg::Image* QuicktimeImportExport::doImport(unsigned char* data, unsigned int sizeData, const std::string& fileTypeHint){ GWorldPtr gworld = 0; OSType pixelFormat; int rowStride; GraphicsImportComponent gicomp = 0; Rect rectImage; GDHandle origDevice = 0; CGrafPtr origPort = 0; ImageDescriptionHandle desc = 0; int depth = 32; unsigned int xsize, ysize; unsigned char* imageData = 0; // Data Handle for file data ( & load data from file ) Handle dataRef = getPtrDataRef(data, sizeData, fileTypeHint); try { OSErr err = noErr; // GraphicsImporter - Get Importer for our filetype GetGraphicsImporterForDataRef(dataRef, 'ptr ', &gicomp); // GWorld - Get Texture Info err = GraphicsImportGetNaturalBounds(gicomp, &rectImage); if (err != noErr) { throw QTImportExportException(err, "GraphicsImportGetNaturalBounds failed"); } xsize = (unsigned int)(rectImage.right - rectImage.left); ysize = (unsigned int)(rectImage.bottom - rectImage.top); // ImageDescription - Get Image Description err = GraphicsImportGetImageDescription(gicomp, &desc); if (err != noErr) { throw QTImportExportException(err, "GraphicsImportGetImageDescription failed"); } // ImageDescription - Get Bit Depth HLock(reinterpret_cast<char **>(desc)); // GWorld - Pixel Format stuff pixelFormat = k32ARGBPixelFormat; // Make sure its forced...NOTE: i'm pretty sure this cannot be RGBA! // GWorld - Row stride rowStride = xsize * 4; // (width * depth_bpp / 8) // GWorld - Allocate output buffer imageData = new unsigned char[rowStride * ysize]; // GWorld - Actually Create IT! QTNewGWorldFromPtr(&gworld, pixelFormat, &rectImage, 0, 0, 0, imageData, rowStride); if (!gworld) { throw QTImportExportException(-1, "QTNewGWorldFromPtr failed"); } // Save old Graphics Device and Graphics Port to reset to later GetGWorld (&origPort, &origDevice); // GraphicsImporter - Set Destination GWorld (our buffer) err = GraphicsImportSetGWorld(gicomp, gworld, 0); if (err != noErr) { throw QTImportExportException(err, "GraphicsImportSetGWorld failed"); } // GraphicsImporter - Set Quality Level err = GraphicsImportSetQuality(gicomp, codecLosslessQuality); if (err != noErr) { throw QTImportExportException(err, "GraphicsImportSetQuality failed"); } // Lock pixels so that we can draw to our memory texture if (!GetGWorldPixMap(gworld) || !LockPixels(GetGWorldPixMap(gworld))) { throw QTImportExportException(0, "GetGWorldPixMap failed"); } //*** Draw GWorld into our Memory Texture! GraphicsImportDraw(gicomp); // Clean up UnlockPixels(GetGWorldPixMap(gworld)); SetGWorld(origPort, origDevice); // set graphics port to offscreen (we don't need it now) DisposeGWorld(gworld); CloseComponent(gicomp); DisposeHandle(reinterpret_cast<char **>(desc)); DisposeHandle(dataRef); } catch (QTImportExportException& e) { setError(e.what()); if (gworld) { UnlockPixels(GetGWorldPixMap(gworld)); SetGWorld(origPort, origDevice); // set graphics port to offscreen (we don't need it now) DisposeGWorld(gworld); } if (gicomp) CloseComponent(gicomp); if (desc) DisposeHandle(reinterpret_cast<char **>(desc)); if (imageData) delete[] imageData; if (dataRef) DisposeHandle(dataRef); return NULL; } unsigned int bytesPerPixel = depth / 8; unsigned int glpixelFormat; switch(bytesPerPixel) { case 3 : glpixelFormat = GL_RGB; break; case 4 : glpixelFormat = GL_RGBA; break; default : delete[] imageData; setError("unknown pixelformat"); return NULL; break; } unsigned char* swizzled = pepareBufferForOSG(imageData, bytesPerPixel, xsize, ysize); delete[] imageData; osg::Image* image = new osg::Image(); image->setFileName(fileTypeHint.c_str()); image->setImage(xsize,ysize,1, bytesPerPixel, glpixelFormat, GL_UNSIGNED_BYTE, swizzled, osg::Image::USE_NEW_DELETE ); return image;} void QuicktimeImportExport::writeToStream(std::ostream& outStream, osg::Image* image, const std::string& fileTypeHint) { std::string ext = osgDB::getFileExtension(fileTypeHint); //Build map of extension <-> osFileTypes static std::map<std::string, OSType> extmap; if (extmap.size() == 0) { extmap["jpg"] = kQTFileTypeJPEG; extmap["jpeg"] = kQTFileTypeJPEG; extmap["bmp"] = kQTFileTypeBMP; extmap["tif"] = kQTFileTypeTIFF; extmap["tiff"] = kQTFileTypeTIFF; extmap["png"] = kQTFileTypePNG; extmap["gif"] = kQTFileTypeGIF; extmap["psd"] = kQTFileTypePhotoShop; extmap["sgi"] = kQTFileTypeSGIImage; extmap["rgb"] = kQTFileTypeSGIImage; extmap["rgba"] = kQTFileTypeSGIImage; } std::map<std::string, OSType>::iterator cur = extmap.find(ext); // can not handle this type of file, perhaps a movie? if (cur == extmap.end()) return; unsigned int numBytes = image->computeNumComponents(image->getPixelFormat()); unsigned char* pixels = prepareBufferForQuicktime( image->data(), image->getPixelFormat(), numBytes, image->s(), image->t() ); OSType desiredType = cur->second; GraphicsExportComponent geComp = NULL; GWorldPtr gw = 0; Handle dataHandle; dataHandle = NewHandle(0); try { OSErr err = OpenADefaultComponent(GraphicsExporterComponentType, desiredType, &geComp); Rect bounds = {0,0, image->t(), image->s()}; err = QTNewGWorldFromPtr(&gw, k32ARGBPixelFormat, &bounds, 0,0,0, pixels, image->s()*4); if (err != noErr) { throw QTImportExportException(err, "could not create gworld for type " + ext); } err = GraphicsExportSetInputGWorld(geComp, gw); if (err != noErr) { throw QTImportExportException(err, "could not set input gworld for type " + ext); } err = GraphicsExportSetOutputHandle( geComp, dataHandle); if (err != noErr) { throw QTImportExportException(err, "could not set output file for type " + ext); } // Set the compression quality (needed for JPEG, not necessarily for other formats) if (desiredType == kQTFileTypeJPEG) { err = GraphicsExportSetCompressionQuality(geComp, codecLosslessQuality); if (err != noErr) { throw QTImportExportException(err, "could not set compression for type " + ext); } } if(4 == numBytes) { err = GraphicsExportSetDepth( geComp, k32ARGBPixelFormat ); // depth } // else k24RGBPixelFormat??? // do the export err = GraphicsExportDoExport(geComp, NULL); if (err != noErr) { throw QTImportExportException(err, "could not do the export for type " + ext); } if (geComp != NULL) CloseComponent(geComp); if (gw) DisposeGWorld (gw); if (pixels) free(pixels); outStream.write(*dataHandle, GetHandleSize(dataHandle)); DisposeHandle(dataHandle); } catch (QTImportExportException& e) { setError(e.what()); if (geComp != NULL) CloseComponent(geComp); if (gw != NULL) DisposeGWorld (gw); if (pixels) free(pixels); DisposeHandle(dataHandle); }}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -