osg::Image* QgsOsgEarthTileSource::createImage( const TileKey& key, ProgressCallback* progress ) { Q_UNUSED( key ); Q_UNUSED( progress ); osg::ref_ptr<osg::Image> image; if ( intersects( &key ) ) { //Get the extents of the tile double xmin, ymin, xmax, ymax; key.getExtent().getBounds( xmin, ymin, xmax, ymax ); int tileSize = getPixelsPerTile(); int target_width = tileSize; int target_height = tileSize; QgsDebugMsg( "QGIS: xmin:" + QString::number( xmin ) + " ymin:" + QString::number( ymin ) + " ymax:" + QString::number( ymax ) + " ymax " + QString::number( ymax ) ); //Return if parameters are out of range. if ( target_width <= 0 || target_height <= 0 ) { return 0; } QImage* qImage = createImage( target_width, target_height ); if ( !qImage ) { return 0; } QgsMapRenderer* mainRenderer = mQGisIface->mapCanvas()->mapRenderer(); mMapRenderer->setLayerSet( mainRenderer->layerSet() ); mMapRenderer->setOutputSize( QSize( qImage->width(), qImage->height() ), qImage->logicalDpiX() ); QgsRectangle mapExtent( xmin, ymin, xmax, ymax ); mMapRenderer->setExtent( mapExtent ); QPainter thePainter( qImage ); //thePainter.setRenderHint(QPainter::Antialiasing); //make it look nicer mMapRenderer->render( &thePainter ); unsigned char* data = qImage->bits(); image = new osg::Image; //The pixel format is always RGBA to support transparency image->setImage( qImage->width(), qImage->height(), 1, 4, GL_BGRA, GL_UNSIGNED_BYTE, //Why not GL_RGBA - QGIS bug? data, osg::Image::NO_DELETE, 1 ); image->flipVertical(); } //Create a transparent image if we don't have an image if ( !image.valid() ) { return ImageUtils::createEmptyImage(); } return image.release(); }
osg::Image* QgsOsgEarthTileSource::createImage( const TileKey& key, ProgressCallback* progress ) { QString kname = key.str().c_str(); kname.replace( '/', '_' ); Q_UNUSED( progress ); //Get the extents of the tile int tileSize = getPixelsPerTile(); if ( tileSize <= 0 ) { QgsDebugMsg( "Tile size too small." ); return ImageUtils::createEmptyImage(); } QgsRectangle viewExtent = mQGisIface->mapCanvas()->fullExtent(); if ( mCoordTransform ) { QgsDebugMsg( QString( "vext0:%1" ).arg( viewExtent.toString( 5 ) ) ); viewExtent = mCoordTransform->transformBoundingBox( viewExtent ); } QgsDebugMsg( QString( "vext1:%1" ).arg( viewExtent.toString( 5 ) ) ); double xmin, ymin, xmax, ymax; key.getExtent().getBounds( xmin, ymin, xmax, ymax ); QgsRectangle tileExtent( xmin, ymin, xmax, ymax ); QgsDebugMsg( QString( "text0:%1" ).arg( tileExtent.toString( 5 ) ) ); if ( !viewExtent.intersects( tileExtent ) ) { QgsDebugMsg( QString( "earth tile key:%1 ext:%2: NO INTERSECT" ).arg( kname ).arg( tileExtent.toString( 5 ) ) ); return ImageUtils::createEmptyImage(); } #ifdef USE_RENDERER QImage *qImage = createQImage( tileSize, tileSize ); if ( !qImage ) { QgsDebugMsg( QString( "earth tile key:%1 ext:%2: EMPTY IMAGE" ).arg( kname ).arg( tileExtent.toString( 5 ) ) ); return ImageUtils::createEmptyImage(); } mMapRenderer->setLayerSet( mQGisIface->mapCanvas()->mapRenderer()->layerSet() ); mMapRenderer->setOutputSize( QSize( tileSize, tileSize ), qImage->logicalDpiX() ); mMapRenderer->setExtent( tileExtent ); QPainter thePainter( qImage ); mMapRenderer->render( &thePainter ); #else mMapSettings.setLayers( mQGisIface->mapCanvas()->mapSettings().layers() ); mMapSettings.setOutputSize( QSize( tileSize, tileSize ) ); mMapSettings.setOutputDpi( QgsApplication::desktop()->logicalDpiX() ); mMapSettings.setExtent( tileExtent ); mMapSettings.setBackgroundColor( QColor( 0, 0, 0, 0 ) ); QgsMapRendererSequentialJob job( mMapSettings ); job.start(); job.waitForFinished(); QImage *qImage = new QImage( job.renderedImage() ); if ( !qImage ) { QgsDebugMsg( QString( "earth tile key:%1 ext:%2: EMPTY IMAGE" ).arg( kname ).arg( tileExtent.toString( 5 ) ) ); return ImageUtils::createEmptyImage(); } Q_ASSERT( qImage->logicalDpiX() == QgsApplication::desktop()->logicalDpiX() ); Q_ASSERT( qImage->format() == QImage::Format_ARGB32_Premultiplied ); #endif QgsDebugMsg( QString( "earth tile key:%1 ext:%2" ).arg( kname ).arg( tileExtent.toString( 5 ) ) ); #if 0 qImage->save( QString( "/tmp/tile-%1.png" ).arg( kname ) ); #endif osg::ref_ptr<osg::Image> image = new osg::Image; //The pixel format is always RGBA to support transparency image->setImage( tileSize, tileSize, 1, 4, // width, height, depth, pixelFormat? GL_BGRA, GL_UNSIGNED_BYTE, //Why not GL_RGBA - Qt bug? qImage->bits(), osg::Image::NO_DELETE, 1 ); image->flipVertical(); //Create a transparent image if we don't have an image if ( !image.valid() ) { QgsDebugMsg( "image is invalid" ); return ImageUtils::createEmptyImage(); } QgsDebugMsg( "returning image" ); return image.release(); }