예제 #1
0
void QgsMapCanvas::readProject( const QDomDocument & doc )
{
  QDomNodeList nodes = doc.elementsByTagName( "mapcanvas" );
  if ( nodes.count() )
  {
    QDomNode node = nodes.item( 0 );

    QgsMapSettings tmpSettings;
    tmpSettings.readXML( node );
    setMapUnits( tmpSettings.mapUnits() );
    setCrsTransformEnabled( tmpSettings.hasCrsTransformEnabled() );
    setDestinationCrs( tmpSettings.destinationCrs() );
    setExtent( tmpSettings.extent() );
    setRotation( tmpSettings.rotation() );
    mSettings.datumTransformStore() = tmpSettings.datumTransformStore();

    clearExtentHistory(); // clear the extent history on project load
  }
  else
  {
    QgsDebugMsg( "Couldn't read mapcanvas information from project" );
  }
}
예제 #2
0
void QgsDecorationNorthArrow::render( const QgsMapSettings &mapSettings, QgsRenderContext &context )
{

  //Large IF statement controlled by enable checkbox
  if ( enabled() )
  {
    QSize size( 64, 64 );
    QSvgRenderer svg;

    const QByteArray &svgContent = QgsApplication::svgCache()->svgContent( QStringLiteral( ":/images/north_arrows/default.svg" ), size.width(), mColor, mOutlineColor, 1.0, 1.0 );
    svg.load( svgContent );

    if ( svg.isValid() )
    {
      double centerXDouble = size.width() / 2.0;
      double centerYDouble = size.width() / 2.0;

      //save the current canvas rotation
      context.painter()->save();
      //
      //work out how to shift the image so that it rotates
      //           properly about its center
      //(x cos a + y sin a - x, -x sin a + y cos a - y)
      //

      // could move this call to somewhere else so that it is only
      // called when the projection or map extent changes
      if ( mAutomatic )
      {
        mRotationInt = QgsBearingUtils:: bearingTrueNorth( mapSettings.destinationCrs(), context.extent().center() );
        mRotationInt += mapSettings.rotation();
      }

      double myRadiansDouble = mRotationInt * M_PI / 180.0;
      int xShift = static_cast<int>( (
                                       ( centerXDouble * cos( myRadiansDouble ) ) +
                                       ( centerYDouble * sin( myRadiansDouble ) )
                                     ) - centerXDouble );
      int yShift = static_cast<int>( (
                                       ( -centerXDouble * sin( myRadiansDouble ) ) +
                                       ( centerYDouble * cos( myRadiansDouble ) )
                                     ) - centerYDouble );

      // need width/height of paint device
      int myHeight = context.painter()->device()->height();
      int myWidth = context.painter()->device()->width();

      //QgsDebugMsg("Rendering north arrow at " + mPlacementLabels.at(mPlacementIndex));

      // Set  margin according to selected units
      int myXOffset = 0;
      int myYOffset = 0;
      switch ( mMarginUnit )
      {
        case QgsUnitTypes::RenderMillimeters:
        {
          int myPixelsInchX = context.painter()->device()->logicalDpiX();
          int myPixelsInchY = context.painter()->device()->logicalDpiY();
          myXOffset = myPixelsInchX * INCHES_TO_MM * mMarginHorizontal;
          myYOffset = myPixelsInchY * INCHES_TO_MM * mMarginVertical;
          break;
        }

        case QgsUnitTypes::RenderPixels:
          myXOffset = mMarginHorizontal - 5; // Minus 5 to shift tight into corner
          myYOffset = mMarginVertical - 5;
          break;

        case QgsUnitTypes::RenderPercentage:
          myXOffset = ( ( myWidth - size.width() ) / 100. ) * mMarginHorizontal;
          myYOffset = ( ( myHeight - size.width() ) / 100. ) * mMarginVertical;
          break;

        default:  // Use default of top left
          break;
      }
      //Determine placement of label from form combo box
      switch ( mPlacement )
      {
        case BottomLeft:
          context.painter()->translate( myXOffset, myHeight - myYOffset - size.width() );
          break;
        case TopLeft:
          context.painter()->translate( myXOffset, myYOffset );
          break;
        case TopRight:
          context.painter()->translate( myWidth - myXOffset - size.width(), myYOffset );
          break;
        case BottomRight:
          context.painter()->translate( myWidth - myXOffset - size.width(),
                                        myHeight - myYOffset - size.width() );
          break;
        default:
        {
          //QgsDebugMsg("Unable to determine where to put north arrow so defaulting to top left");
        }
      }

      //rotate the canvas by the north arrow rotation amount
      context.painter()->rotate( mRotationInt );
      //Now we can actually do the drawing, and draw a smooth north arrow even when rotated

      context.painter()->translate( xShift, yShift );
      svg.render( context.painter(), QRectF( 0, 0, size.width(), size.height() ) );

      //unrotate the canvas again
      context.painter()->restore();
    }
    else
    {
      QFont myQFont( QStringLiteral( "time" ), 12, QFont::Bold );
      context.painter()->setFont( myQFont );
      context.painter()->setPen( Qt::black );
      context.painter()->drawText( 10, 20, tr( "North arrow pixmap not found" ) );
    }
  }

}
예제 #3
0
void QgsDecorationNorthArrow::render( const QgsMapSettings &mapSettings, QgsRenderContext &context )
{
  if ( !enabled() )
    return;

  double maxLength = mSize * mapSettings.outputDpi() / 25.4;
  QSvgRenderer svg;

  const QByteArray &svgContent = QgsApplication::svgCache()->svgContent( svgPath(), maxLength, mColor, mOutlineColor, 1.0, 1.0 );
  svg.load( svgContent );

  if ( svg.isValid() )
  {
    QSize size( maxLength, maxLength );
    QRectF viewBox = svg.viewBoxF();
    if ( viewBox.height() > viewBox.width() )
    {
      size.setWidth( maxLength * viewBox.width() / viewBox.height() );
    }
    else
    {
      size.setHeight( maxLength * viewBox.height() / viewBox.width() );
    }

    double centerXDouble = size.width() / 2.0;
    double centerYDouble = size.height() / 2.0;

    //save the current canvas rotation
    context.painter()->save();
    //
    //work out how to shift the image so that it rotates
    //           properly about its center
    //(x cos a + y sin a - x, -x sin a + y cos a - y)
    //
    // could move this call to somewhere else so that it is only
    // called when the projection or map extent changes
    if ( mAutomatic )
    {
      try
      {
        mRotationInt = QgsBearingUtils:: bearingTrueNorth( mapSettings.destinationCrs(), mapSettings.transformContext(), context.extent().center() );
      }
      catch ( QgsException & )
      {
        mRotationInt = 0.0;
      }
      mRotationInt += mapSettings.rotation();
    }

    double radiansDouble = mRotationInt * M_PI / 180.0;
    int xShift = static_cast<int>( (
                                     ( centerXDouble * std::cos( radiansDouble ) ) +
                                     ( centerYDouble * std::sin( radiansDouble ) )
                                   ) - centerXDouble );
    int yShift = static_cast<int>( (
                                     ( -centerXDouble * std::sin( radiansDouble ) ) +
                                     ( centerYDouble * std::cos( radiansDouble ) )
                                   ) - centerYDouble );
    // need width/height of paint device
    int deviceHeight = context.painter()->device()->height();
    int deviceWidth = context.painter()->device()->width();

    // Set  margin according to selected units
    int xOffset = 0;
    int yOffset = 0;
    switch ( mMarginUnit )
    {
      case QgsUnitTypes::RenderMillimeters:
      {
        int pixelsInchX = context.painter()->device()->logicalDpiX();
        int pixelsInchY = context.painter()->device()->logicalDpiY();
        xOffset = pixelsInchX * INCHES_TO_MM * mMarginHorizontal;
        yOffset = pixelsInchY * INCHES_TO_MM * mMarginVertical;
        break;
      }

      case QgsUnitTypes::RenderPixels:
        xOffset = mMarginHorizontal - 5; // Minus 5 to shift tight into corner
        yOffset = mMarginVertical - 5;
        break;

      case QgsUnitTypes::RenderPercentage:
        xOffset = ( ( deviceWidth - size.width() ) / 100. ) * mMarginHorizontal;
        yOffset = ( ( deviceHeight - size.width() ) / 100. ) * mMarginVertical;
        break;
      case QgsUnitTypes::RenderMapUnits:
      case QgsUnitTypes::RenderPoints:
      case QgsUnitTypes::RenderInches:
      case QgsUnitTypes::RenderUnknownUnit:
      case QgsUnitTypes::RenderMetersInMapUnits:
        break;
    }
    //Determine placement of label from form combo box
    switch ( mPlacement )
    {
      case BottomLeft:
        context.painter()->translate( xOffset, deviceHeight - yOffset - maxLength + ( maxLength - size.height() ) / 2 );
        break;
      case TopLeft:
        context.painter()->translate( xOffset, yOffset );
        break;
      case TopRight:
        context.painter()->translate( deviceWidth - xOffset - maxLength + ( maxLength - size.width() ) / 2, yOffset );
        break;
      case BottomRight:
        context.painter()->translate( deviceWidth - xOffset - maxLength + ( maxLength - size.width() ) / 2,
                                      deviceHeight - yOffset - maxLength + ( maxLength - size.height() ) / 2 );
        break;
    }

    //rotate the canvas by the north arrow rotation amount
    context.painter()->rotate( mRotationInt );
    //Now we can actually do the drawing, and draw a smooth north arrow even when rotated
    context.painter()->translate( xShift, yShift );
    svg.render( context.painter(), QRectF( 0, 0, size.width(), size.height() ) );

    //unrotate the canvas again
    context.painter()->restore();
  }
}