Пример #1
0
bool ArcObjectImp::hit(LocationType pixelCoord) const
{
    int iStart = static_cast<int>(getStartAngle());
    if (iStart < 0)
    {
        iStart--;
    }

    int iStop = static_cast<int>(getStopAngle());
    if (iStop < 0)
    {
        iStop--;
    }

    if (iStart == iStop)
    {
        iStart = 0;
        iStop = 360;
    }

    ArcRegion eArcRegion = getArcRegion();

    DrawUtil::initializeCircle();
    LocationType center = getCenter();

    bool bHit = false;

    // Filled area
    FillStyle eFillStyle = getFillStyle();
    if (eFillStyle != EMPTY_FILL)
    {
        int iSize = abs(iStop - iStart) + 1;
        if (eArcRegion == ARC_CENTER)
        {
            iSize += 2;
        }
        else if (eArcRegion == ARC_CHORD)
        {
            iSize += 1;
        }

        double* pXVertices = new double[iSize];
        double* pYVertices = new double[iSize];

        int i = 0;
        int iIndex = 0;
        for (i = iStart, iIndex = 0; i <= iStop; i++, iIndex++)
        {
            LocationType arcPoint = getLocation(static_cast<double>(i));
            pXVertices[iIndex] = arcPoint.mX;
            pYVertices[iIndex] = arcPoint.mY;
        }

        if ((eArcRegion == ARC_CENTER) || (eArcRegion == ARC_CHORD))
        {
            if (eArcRegion == ARC_CENTER)
            {
                pXVertices[iSize - 2] = center.mX;
                pYVertices[iSize - 2] = center.mY;
            }

            pXVertices[iSize - 1] = pXVertices[0];
            pYVertices[iSize - 1] = pYVertices[0];
        }

        bHit = DrawUtil::isWithin(pixelCoord.mX, pixelCoord.mY, pXVertices, pYVertices, iSize);

        delete [] pXVertices;
        delete [] pYVertices;
    }

    // Line
    if (bHit == false)
    {
        bool bLine = false;
        bLine = getLineState();
        if (bLine == true)
        {
            // Check the arc line
            double size = 1.0;

            GraphicLayer* pLayer = NULL;
            pLayer = getLayer();
            if (pLayer != NULL)
            {
                View* pView = pLayer->getView();
                if (pView != NULL)
                {
                    size = pView->getPixelSize(center, center);
                }

                size *= min(pLayer->getXScaleFactor(), pLayer->getYScaleFactor());
            }

            LocationType basePoint;
            for (int i = iStart; i <= iStop; i++)
            {
                LocationType currentPoint = getLocation(static_cast<double>(i));
                if (i != iStart)
                {
                    bHit = DrawUtil::lineHit(currentPoint, basePoint, pixelCoord, 2.0/size);
                    if (bHit == true)
                    {
                        break;
                    }
                }

                basePoint.mX = currentPoint.mX;
                basePoint.mY = currentPoint.mY;
            }

            // Check the arc region lines
            if (bHit == false)
            {
                LocationType startPoint = getLocation(static_cast<double>(iStart));
                LocationType stopPoint = getLocation(static_cast<double>(iStop));

                if (eArcRegion == ARC_CENTER)
                {
                    bHit = DrawUtil::lineHit(startPoint, center, pixelCoord, 2.0/size);
                    if (bHit == false)
                    {
                        bHit = DrawUtil::lineHit(stopPoint, center, pixelCoord, 2.0/size);
                    }
                }
                else if (eArcRegion == ARC_CHORD)
                {
                    bHit = DrawUtil::lineHit(startPoint, stopPoint, pixelCoord, 2.0/size);
                }
            }
        }
    }

    return bHit;
}
Пример #2
0
void TextObjectImp::updateBoundingBox()
{
   // Get the width and height of the bounding box in screen pixels based on the scaled text image size
   int iWidth = 0;
   int iHeight = 0;

   string text = getSubstitutedText();
   if (text.empty() == false)
   {
      QString strMessage = QString::fromStdString(text);
      QFont scaledFont = getScaledFont();

      int iMaxSize = 0;
      glGetIntegerv(GL_MAX_TEXTURE_SIZE, &iMaxSize);

      int iAlignment = getTextAlignment();

      QFontMetrics ftMetrics(scaledFont);
      QRect boundingBox = ftMetrics.boundingRect(0, 0, iMaxSize, iMaxSize,
         iAlignment | Qt::TextWordWrap, strMessage);

      iWidth = boundingBox.width();
      iHeight = boundingBox.height();
   }

   // Get the current bounding box
   LocationType llCorner = getLlCorner();
   LocationType urCorner = getUrCorner();

   // Use the lower left corner as the anchor and compute the data coordinate of the upper right corner
   GraphicLayer* pLayer = getLayer();
   if (pLayer != NULL)
   {
      // Compute the upper right coordinate
      PerspectiveView* pView = dynamic_cast<PerspectiveView*>(pLayer->getView());
      if (pView != NULL)
      {
         double zoomFactor = 100.0 / pView->getZoomPercentage();
         double xScale = zoomFactor / pLayer->getXScaleFactor();
         double yScale = zoomFactor / pLayer->getYScaleFactor();

         urCorner.mX = llCorner.mX + (iWidth * xScale);
         urCorner.mY = llCorner.mY + (iHeight * yScale);
      }

      if (dynamic_cast<OrthographicView*>(pLayer->getView()) != NULL)
      {
         double dScreenX = 0.0;
         double dScreenY = 0.0;
         pLayer->translateDataToScreen(llCorner.mX, llCorner.mY, dScreenX, dScreenY);
         pLayer->translateScreenToData(dScreenX + iWidth, dScreenY + iHeight, urCorner.mX, urCorner.mY);
      }
   }
   else
   {
      urCorner.mX = llCorner.mX + iWidth;
      urCorner.mY = llCorner.mY + iHeight;
   }

   // Update the bounding box and selection handles
   setBoundingBox(llCorner, urCorner);
   updateHandles();

   mUpdateBoundingBox = false;
}
Пример #3
0
bool EllipseObjectImp::hit(LocationType pixelCoord) const
{ 
   LocationType llCorner = getLlCorner();
   LocationType urCorner = getUrCorner();

   double xVertices[DrawUtil::VERTEX_COUNT + 1];
   double yVertices[DrawUtil::VERTEX_COUNT + 1];
   DrawUtil::initializeCircle();

   LocationType center;
   center.mX = (llCorner.mX + urCorner.mX) / 2.0;
   center.mY = (llCorner.mY + urCorner.mY) / 2.0;

   LocationType radii;
   radii.mX = fabs (llCorner.mX - urCorner.mX) / 2.0;
   radii.mY = fabs (llCorner.mY - urCorner.mY) / 2.0;

   int i = 0;
   for (i = 0; i < DrawUtil::VERTEX_COUNT; i++)
   {
      xVertices[i] = center.mX + radii.mX * DrawUtil::sCirclePoints[i].mX;
      yVertices[i] = center.mY + radii.mY * DrawUtil::sCirclePoints[i].mY;
   }

   xVertices[DrawUtil::VERTEX_COUNT] = xVertices[0];
   yVertices[DrawUtil::VERTEX_COUNT] = yVertices[0];

   bool bHit = false;

   // Filled area
   FillStyle eFillStyle = getFillStyle();
   if (eFillStyle != EMPTY_FILL)
   {
      bHit = DrawUtil::isWithin(pixelCoord.mX, pixelCoord.mY, xVertices, yVertices, DrawUtil::VERTEX_COUNT+1);
   }

   // Line
   if (bHit == false)
   {
      bool bLine = false;
      bLine = getLineState();
      if (bLine == true)
      {
         double size = 1.0;

         GraphicLayer* pLayer = NULL;
         pLayer = getLayer();
         if (pLayer != NULL)
         {
            View* pView = pLayer->getView();
            if (pView != NULL)
            {
               size = pView->getPixelSize(llCorner, urCorner);
            }
            size *= min(pLayer->getXScaleFactor(), pLayer->getYScaleFactor());
         }

         LocationType basePoint;
         for (i = 0; i < DrawUtil::VERTEX_COUNT; i++)
         {
            LocationType currentPoint(xVertices[i], yVertices[i]);

            if (i != 0)
            {
               bHit = DrawUtil::lineHit(currentPoint, basePoint, pixelCoord, 2.0/size);
               if (bHit == true)
               {
                  break;
               }
            }

            basePoint = currentPoint;
         }
      }
   }

   return bHit;
}