Beispiel #1
0
QList<QByteArray> QImageReader::supportedMimeTypes()
{
    QSet<QByteArray> mimeTypes;
    for (int i = 0; i < _qt_NumFormats; ++i)
        mimeTypes << _qt_BuiltInFormats[i].mimeType;

#ifndef QT_NO_IMAGEFORMATPLUGIN
    supportedImageHandlerMimeTypes(loader(), QImageIOPlugin::CanRead, &mimeTypes);
#endif // QT_NO_IMAGEFORMATPLUGIN

    QList<QByteArray> sortedMimeTypes;
    for (QSet<QByteArray>::ConstIterator it = mimeTypes.constBegin(); it != mimeTypes.constEnd(); ++it)
        sortedMimeTypes << *it;

    qSort(sortedMimeTypes);
    return sortedMimeTypes;
}
Beispiel #2
0
QList<QByteArray> QImageReader::supportedImageFormats()
{
    QSet<QByteArray> formats;
    for (int i = 0; i < _qt_NumFormats; ++i)
        formats << _qt_BuiltInFormats[i].extension;

#ifndef QT_NO_IMAGEFORMATPLUGIN
    supportedImageHandlerFormats(loader(), QImageIOPlugin::CanRead, &formats);
#endif // QT_NO_IMAGEFORMATPLUGIN

    QList<QByteArray> sortedFormats;
    for (QSet<QByteArray>::ConstIterator it = formats.constBegin(); it != formats.constEnd(); ++it)
        sortedFormats << *it;

    qSort(sortedFormats);
    return sortedFormats;
}
Beispiel #3
0
/*!
    Returns the list of image formats supported by QImageWriter.

    By default, Qt can write the following formats:

    \table
    \header \o Format \o Description
    \row    \o BMP    \o Windows Bitmap
    \row    \o JPG    \o Joint Photographic Experts Group
    \row    \o JPEG   \o Joint Photographic Experts Group
    \row    \o PNG    \o Portable Network Graphics
    \row    \o PPM    \o Portable Pixmap
    \row    \o TIFF   \o Tagged Image File Format
    \row    \o XBM    \o X11 Bitmap
    \row    \o XPM    \o X11 Pixmap
    \endtable

    Reading and writing SVG files is supported through Qt's
    \l{QtSvg Module}{SVG Module}.

    Note that the QApplication instance must be created before this function is
    called.

    \sa setFormat(), QImageReader::supportedImageFormats(), QImageIOPlugin
*/
QList<QByteArray> QImageWriter::supportedImageFormats()
{
    QSet<QByteArray> formats;
    formats << "bmp";
#ifndef QT_NO_IMAGEFORMAT_PPM
    formats << "ppm";
#endif
#ifndef QT_NO_IMAGEFORMAT_XBM
    formats << "xbm";
#endif
#ifndef QT_NO_IMAGEFORMAT_XPM
    formats << "xpm";
#endif
#ifndef QT_NO_IMAGEFORMAT_PNG
    formats << "png";
#endif
#ifndef QT_NO_IMAGEFORMAT_JPEG
    formats << "jpg" << "jpeg";
#endif
#ifndef QT_NO_IMAGEFORMAT_MNG
    formats << "mng";
#endif
#ifndef QT_NO_IMAGEFORMAT_TIFF
    formats << "tif" << "tiff";
#endif
#ifdef QT_BUILTIN_GIF_READER
    formats << "gif";
#endif

#ifndef QT_NO_LIBRARY
    QFactoryLoader *l = loader();
    QStringList keys = l->keys();
    for (int i = 0; i < keys.count(); ++i) {
        QImageIOPlugin *plugin = qobject_cast<QImageIOPlugin *>(l->instance(keys.at(i)));
        if (plugin && (plugin->capabilities(0, keys.at(i).toLatin1()) & QImageIOPlugin::CanWrite) != 0)
            formats << keys.at(i).toLatin1();
    }
#endif // QT_NO_LIBRARY

    QList<QByteArray> sortedFormats;
    for (QSet<QByteArray>::ConstIterator it = formats.constBegin(); it != formats.constEnd(); ++it)
        sortedFormats << *it;

    qSort(sortedFormats);
    return sortedFormats;
}
void QgsComposerAttributeTableV2::setDisplayAttributes( const QSet<int>& attr, bool refresh )
{
  QgsVectorLayer* source = sourceLayer();
  if ( !source )
  {
    return;
  }

  //rebuild columns list, taking only attributes with index in supplied QSet
  qDeleteAll( mColumns );
  mColumns.clear();

  const QgsFields& fields = source->fields();

  if ( !attr.empty() )
  {
    QSet<int>::const_iterator attIt = attr.constBegin();
    for ( ; attIt != attr.constEnd(); ++attIt )
    {
      int attrIdx = ( *attIt );
      if ( !fields.exists( attrIdx ) )
      {
        continue;
      }
      QString currentAlias = source->attributeDisplayName( attrIdx );
      QgsComposerTableColumn* col = new QgsComposerTableColumn;
      col->setAttribute( fields.at( attrIdx ).name() );
      col->setHeading( currentAlias );
      mColumns.append( col );
    }
  }
  else
  {
    //resetting, so add all attributes to columns
    int idx = 0;
    Q_FOREACH ( const QgsField& field, fields )
    {
      QString currentAlias = source->attributeDisplayName( idx );
      QgsComposerTableColumn* col = new QgsComposerTableColumn;
      col->setAttribute( field.name() );
      col->setHeading( currentAlias );
      mColumns.append( col );
      idx++;
    }
  }
static QList<QNetworkInterfacePrivate *> interfaceListing()
{
    QList<QNetworkInterfacePrivate *> interfaces;

    int socket;
    if ((socket = qt_safe_socket(AF_INET, SOCK_STREAM, IPPROTO_IP)) == -1)
        return interfaces;      // error

    QSet<QByteArray> names = interfaceNames(socket);
    QSet<QByteArray>::ConstIterator it = names.constBegin();
    for ( ; it != names.constEnd(); ++it) {
        ifreq req;
        memset(&req, 0, sizeof(ifreq));
        memcpy(req.ifr_name, *it, qMin<int>(it->length() + 1, sizeof(req.ifr_name) - 1));

        QNetworkInterfacePrivate *iface = findInterface(socket, interfaces, req);

        // Get the interface broadcast address
        QNetworkAddressEntry entry;
        if (iface->flags & QNetworkInterface::CanBroadcast) {
            if (qt_safe_ioctl(socket, SIOCGIFBRDADDR, &req) >= 0) {
                sockaddr *sa = &req.ifr_addr;
                if (sa->sa_family == AF_INET)
                    entry.setBroadcast(addressFromSockaddr(sa));
            }
        }

        // Get the interface netmask
        if (qt_safe_ioctl(socket, SIOCGIFNETMASK, &req) >= 0) {
            sockaddr *sa = &req.ifr_addr;
	    entry.setNetmask(addressFromSockaddr(sa));
        }

        // Get the address of the interface
        if (qt_safe_ioctl(socket, SIOCGIFADDR, &req) >= 0) {
            sockaddr *sa = &req.ifr_addr;
            entry.setIp(addressFromSockaddr(sa));
        }

        iface->addressEntries << entry;
    }

    ::close(socket);
    return interfaces;
}
void QGeoTileFetcher::cancelTileRequests(const QSet<QGeoTileSpec> &tiles)
{
    Q_D(QGeoTileFetcher);

    typedef QSet<QGeoTileSpec>::const_iterator tile_iter;
    tile_iter tile = tiles.constBegin();
    tile_iter end = tiles.constEnd();
    for (; tile != end; ++tile) {
        QGeoTiledMapReply *reply = d->invmap_.value(*tile, 0);
        if (reply) {
            d->invmap_.remove(*tile);
            reply->abort();
            if (reply->isFinished())
                reply->deleteLater();
        }
        d->queue_.removeAll(*tile);
    }
}
CommandTransform::CommandTransform(const QSet<int> &selection, ldraw::model *model, Editor::RotationPivot pivot)
	: CommandBase(selection, model)
{
	setText(i18n("Transform"));

	pivot_ = pivot;

	bool center = false;
	if (pivot_ == Editor::PivotCenter)
		center = true;

	CommandSelectionFilter csf(this);
	pivotpoint_ = PivotExtension::queryPivot(model_, center, &csf);

	for (QSet<int>::ConstIterator it = selection.constBegin(); it != selection.constEnd(); ++it) {
		if (model->elements()[*it]->get_type() == ldraw::type_ref)
			oldmatrices_[*it] = CAST_AS_CONST_REF(model->elements()[*it])->get_matrix();
	}
}
void QgsComposerManager::initialize()
{
  QSettings settings;
  QSet<QgsComposer*> composers = QgisApp::instance()->printComposers();
  QSet<QgsComposer*>::const_iterator it = composers.constBegin();
  for ( ; it != composers.constEnd(); ++it )
  {
    QListWidgetItem* item = new QListWidgetItem(( *it )->title(), mComposerListWidget );
    item->setFlags( Qt::ItemIsEnabled | Qt::ItemIsSelectable | Qt::ItemIsEditable );
    mItemComposerMap.insert( item, *it );
  }
  mComposerListWidget->sortItems();

  mTemplate->addItem( tr( "Empty composer" ) );
  mTemplate->addItem( tr( "Specific" ) );

  mUserTemplatesDir = QgsApplication::qgisSettingsDirPath() + "/composer_templates";
  QMap<QString, QString> userTemplateMap = defaultTemplates( true );
  if ( userTemplateMap.size() > 0 )
  {
    mTemplate->insertSeparator( mTemplate->count() );
    QMap<QString, QString>::const_iterator templateIt = userTemplateMap.constBegin();
    for ( ; templateIt != userTemplateMap.constEnd(); ++templateIt )
    {
      mTemplate->addItem( templateIt.key(), templateIt.value() );
    }
  }

  mDefaultTemplatesDir = QgsApplication::pkgDataPath() + "/composer_templates";
  QMap<QString, QString> defaultTemplateMap = defaultTemplates( false );
  if ( defaultTemplateMap.size() > 0 )
  {
    mTemplate->insertSeparator( mTemplate->count() );
    QMap<QString, QString>::const_iterator templateIt = defaultTemplateMap.constBegin();
    for ( ; templateIt != defaultTemplateMap.constEnd(); ++templateIt )
    {
      mTemplate->addItem( templateIt.key(), templateIt.value() );
    }
  }

  mTemplatePathLineEdit->setText( settings.value( "/UI/ComposerManager/templatePath", QString( "" ) ).toString() );
}
void QSGSharedDistanceFieldGlyphCache::releaseGlyphs(const QSet<glyph_t> &glyphs)
{
#if defined(QSGSHAREDDISTANCEFIELDGLYPHCACHE_DEBUG)
    qDebug("QSGSharedDistanceFieldGlyphCache::releaseGlyphs() called for %s (%d glyphs)",
           m_cacheId.constData(), glyphs.size());
#endif

    m_requestedGlyphs.subtract(glyphs);

    QVector<quint32> glyphsVector;
    glyphsVector.reserve(glyphs.size());

    QSet<glyph_t>::const_iterator glyphsIt;
    for (glyphsIt = glyphs.constBegin(); glyphsIt != glyphs.constEnd(); ++glyphsIt) {
        QHash<glyph_t, void *>::iterator bufferIt = m_bufferForGlyph.find(*glyphsIt);
        if (bufferIt != m_bufferForGlyph.end()) {
            void *buffer = bufferIt.value();
            removeGlyph(*glyphsIt);
            m_bufferForGlyph.erase(bufferIt);
            Q_ASSERT(!m_bufferForGlyph.contains(*glyphsIt));

            if (!m_sharedGraphicsCache->dereferenceBuffer(buffer)) {
#if !defined(QT_NO_DEBUG)
                bufferIt = m_bufferForGlyph.begin();
                while (bufferIt != m_bufferForGlyph.end()) {
                    Q_ASSERT(bufferIt.value() != buffer);
                    ++bufferIt;
                }
#endif
            }
        }

        glyphsVector.append(*glyphsIt);
    }

    m_hasPostedEvents = true;
    QSGMainThreadInvoker *mainThreadInvoker = QSGMainThreadInvoker::instance();
    QCoreApplication::postEvent(mainThreadInvoker, new QSGReleaseItemsEvent(m_sharedGraphicsCache,
                                                                            m_cacheId,
                                                                            glyphsVector,
                                                                            m_isInSceneGraphUpdate));
}
CommandTransform::CommandTransform(const ldraw::matrix &premult,
                                   const ldraw::matrix &postmult,
                                   const QSet<int> &selection,
                                   ldraw::model *model,
                                   Editor::RotationPivot pivotMode,
                                   const ldraw::vector &pivot)
    : CommandBase(selection, model)
{
    setText(QObject::tr("Transform"));

    premult_ = premult;
    postmult_ = postmult;
    pivotMode_ = pivotMode;
    pivot_ = pivot;

    for (QSet<int>::ConstIterator it = selection.constBegin(); it != selection.constEnd(); ++it) {
        if (model->elements()[*it]->get_type() == ldraw::type_ref)
            oldmatrices_[*it] = CAST_AS_CONST_REF(model->elements()[*it])->get_matrix();
    }
}
Beispiel #11
0
QList<QgsComposerInterface *> QgisAppInterface::openComposers()
{
  QList<QgsComposerInterface *> composerInterfaceList;
  if ( qgis )
  {
    const QSet<QgsComposer *> composerList = qgis->printComposers();
    QSet<QgsComposer *>::const_iterator it = composerList.constBegin();
    for ( ; it != composerList.constEnd(); ++it )
    {
      if ( *it )
      {
        QgsComposerInterface *v = ( *it )->iface();
        if ( v )
        {
          composerInterfaceList << v;
        }
      }
    }
  }
  return composerInterfaceList;
}
QList<QgsComposerView*> QgisAppInterface::activeComposers()
{
  QList<QgsComposerView*> composerViewList;
  if ( qgis )
  {
    const QSet<QgsComposer*> composerList = qgis->printComposers();
    QSet<QgsComposer*>::const_iterator it = composerList.constBegin();
    for ( ; it != composerList.constEnd(); ++it )
    {
      if ( *it )
      {
        QgsComposerView* v = ( *it )->view();
        if ( v )
        {
          composerViewList.push_back( v );
        }
      }
    }
  }
  return composerViewList;
}
Beispiel #13
0
QList<QgsLayoutDesignerInterface *> QgisAppInterface::openLayoutDesigners()
{
  QList<QgsLayoutDesignerInterface *> designerInterfaceList;
  if ( qgis )
  {
    const QSet<QgsLayoutDesignerDialog *> designerList = qgis->layoutDesigners();
    QSet<QgsLayoutDesignerDialog *>::const_iterator it = designerList.constBegin();
    for ( ; it != designerList.constEnd(); ++it )
    {
      if ( *it )
      {
        QgsLayoutDesignerInterface *v = ( *it )->iface();
        if ( v )
        {
          designerInterfaceList << v;
        }
      }
    }
  }
  return designerInterfaceList;
}
Beispiel #14
0
void PhysicsSimulation::resolveCollisions() {
    PerformanceTimer perfTimer("resolve");
    // walk all collisions, accumulate movement on shapes, and build a list of affected shapes
    QSet<Shape*> shapes;
    int numCollisions = _collisions.size();
    for (int i = 0; i < numCollisions; ++i) {
        CollisionInfo* collision = _collisions.getCollision(i);
        collision->apply();
        // there is always a shapeA
        shapes.insert(collision->getShapeA());
        // but need to check for valid shapeB
        if (collision->_shapeB) {
            shapes.insert(collision->getShapeB());
        }
    }
    // walk all affected shapes and apply accumulated movement
    QSet<Shape*>::const_iterator shapeItr = shapes.constBegin();
    while (shapeItr != shapes.constEnd()) {
        (*shapeItr)->applyAccumulatedDelta();
        ++shapeItr;
    }
}
Beispiel #15
0
void QgsComposerManager::initialize()
{
  QSet<QgsComposer*> composers = QgisApp::instance()->printComposers();
  QSet<QgsComposer*>::const_iterator it = composers.constBegin();
  for ( ; it != composers.constEnd(); ++it )
  {
    QListWidgetItem* item = new QListWidgetItem(( *it )->title(), mComposerListWidget );
    item->setFlags( Qt::ItemIsEnabled | Qt::ItemIsSelectable | Qt::ItemIsEditable );
    mItemComposerMap.insert( item, *it );
  }

  mTemplate->addItem( tr( "Empty composer" ) );

  QMap<QString, QString> templateMap = defaultTemplates();
  if ( templateMap.size() > 0 )
  {
    QMap<QString, QString>::const_iterator templateIt = templateMap.constBegin();
    for ( ; templateIt != templateMap.constEnd(); ++templateIt )
    {
      mTemplate->addItem( templateIt.key(), templateIt.value() );
    }
  }
}
// Return true if rendering properties needs to render with transparency
bool GLC_RenderProperties::needToRenderWithTransparency() const
{
	bool renderWithTransparency= false;
	if (m_RenderMode == glc::OverwriteMaterial)
	{
		Q_ASSERT(NULL != m_pOverwriteMaterial);
		renderWithTransparency= m_pOverwriteMaterial->isTransparent();
	}
	else if ((m_RenderMode == glc::OverwriteTransparency) || (m_RenderMode == glc::OverwriteTransparencyAndMaterial))
	{
		Q_ASSERT(-1.0f != m_OverwriteOpacity);
		renderWithTransparency= (m_OverwriteOpacity < 1.0f);
	}
	else if ((m_RenderMode == glc::OverwritePrimitiveMaterial)
			|| ((m_RenderMode == glc::PrimitiveSelected) && (NULL != m_pOverwritePrimitiveMaterialMaps) && (!m_pOverwritePrimitiveMaterialMaps->isEmpty())))
	{
		Q_ASSERT(NULL != m_pOverwritePrimitiveMaterialMaps);
		Q_ASSERT(!m_pOverwritePrimitiveMaterialMaps->isEmpty());

		QList<QHash<GLC_uint, GLC_Material* >* > hashList= m_pOverwritePrimitiveMaterialMaps->values();
		QSet<GLC_Material*> materialSet;
		const int size= hashList.size();
		for (int i= 0; i < size; ++i)
		{
			materialSet.unite(QSet<GLC_Material*>::fromList(hashList.at(i)->values()));
		}

		QSet<GLC_Material*>::const_iterator iMat= materialSet.constBegin();
		while ((materialSet.constEnd() != iMat) && !renderWithTransparency)
		{
			renderWithTransparency= (*iMat)->isTransparent();
			++iMat;
		}
	}

	return renderWithTransparency;
}
/**
* Populates the items (log values) into their table.
*
* @param fittedWsList :: a workspace list containing ONLY the workspaces that have parameter
*                   tables associated with it.
*/
void MuonAnalysisResultTableTab::populateLogsAndValues(const QStringList& fittedWsList)
{
  // A set of all the logs we've met in the workspaces
  QSet<QString> allLogs;

  for (int i=0; i<fittedWsList.size(); i++)
  { 
    QMap<QString, QVariant> wsLogValues;

    // Get log information
    auto ws = retrieveWSChecked<ExperimentInfo>(fittedWsList[i].toStdString() + WORKSPACE_POSTFIX);

    Mantid::Kernel::DateAndTime start = ws->run().startTime();
    Mantid::Kernel::DateAndTime end = ws->run().endTime();

    const std::vector<Property*> & logData = ws->run().getLogData();
    std::vector<Property*>::const_iterator pEnd = logData.end();

    for( std::vector<Property*>::const_iterator pItr = logData.begin(); pItr != pEnd; ++pItr )
    {  
      // Check if is a timeseries log
      if( TimeSeriesProperty<double> *tspd = dynamic_cast<TimeSeriesProperty<double>*>(*pItr) )
      {
        QString logFile(QFileInfo((**pItr).name().c_str()).fileName());

        double value(0.0);
        int count(0);

        Mantid::Kernel::DateAndTime logTime;

        //iterate through all logs entries of a specific log
        for (int k(0); k<tspd->size(); k++)
        {
          // Get the log time for the specific entry
          logTime = tspd->nthTime(k);

          // If the entry was made during the run times
          if ((logTime >= start) && (logTime <= end))
          {
            // add it to a total and increment the count (will be used to make average entry value during a run)
            value += tspd->nthValue(k);
            count++;
          }
        }

        if ( count != 0 )
        {
          //Find average
          wsLogValues[logFile] = value / count;
        }
      }
      else // Should be a non-timeseries one
      {
        QString logName = QString::fromStdString( (**pItr).name() );

        // Check if we should display it
        if ( NON_TIMESERIES_LOGS.contains(logName) )
        {
          QVariant value;

          if ( auto stringProp = dynamic_cast<PropertyWithValue<std::string>*>(*pItr) )
          {
            value = QString::fromStdString( (*stringProp)() );
          }
          else if ( auto doubleProp = dynamic_cast<PropertyWithValue<double>*>(*pItr) )
          {
            value = (*doubleProp)();
          }
          else
          {
            throw std::runtime_error("Unsupported non-timeseries log type");
          }

          wsLogValues[logName] = value;
        }
      }
    }

    // Append log names found in the workspace to the list of all known log names
    allLogs += wsLogValues.keys().toSet();

    // Add all data collected from one workspace to another map. Will be used when creating table.
    m_logValues[fittedWsList[i]] = wsLogValues;

  } // End loop over all workspace's log information and param information

  // Remove the logs that don't appear in all workspaces
  QSet<QString> toRemove;
  for ( auto logIt = allLogs.constBegin(); logIt != allLogs.constEnd(); ++logIt )
  {
    for ( auto wsIt = m_logValues.constBegin(); wsIt != m_logValues.constEnd(); ++wsIt )
    { 
      auto wsLogValues = wsIt.value();
      if ( ! wsLogValues.contains(*logIt) )
      {      
        toRemove.insert(*logIt);
        break;
      }
    }      
  }

  allLogs = allLogs.subtract(toRemove);

  // Sort logs
  QList<QString> allLogsSorted(allLogs.toList());
  qSort(allLogsSorted.begin(), allLogsSorted.end(), MuonAnalysisResultTableTab::logNameLessThan);
  
  // Add number of rows to the table based on number of logs to display.
  m_uiForm.valueTable->setRowCount(allLogsSorted.size());

  // Populate table with all log values available without repeating any.
  for ( auto it = allLogsSorted.constBegin(); it != allLogsSorted.constEnd(); ++it )
  {
    int row = static_cast<int>( std::distance(allLogsSorted.constBegin(), it) );
    m_uiForm.valueTable->setItem(row, 0, new QTableWidgetItem(*it));
  }

  // Save the number of logs displayed
  // XXX: this is redundant, as number of logs == number of rows
  m_numLogsdisplayed = m_uiForm.valueTable->rowCount();

  // Add check boxes for the include column on log table, and make text uneditable.
  for (int i = 0; i < m_uiForm.valueTable->rowCount(); i++)
  {
    m_uiForm.valueTable->setCellWidget(i,1, new QCheckBox);
    
    if( auto textItem = m_uiForm.valueTable->item(i, 0) )
    {
      textItem->setFlags(textItem->flags() & (~Qt::ItemIsEditable));
    }
  }
}
Beispiel #18
0
void * QgsMultiBandColorRenderer::readBlock( int bandNo, QgsRectangle  const & extent, int width, int height )
{
  Q_UNUSED( bandNo );
  if ( !mInput )
  {
    return 0;
  }

  //In some (common) cases, we can simplify the drawing loop considerably and save render time
  bool fastDraw = ( !usesTransparency()
                    && mRedBand > 0 && mGreenBand > 0 && mBlueBand > 0
                    && mAlphaBand < 1 && !mRedContrastEnhancement && !mGreenContrastEnhancement && !mBlueContrastEnhancement
                    && !mInvertColor );

  QgsRasterInterface::DataType redType = QgsRasterInterface::UnknownDataType;

  if ( mRedBand > 0 )
  {
    redType = ( QgsRasterInterface::DataType )mInput->dataType( mRedBand );
  }
  QgsRasterInterface::DataType greenType = QgsRasterInterface::UnknownDataType;
  if ( mGreenBand > 0 )
  {
    greenType = ( QgsRasterInterface::DataType )mInput->dataType( mGreenBand );
  }
  QgsRasterInterface::DataType blueType = QgsRasterInterface::UnknownDataType;
  if ( mBlueBand > 0 )
  {
    blueType = ( QgsRasterInterface::DataType )mInput->dataType( mBlueBand );
  }
  QgsRasterInterface::DataType transparencyType = QgsRasterInterface::UnknownDataType;
  if ( mAlphaBand > 0 )
  {
    transparencyType = ( QgsRasterInterface::DataType )mInput->dataType( mAlphaBand );
  }

  QSet<int> bands;
  if ( mRedBand > 0 )
  {
    bands << mRedBand;
  }
  if ( mGreenBand > 0 )
  {
    bands << mGreenBand;
  }
  if ( mBlueBand > 0 )
  {
    bands << mBlueBand;
  }
  if ( bands.size() < 1 )
  {
    return 0; //no need to draw anything if no band is set
  }

  if ( mAlphaBand > 0 )
  {
    bands << mAlphaBand;
  }

  QMap<int, void*> bandData;
  void* defaultPointer = 0;
  QSet<int>::const_iterator bandIt = bands.constBegin();
  for ( ; bandIt != bands.constEnd(); ++bandIt )
  {
    bandData.insert( *bandIt, defaultPointer );
  }

  void* redData = 0;
  void* greenData = 0;
  void* blueData = 0;
  void* alphaData = 0;

  bandIt = bands.constBegin();
  for ( ; bandIt != bands.constEnd(); ++bandIt )
  {
    bandData[*bandIt] =  mInput->block( *bandIt, extent, width, height );
    if ( !bandData[*bandIt] )
    {
      // We should free the alloced mem from block().
      QgsDebugMsg( "No input band" );
      bandIt--;
      for ( ; bandIt != bands.constBegin(); bandIt-- )
      {
        VSIFree( bandData[*bandIt] );
      }
      return 0;
    }
  }

  if ( mRedBand > 0 )
  {
    redData = bandData[mRedBand];
  }
  if ( mGreenBand > 0 )
  {
    greenData = bandData[mGreenBand];
  }
  if ( mBlueBand > 0 )
  {
    blueData = bandData[mBlueBand];
  }
  if ( mAlphaBand > 0 )
  {
    alphaData = bandData[mAlphaBand];
  }

  QImage img( width, height, QImage::Format_ARGB32_Premultiplied );
  if ( img.isNull() )
  {
    QgsDebugMsg( "Could not create QImage" );
    bandIt = bands.constBegin();
    for ( ; bandIt != bands.constEnd(); ++bandIt )
    {
      VSIFree( bandData[*bandIt] );
    }
    return 0;
  }

  QRgb* imageScanLine = 0;
  int currentRasterPos = 0;
  int redVal = 0;
  int greenVal = 0;
  int blueVal = 0;
  QRgb defaultColor = qRgba( 255, 255, 255, 0 );
  double currentOpacity = mOpacity; //opacity (between 0 and 1)

  for ( int i = 0; i < height; ++i )
  {
    imageScanLine = ( QRgb* )( img.scanLine( i ) );
    for ( int j = 0; j < width; ++j )
    {
      if ( fastDraw ) //fast rendering if no transparency, stretching, color inversion, etc.
      {
        redVal = readValue( redData, redType, currentRasterPos );
        greenVal = readValue( greenData, greenType, currentRasterPos );
        blueVal = readValue( blueData, blueType, currentRasterPos );
        if ( mInput->isNoDataValue( mRedBand, redVal ) ||
             mInput->isNoDataValue( mGreenBand, greenVal ) ||
             mInput->isNoDataValue( mBlueBand, blueVal ) )
        {
          imageScanLine[j] = defaultColor;
        }
        else
        {
          imageScanLine[j] = qRgba( redVal, greenVal, blueVal, 255 );
        }

        ++currentRasterPos;
        continue;
      }

      bool isNoData = false;
      if ( mRedBand > 0 )
      {
        redVal = readValue( redData, redType, currentRasterPos );
        if ( mInput->isNoDataValue( mRedBand, redVal ) ) isNoData = true;
      }
      if ( mGreenBand > 0 )
      {
        greenVal = readValue( greenData, greenType, currentRasterPos );
        if ( mInput->isNoDataValue( mGreenBand, greenVal ) ) isNoData = true;
      }
      if ( mBlueBand > 0 )
      {
        blueVal = readValue( blueData, blueType, currentRasterPos );
        if ( mInput->isNoDataValue( mBlueBand, blueVal ) ) isNoData = true;
      }
      if ( isNoData )
      {
        imageScanLine[j] = defaultColor;
        ++currentRasterPos;
        continue;
      }

      //apply default color if red, green or blue not in displayable range
      if (( mRedContrastEnhancement && !mRedContrastEnhancement->isValueInDisplayableRange( redVal ) )
          || ( mGreenContrastEnhancement && !mGreenContrastEnhancement->isValueInDisplayableRange( redVal ) )
          || ( mBlueContrastEnhancement && !mBlueContrastEnhancement->isValueInDisplayableRange( redVal ) ) )
      {
        imageScanLine[j] = defaultColor;
        ++currentRasterPos;
        continue;
      }

      //stretch color values
      if ( mRedContrastEnhancement )
      {
        redVal = mRedContrastEnhancement->enhanceContrast( redVal );
      }
      if ( mGreenContrastEnhancement )
      {
        greenVal = mGreenContrastEnhancement->enhanceContrast( greenVal );
      }
      if ( mBlueContrastEnhancement )
      {
        blueVal = mBlueContrastEnhancement->enhanceContrast( blueVal );
      }

      if ( mInvertColor )
      {
        redVal = 255 - redVal;
        greenVal = 255 - greenVal;
        blueVal = 255 - blueVal;
      }

      //opacity
      currentOpacity = mOpacity;
      if ( mRasterTransparency )
      {
        currentOpacity = mRasterTransparency->alphaValue( redVal, greenVal, blueVal, mOpacity * 255 ) / 255.0;
      }
      if ( mAlphaBand > 0 )
      {
        currentOpacity *= ( readValue( alphaData, transparencyType, currentRasterPos ) / 255.0 );
      }

      if ( doubleNear( currentOpacity, 1.0 ) )
      {
        imageScanLine[j] = qRgba( redVal, greenVal, blueVal, 255 );
      }
      else
      {
        imageScanLine[j] = qRgba( currentOpacity * redVal, currentOpacity * greenVal, currentOpacity * blueVal, currentOpacity * 255 );
      }

      ++currentRasterPos;
    }
  }

  bandIt = bands.constBegin();
  for ( ; bandIt != bands.constEnd(); ++bandIt )
  {
    VSIFree( bandData[*bandIt] );
  }

  void * data = VSIMalloc( img.byteCount() );
  if ( ! data )
  {
    QgsDebugMsg( QString( "Couldn't allocate output data memory of % bytes" ).arg( img.byteCount() ) );
    return 0;
  }
  return memcpy( data, img.bits(), img.byteCount() );
}
Beispiel #19
0
void Locator::computeProjLevel()
{
	QSet<SymbolPath> projProcessed;
	QSet<SymbolPath> curLowestSet;
	for (QHash<SymbolPath, ProjectData>::Iterator pProj = m_projectWordList.begin();
		 pProj != m_projectWordList.end(); ++pProj)
	{
		ProjectData& proj = pProj.value();
		SymbolData&  data = proj.m_projectData;
		bool isLowest = data.m_lowLevelSym.size() == 0;
		bool isHighest= data.m_highLevelSym.size()== 0;
		if (isLowest && isHighest)
		{	// isolated project
			proj.m_projectData.m_level = 0;
			projProcessed.insert(pProj.key());
		}
		else if (isLowest)
			curLowestSet.insert(pProj.key());
	}

	int curLevel = 0;
	for (; curLowestSet.size() != 0; curLevel++)
	{
		// set current lowest level
		for (QSet<SymbolPath>::ConstIterator pProjPath = curLowestSet.constBegin();
			 pProjPath != curLowestSet.constEnd(); pProjPath++)
		{
			m_projectWordList[*pProjPath].m_projectData.m_level = curLevel;
			projProcessed.insert(*pProjPath);
		}

		QSet<SymbolPath> nextLowestSet;
		QSet<SymbolPath> candidateSet;
		for (QSet<SymbolPath>::ConstIterator pProjPath = curLowestSet.constBegin();
			pProjPath != curLowestSet.constEnd(); pProjPath++)
		{
			const ProjectData& projData = m_projectWordList[*pProjPath];
			const SymbolData&  data     = projData.m_projectData;

			// insert projects that only depends on processed project to next lowest set
			for (QSet<SymbolPath>::ConstIterator pHighProj = data.m_highLevelSym.constBegin();
				pHighProj != data.m_highLevelSym.constEnd(); pHighProj++)
			{
				// ignore self-link or loop node
				if (projProcessed.contains(*pHighProj))
					continue;
				ProjectData& highProj = m_projectWordList[*pHighProj];
				SymbolData & highData = highProj.m_projectData;
				if ((highData.m_lowLevelSym-projProcessed).size() == 0)
					nextLowestSet.insert(*pHighProj);
				else
					candidateSet.insert(*pHighProj);
			}
		}

		// encounter loop
		if (nextLowestSet.size() == 0 && candidateSet.size() != 0)
			curLowestSet = candidateSet;
		else
			curLowestSet = nextLowestSet;
	}
}
Beispiel #20
0
void Locator::computeSymbolLevel(ProjectData& proj)
{
	QSet<SymbolPath> symProcessed;
	QSet<SymbolPath> curLowestSet;
	for (QHash<SymbolPath, SymbolData>::Iterator pSym = proj.m_symbolData.begin();
		pSym != proj.m_symbolData.end(); ++pSym)
	{
		SymbolData&  data = pSym.value();
		bool isLowest = data.m_lowLevelSym.size() == 0;
		bool isHighest= data.m_highLevelSym.size()== 0;
		if (isLowest && isHighest)
		{	// isolated project
			data.m_level = 0;
			symProcessed.insert(pSym.key());
		}
		else if (isLowest)
			curLowestSet.insert(pSym.key());
	}

	int maxLevel = 0;
	for (int curLevel = 0; curLowestSet.size() != 0; curLevel++)
	{
		maxLevel = curLevel;

		// set current lowest level
		for (QSet<SymbolPath>::ConstIterator pSym = curLowestSet.constBegin();
			pSym != curLowestSet.constEnd(); pSym++)
		{
			proj.m_symbolData[*pSym].m_level = curLevel;
			symProcessed.insert(*pSym);
		}

		QSet<SymbolPath> nextLowestSet;
		QSet<SymbolPath> candidateSet;
		for (QSet<SymbolPath>::ConstIterator pSym = curLowestSet.constBegin();
			pSym != curLowestSet.constEnd(); pSym++)
		{
			const SymbolData&  data     = proj.m_symbolData[*pSym];

			// insert projects that only depends on processed project to next lowest set
			for (QSet<SymbolPath>::ConstIterator pHighSym = data.m_highLevelSym.constBegin();
				pHighSym != data.m_highLevelSym.constEnd(); pHighSym++)
			{
				// ignore self-link or loop node
				if (symProcessed.contains(*pHighSym))
					continue;
				SymbolData & highData = proj.m_symbolData[*pHighSym];
				if ((highData.m_lowLevelSym-symProcessed).size() == 0)
					nextLowestSet.insert(*pHighSym);
				else
					candidateSet.insert(*pHighSym);
			}
		}

		// encounter loop
		if (nextLowestSet.size() == 0 && candidateSet.size() != 0)
			curLowestSet = candidateSet;
		else
			curLowestSet = nextLowestSet;
	}
	proj.m_nSymbolLevel = maxLevel + 1;
}
QgsRasterBlock *QgsMultiBandColorRenderer::block( int bandNo, QgsRectangle  const &extent, int width, int height, QgsRasterBlockFeedback *feedback )
{
  Q_UNUSED( bandNo );
  std::unique_ptr< QgsRasterBlock > outputBlock( new QgsRasterBlock() );
  if ( !mInput )
  {
    return outputBlock.release();
  }

  //In some (common) cases, we can simplify the drawing loop considerably and save render time
  bool fastDraw = ( !usesTransparency()
                    && mRedBand > 0 && mGreenBand > 0 && mBlueBand > 0
                    && mAlphaBand < 1 && !mRedContrastEnhancement && !mGreenContrastEnhancement && !mBlueContrastEnhancement );

  QSet<int> bands;
  if ( mRedBand > 0 )
  {
    bands << mRedBand;
  }
  if ( mGreenBand > 0 )
  {
    bands << mGreenBand;
  }
  if ( mBlueBand > 0 )
  {
    bands << mBlueBand;
  }
  if ( bands.size() < 1 )
  {
    // no need to draw anything if no band is set
    // TODO:: we should probably return default color block
    return outputBlock.release();
  }

  if ( mAlphaBand > 0 )
  {
    bands << mAlphaBand;
  }

  QMap<int, QgsRasterBlock *> bandBlocks;
  QgsRasterBlock *defaultPointer = nullptr;
  QSet<int>::const_iterator bandIt = bands.constBegin();
  for ( ; bandIt != bands.constEnd(); ++bandIt )
  {
    bandBlocks.insert( *bandIt, defaultPointer );
  }

  QgsRasterBlock *redBlock = nullptr;
  QgsRasterBlock *greenBlock = nullptr;
  QgsRasterBlock *blueBlock = nullptr;
  QgsRasterBlock *alphaBlock = nullptr;

  bandIt = bands.constBegin();
  for ( ; bandIt != bands.constEnd(); ++bandIt )
  {
    bandBlocks[*bandIt] =  mInput->block( *bandIt, extent, width, height, feedback );
    if ( !bandBlocks[*bandIt] )
    {
      // We should free the alloced mem from block().
      QgsDebugMsg( "No input band" );
      --bandIt;
      for ( ; bandIt != bands.constBegin(); --bandIt )
      {
        delete bandBlocks[*bandIt];
      }
      return outputBlock.release();
    }
  }

  if ( mRedBand > 0 )
  {
    redBlock = bandBlocks[mRedBand];
  }
  if ( mGreenBand > 0 )
  {
    greenBlock = bandBlocks[mGreenBand];
  }
  if ( mBlueBand > 0 )
  {
    blueBlock = bandBlocks[mBlueBand];
  }
  if ( mAlphaBand > 0 )
  {
    alphaBlock = bandBlocks[mAlphaBand];
  }

  if ( !outputBlock->reset( Qgis::ARGB32_Premultiplied, width, height ) )
  {
    for ( int i = 0; i < bandBlocks.size(); i++ )
    {
      delete bandBlocks.value( i );
    }
    return outputBlock.release();
  }

  QRgb myDefaultColor = NODATA_COLOR;

  for ( qgssize i = 0; i < ( qgssize )width * height; i++ )
  {
    if ( fastDraw ) //fast rendering if no transparency, stretching, color inversion, etc.
    {
      if ( redBlock->isNoData( i ) ||
           greenBlock->isNoData( i ) ||
           blueBlock->isNoData( i ) )
      {
        outputBlock->setColor( i, myDefaultColor );
      }
      else
      {
        int redVal = ( int )redBlock->value( i );
        int greenVal = ( int )greenBlock->value( i );
        int blueVal = ( int )blueBlock->value( i );
        outputBlock->setColor( i, qRgba( redVal, greenVal, blueVal, 255 ) );
      }
      continue;
    }

    bool isNoData = false;
    double redVal = 0;
    double greenVal = 0;
    double blueVal = 0;
    if ( mRedBand > 0 )
    {
      redVal = redBlock->value( i );
      if ( redBlock->isNoData( i ) ) isNoData = true;
    }
    if ( !isNoData && mGreenBand > 0 )
    {
      greenVal = greenBlock->value( i );
      if ( greenBlock->isNoData( i ) ) isNoData = true;
    }
    if ( !isNoData && mBlueBand > 0 )
    {
      blueVal = blueBlock->value( i );
      if ( blueBlock->isNoData( i ) ) isNoData = true;
    }
    if ( isNoData )
    {
      outputBlock->setColor( i, myDefaultColor );
      continue;
    }

    //apply default color if red, green or blue not in displayable range
    if ( ( mRedContrastEnhancement && !mRedContrastEnhancement->isValueInDisplayableRange( redVal ) )
         || ( mGreenContrastEnhancement && !mGreenContrastEnhancement->isValueInDisplayableRange( redVal ) )
         || ( mBlueContrastEnhancement && !mBlueContrastEnhancement->isValueInDisplayableRange( redVal ) ) )
    {
      outputBlock->setColor( i, myDefaultColor );
      continue;
    }

    //stretch color values
    if ( mRedContrastEnhancement )
    {
      redVal = mRedContrastEnhancement->enhanceContrast( redVal );
    }
    if ( mGreenContrastEnhancement )
    {
      greenVal = mGreenContrastEnhancement->enhanceContrast( greenVal );
    }
    if ( mBlueContrastEnhancement )
    {
      blueVal = mBlueContrastEnhancement->enhanceContrast( blueVal );
    }

    //opacity
    double currentOpacity = mOpacity;
    if ( mRasterTransparency )
    {
      currentOpacity = mRasterTransparency->alphaValue( redVal, greenVal, blueVal, mOpacity * 255 ) / 255.0;
    }
    if ( mAlphaBand > 0 )
    {
      currentOpacity *= alphaBlock->value( i ) / 255.0;
    }

    if ( qgsDoubleNear( currentOpacity, 1.0 ) )
    {
      outputBlock->setColor( i, qRgba( redVal, greenVal, blueVal, 255 ) );
    }
    else
    {
      outputBlock->setColor( i, qRgba( currentOpacity * redVal, currentOpacity * greenVal, currentOpacity * blueVal, currentOpacity * 255 ) );
    }
  }

  //delete input blocks
  QMap<int, QgsRasterBlock *>::const_iterator bandDelIt = bandBlocks.constBegin();
  for ( ; bandDelIt != bandBlocks.constEnd(); ++bandDelIt )
  {
    delete bandDelIt.value();
  }

  return outputBlock.release();
}
void QgsMultiBandColorRenderer::draw( QPainter* p, QgsRasterViewPort* viewPort, const QgsMapToPixel* theQgsMapToPixel )
{
  if ( !p || !mProvider || !viewPort || !theQgsMapToPixel )
  {
    return;
  }

  //In some (common) cases, we can simplify the drawing loop considerably and save render time
  bool fastDraw = (
                    !usesTransparency( viewPort->mSrcCRS, viewPort->mDestCRS )
                    && mRedBand > 0 && mGreenBand > 0 && mBlueBand > 0
                    && mAlphaBand < 1 && !mRedContrastEnhancement && !mGreenContrastEnhancement && !mBlueContrastEnhancement
                    && !mInvertColor );

  QgsRasterDataProvider::DataType redType = QgsRasterDataProvider::UnknownDataType;
  if ( mRedBand > 0 )
  {
    redType = ( QgsRasterDataProvider::DataType )mProvider->dataType( mRedBand );
  }
  QgsRasterDataProvider::DataType greenType = QgsRasterDataProvider::UnknownDataType;
  if ( mGreenBand > 0 )
  {
    greenType = ( QgsRasterDataProvider::DataType )mProvider->dataType( mGreenBand );
  }
  QgsRasterDataProvider::DataType blueType = QgsRasterDataProvider::UnknownDataType;
  if ( mBlueBand > 0 )
  {
    blueType = ( QgsRasterDataProvider::DataType )mProvider->dataType( mBlueBand );
  }
  QgsRasterDataProvider::DataType transparencyType = QgsRasterDataProvider::UnknownDataType;
  if ( mAlphaBand > 0 )
  {
    transparencyType = ( QgsRasterDataProvider::DataType )mProvider->dataType( mAlphaBand );
  }

  double oversamplingX = 1.0, oversamplingY = 1.0;
  QSet<int> bands;
  if ( mRedBand > 0 )
  {
    bands << mRedBand;
  }
  if ( mGreenBand > 0 )
  {
    bands << mGreenBand;
  }
  if ( mBlueBand > 0 )
  {
    bands << mBlueBand;
  }
  if ( bands.size() < 1 )
  {
    return; //no need to draw anything if no band is set
  }

  if ( mAlphaBand > 0 )
  {
    bands << mAlphaBand;
  }

  QMap<int, void*> bandData;
  void* defaultPointer = 0;
  QSet<int>::const_iterator bandIt = bands.constBegin();
  for ( ; bandIt != bands.constEnd(); ++bandIt )
  {
    bandData.insert( *bandIt, defaultPointer );
    startRasterRead( *bandIt, viewPort, theQgsMapToPixel, oversamplingX, oversamplingY );
  }

  void* redData = 0;
  void* greenData = 0;
  void* blueData = 0;
  void* alphaData = 0;
  //number of cols/rows in output pixels
  int nCols = 0;
  int nRows = 0;
  //number of raster cols/rows with oversampling
  int nRasterCols = 0;
  int nRasterRows = 0;
  //shift to top left point for the raster part
  int topLeftCol = 0;
  int topLeftRow = 0;

  bool readSuccess = true;
  while ( true )
  {
    QSet<int>::const_iterator bandIt = bands.constBegin();
    for ( ; bandIt != bands.constEnd(); ++bandIt )
    {
      readSuccess = readSuccess && readNextRasterPart( *bandIt, oversamplingX, oversamplingY, viewPort, nCols, nRows,
                    nRasterCols, nRasterRows, &bandData[*bandIt], topLeftCol, topLeftRow );
    }

    if ( !readSuccess )
    {
      break;
    }

    if ( mRedBand > 0 )
    {
      redData = bandData[mRedBand];
    }
    if ( mGreenBand > 0 )
    {
      greenData = bandData[mGreenBand];
    }
    if ( mBlueBand > 0 )
    {
      blueData = bandData[mBlueBand];
    }
    if ( mAlphaBand > 0 )
    {
      alphaData = bandData[mAlphaBand];
    }

    QImage img( nRasterCols, nRasterRows, QImage::Format_ARGB32_Premultiplied );
    QRgb* imageScanLine = 0;
    int currentRasterPos = 0;
    int redVal = 0;
    int greenVal = 0;
    int blueVal = 0;
    int redDataVal = 0;
    int greenDataVal = 0;
    int blueDataVal = 0;
    QRgb defaultColor = qRgba( 255, 255, 255, 0 );
    double currentOpacity = mOpacity; //opacity (between 0 and 1)

    for ( int i = 0; i < nRasterRows; ++i )
    {
      imageScanLine = ( QRgb* )( img.scanLine( i ) );
      for ( int j = 0; j < nRasterCols; ++j )
      {

        if ( fastDraw ) //fast rendering if no transparency, stretching, color inversion, etc.
        {
          redVal = readValue( redData, redType, currentRasterPos );
          greenVal = readValue( greenData, greenType, currentRasterPos );
          blueVal = readValue( blueData, blueType, currentRasterPos );
          imageScanLine[j] = qRgba( redVal, greenVal, blueVal, 255 );
          ++currentRasterPos;
          continue;
        }

        if ( mRedBand > 0 )
        {
          redVal = readValue( redData, redType, currentRasterPos );
          redDataVal = redVal;
        }
        if ( mGreenBand > 0 )
        {
          greenVal = readValue( greenData, greenType, currentRasterPos );
          greenDataVal = greenVal;
        }
        if ( mBlueBand > 0 )
        {
          blueVal = readValue( blueData, blueType, currentRasterPos );
          blueDataVal = blueVal;
        }

        //apply default color if red, green or blue not in displayable range
        if (( mRedContrastEnhancement && !mRedContrastEnhancement->isValueInDisplayableRange( redVal ) )
            || ( mGreenContrastEnhancement && !mGreenContrastEnhancement->isValueInDisplayableRange( redVal ) )
            || ( mBlueContrastEnhancement && !mBlueContrastEnhancement->isValueInDisplayableRange( redVal ) ) )
        {
          imageScanLine[j] = defaultColor;
          ++currentRasterPos;
          continue;
        }

        //stretch color values
        if ( mRedContrastEnhancement )
        {
          redVal = mRedContrastEnhancement->enhanceContrast( redVal );
        }
        if ( mGreenContrastEnhancement )
        {
          greenVal = mGreenContrastEnhancement->enhanceContrast( greenVal );
        }
        if ( mBlueContrastEnhancement )
        {
          blueVal = mBlueContrastEnhancement->enhanceContrast( blueVal );
        }

        if ( mInvertColor )
        {
          redVal = 255 - redVal;
          greenVal = 255 - greenVal;
          blueVal = 255 - blueVal;
        }

        //opacity
        currentOpacity = mOpacity;
        if ( mRasterTransparency )
        {
          currentOpacity = mRasterTransparency->alphaValue( redDataVal, greenDataVal, blueDataVal, mOpacity * 255 ) / 255.0;
        }
        if ( mAlphaBand > 0 )
        {
          currentOpacity *= ( readValue( alphaData, transparencyType, currentRasterPos ) / 255.0 );
        }

        if ( doubleNear( currentOpacity, 1.0 ) )
        {
          imageScanLine[j] = qRgba( redVal, greenVal, blueVal, 255 );
        }
        else
        {
          imageScanLine[j] = qRgba( currentOpacity * redVal, currentOpacity * greenVal, currentOpacity * blueVal, currentOpacity * 255 );
        }
        ++currentRasterPos;
      }
    }

    drawImage( p, viewPort, img, topLeftCol, topLeftRow, nCols, nRows, oversamplingX, oversamplingY );
  }

  bandIt = bands.constBegin();
  for ( ; bandIt != bands.constEnd(); ++bandIt )
  {
    stopRasterRead( *bandIt );
  }
}
Beispiel #23
0
QScriptObjectSnapshot::Delta QScriptObjectSnapshot::capture(const QScriptValue &object)
{
    Delta result;
    QMap<QString, QScriptValueProperty> currProps;
    QHash<QString, int> propertyNameToIndex;
    {
        int i = 0;
        QScriptValueIterator it(object);
        while (it.hasNext()) {
            it.next();
            QScriptValueProperty prop(it.name(), it.value(), it.flags());
            currProps.insert(it.name(), prop);
            propertyNameToIndex.insert(it.name(), i);
            ++i;
        }
        if (object.prototype().isValid()) {
            QString __proto__ = QString::fromLatin1("__proto__");
            QScriptValueProperty protoProp(
                __proto__, object.prototype(),
                QScriptValue::Undeletable | QScriptValue::ReadOnly);
            currProps.insert(__proto__, protoProp);
            propertyNameToIndex.insert(__proto__, i);
            ++i;
        }
    }

    QSet<QString> prevSet;
    for (int i = 0; i < m_properties.size(); ++i)
        prevSet.insert(m_properties.at(i).name());
    QSet<QString> currSet = currProps.keys().toSet();
    QSet<QString> removedProperties = prevSet - currSet;
    QSet<QString> addedProperties = currSet - prevSet;
    QSet<QString> maybeChangedProperties = currSet & prevSet;

    {
        QMap<int, QScriptValueProperty> am;
        QSet<QString>::const_iterator it;
        for (it = addedProperties.constBegin(); it != addedProperties.constEnd(); ++it) {
            int idx = propertyNameToIndex[*it];
            am[idx] = currProps[*it];
        }
        result.addedProperties = am.values();
    }

    {
        QSet<QString>::const_iterator it;
        for (it = maybeChangedProperties.constBegin(); it != maybeChangedProperties.constEnd(); ++it) {
            const QScriptValueProperty &p1 = currProps[*it];
            const QScriptValueProperty &p2 = findProperty(*it);
            if (!_q_equal(p1.value(), p2.value())
                || (p1.flags() != p2.flags())) {
                result.changedProperties.append(p1);
            }
        }
    }

    result.removedProperties = removedProperties.toList();

    m_properties = currProps.values();

    return result;
}
QgsRasterBlock *QgsMultiBandColorRenderer::block( int bandNo, QgsRectangle  const &extent, int width, int height, QgsRasterBlockFeedback *feedback )
{
  Q_UNUSED( bandNo );
  std::unique_ptr< QgsRasterBlock > outputBlock( new QgsRasterBlock() );
  if ( !mInput )
  {
    return outputBlock.release();
  }

  //In some (common) cases, we can simplify the drawing loop considerably and save render time
  bool fastDraw = ( !usesTransparency()
                    && mRedBand > 0 && mGreenBand > 0 && mBlueBand > 0
                    && mAlphaBand < 1 );

  QSet<int> bands;
  if ( mRedBand > 0 )
  {
    bands << mRedBand;
  }
  if ( mGreenBand > 0 )
  {
    bands << mGreenBand;
  }
  if ( mBlueBand > 0 )
  {
    bands << mBlueBand;
  }
  if ( bands.empty() )
  {
    // no need to draw anything if no band is set
    // TODO:: we should probably return default color block
    return outputBlock.release();
  }

  if ( mAlphaBand > 0 )
  {
    bands << mAlphaBand;
  }

  QMap<int, QgsRasterBlock *> bandBlocks;
  QgsRasterBlock *defaultPointer = nullptr;
  QSet<int>::const_iterator bandIt = bands.constBegin();
  for ( ; bandIt != bands.constEnd(); ++bandIt )
  {
    bandBlocks.insert( *bandIt, defaultPointer );
  }

  QgsRasterBlock *redBlock = nullptr;
  QgsRasterBlock *greenBlock = nullptr;
  QgsRasterBlock *blueBlock = nullptr;
  QgsRasterBlock *alphaBlock = nullptr;

  bandIt = bands.constBegin();
  for ( ; bandIt != bands.constEnd(); ++bandIt )
  {
    bandBlocks[*bandIt] = mInput->block( *bandIt, extent, width, height, feedback );
    if ( !bandBlocks[*bandIt] )
    {
      // We should free the alloced mem from block().
      QgsDebugMsg( QStringLiteral( "No input band" ) );
      --bandIt;
      for ( ; bandIt != bands.constBegin(); --bandIt )
      {
        delete bandBlocks[*bandIt];
      }
      return outputBlock.release();
    }
  }

  if ( mRedBand > 0 )
  {
    redBlock = bandBlocks[mRedBand];
  }
  if ( mGreenBand > 0 )
  {
    greenBlock = bandBlocks[mGreenBand];
  }
  if ( mBlueBand > 0 )
  {
    blueBlock = bandBlocks[mBlueBand];
  }
  if ( mAlphaBand > 0 )
  {
    alphaBlock = bandBlocks[mAlphaBand];
  }

  if ( !outputBlock->reset( Qgis::ARGB32_Premultiplied, width, height ) )
  {
    for ( int i = 0; i < bandBlocks.size(); i++ )
    {
      delete bandBlocks.value( i );
    }
    return outputBlock.release();
  }

  QRgb *outputBlockColorData = outputBlock->colorData();

  // faster data access to data for the common case that input data are coming from RGB image with 8-bit bands
  bool hasByteRgb = ( redBlock && greenBlock && blueBlock && redBlock->dataType() == Qgis::Byte && greenBlock->dataType() == Qgis::Byte && blueBlock->dataType() == Qgis::Byte );
  const quint8 *redData = nullptr, *greenData = nullptr, *blueData = nullptr;
  if ( hasByteRgb )
  {
    redData = redBlock->byteData();
    greenData = greenBlock->byteData();
    blueData = blueBlock->byteData();
  }

  QRgb myDefaultColor = NODATA_COLOR;

  if ( fastDraw )
  {
    // By default RGB raster layers have contrast enhancement assigned and normally that requires us to take the slow
    // route that applies the enhancement. However if the algorithm type is "no enhancement" and all input bands are byte-sized,
    // no transform would be applied to the input values and we can take the fast route.
    bool hasEnhancement;
    if ( hasByteRgb )
    {
      hasEnhancement =
        ( mRedContrastEnhancement && mRedContrastEnhancement->contrastEnhancementAlgorithm() != QgsContrastEnhancement::NoEnhancement ) ||
        ( mGreenContrastEnhancement && mGreenContrastEnhancement->contrastEnhancementAlgorithm() != QgsContrastEnhancement::NoEnhancement ) ||
        ( mBlueContrastEnhancement && mBlueContrastEnhancement->contrastEnhancementAlgorithm() != QgsContrastEnhancement::NoEnhancement );
    }
    else
    {
      hasEnhancement = mRedContrastEnhancement || mGreenContrastEnhancement || mBlueContrastEnhancement;
    }
    if ( hasEnhancement )
      fastDraw = false;
  }

  qgssize count = ( qgssize )width * height;
  for ( qgssize i = 0; i < count; i++ )
  {
    if ( fastDraw ) //fast rendering if no transparency, stretching, color inversion, etc.
    {
      if ( redBlock->isNoData( i ) ||
           greenBlock->isNoData( i ) ||
           blueBlock->isNoData( i ) )
      {
        outputBlock->setColor( i, myDefaultColor );
      }
      else
      {
        if ( hasByteRgb )
        {
          outputBlockColorData[i] = qRgb( redData[i], greenData[i], blueData[i] );
        }
        else
        {
          int redVal = static_cast<int>( redBlock->value( i ) );
          int greenVal = static_cast<int>( greenBlock->value( i ) );
          int blueVal = static_cast<int>( blueBlock->value( i ) );
          outputBlockColorData[i] = qRgb( redVal, greenVal, blueVal );
        }
      }
      continue;
    }

    bool isNoData = false;
    double redVal = 0;
    double greenVal = 0;
    double blueVal = 0;
    if ( mRedBand > 0 )
    {
      redVal = redBlock->value( i );
      if ( redBlock->isNoData( i ) ) isNoData = true;
    }
    if ( !isNoData && mGreenBand > 0 )
    {
      greenVal = greenBlock->value( i );
      if ( greenBlock->isNoData( i ) ) isNoData = true;
    }
    if ( !isNoData && mBlueBand > 0 )
    {
      blueVal = blueBlock->value( i );
      if ( blueBlock->isNoData( i ) ) isNoData = true;
    }
    if ( isNoData )
    {
      outputBlock->setColor( i, myDefaultColor );
      continue;
    }

    //apply default color if red, green or blue not in displayable range
    if ( ( mRedContrastEnhancement && !mRedContrastEnhancement->isValueInDisplayableRange( redVal ) )
         || ( mGreenContrastEnhancement && !mGreenContrastEnhancement->isValueInDisplayableRange( redVal ) )
         || ( mBlueContrastEnhancement && !mBlueContrastEnhancement->isValueInDisplayableRange( redVal ) ) )
    {
      outputBlock->setColor( i, myDefaultColor );
      continue;
    }

    //stretch color values
    if ( mRedContrastEnhancement )
    {
      redVal = mRedContrastEnhancement->enhanceContrast( redVal );
    }
    if ( mGreenContrastEnhancement )
    {
      greenVal = mGreenContrastEnhancement->enhanceContrast( greenVal );
    }
    if ( mBlueContrastEnhancement )
    {
      blueVal = mBlueContrastEnhancement->enhanceContrast( blueVal );
    }

    //opacity
    double currentOpacity = mOpacity;
    if ( mRasterTransparency )
    {
      currentOpacity = mRasterTransparency->alphaValue( redVal, greenVal, blueVal, mOpacity * 255 ) / 255.0;
    }
    if ( mAlphaBand > 0 )
    {
      currentOpacity *= alphaBlock->value( i ) / 255.0;
    }

    if ( qgsDoubleNear( currentOpacity, 1.0 ) )
    {
      outputBlock->setColor( i, qRgba( redVal, greenVal, blueVal, 255 ) );
    }
    else
    {
      outputBlock->setColor( i, qRgba( currentOpacity * redVal, currentOpacity * greenVal, currentOpacity * blueVal, currentOpacity * 255 ) );
    }
  }

  //delete input blocks
  QMap<int, QgsRasterBlock *>::const_iterator bandDelIt = bandBlocks.constBegin();
  for ( ; bandDelIt != bandBlocks.constEnd(); ++bandDelIt )
  {
    delete bandDelIt.value();
  }

  return outputBlock.release();
}