⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 qwt_plot_zoomer.cpp

📁 QWT5.01用于Qt开发的二维图形库程序
💻 CPP
📖 第 1 页 / 共 2 页
字号:
  \param offset Offset relative to the current position of the zoom stack.
  \note The zoomed signal is emitted.
  \sa zoomRectIndex()
*/
void QwtPlotZoomer::zoom(int offset)
{
    if ( offset == 0 )
        d_data->zoomRectIndex = 0;
    else
    {
        int newIndex = d_data->zoomRectIndex + offset;
        newIndex = qwtMax(0, newIndex);
        newIndex = qwtMin(int(d_data->zoomStack.count()) - 1, newIndex);

        d_data->zoomRectIndex = uint(newIndex);
    }

    rescale();

    emit zoomed(zoomRect());
}

/*! 
  Adjust the observed plot to zoomRect()

  \note Initiates QwtPlot::replot
*/

void QwtPlotZoomer::rescale()
{
    QwtPlot *plt = plot();
    if ( !plt )
        return;

    const QwtDoubleRect &rect = d_data->zoomStack[d_data->zoomRectIndex];
    if ( rect != scaleRect() )
    {
        const bool doReplot = plt->autoReplot();
        plt->setAutoReplot(false);

        double x1 = rect.left();
        double x2 = rect.right();
        if ( plt->axisScaleDiv(xAxis())->lBound() > 
            plt->axisScaleDiv(xAxis())->hBound() )
        {
            qSwap(x1, x2);
        }

        plt->setAxisScale(xAxis(), x1, x2);

        double y1 = rect.top();
        double y2 = rect.bottom();
        if ( plt->axisScaleDiv(yAxis())->lBound() > 
            plt->axisScaleDiv(yAxis())->hBound() )
        {
            qSwap(y1, y2);
        }
        plt->setAxisScale(yAxis(), y1, y2);

        plt->setAutoReplot(doReplot);

        plt->replot();
    }
}

/*!
  Reinitialize the axes, and set the zoom base to their scales.

  \param xAxis X axis 
  \param yAxis Y axis
*/

void QwtPlotZoomer::setAxis(int xAxis, int yAxis)
{
    if ( xAxis != QwtPlotPicker::xAxis() || yAxis != QwtPlotPicker::yAxis() )
    {
        QwtPlotPicker::setAxis(xAxis, yAxis);
        setZoomBase(scaleRect());
    }
}

/*!
   Qt::MidButton zooms out one position on the zoom stack,
   Qt::RightButton to the zoom base.

   Changes the current position on the stack, but doesn't pop
   any rectangle.

   \note The mouse events can be changed, using
         QwtEventPattern::setMousePattern: 2, 1
*/
void QwtPlotZoomer::widgetMouseReleaseEvent(QMouseEvent *me)
{
    if ( mouseMatch(MouseSelect2, me) )
        zoom(0);
    else if ( mouseMatch(MouseSelect3, me) )
        zoom(-1);
    else if ( mouseMatch(MouseSelect6, me) )
        zoom(+1);
    else 
        QwtPlotPicker::widgetMouseReleaseEvent(me);
}

/*!
   Qt::Key_Plus zooms out, Qt::Key_Minus zooms in one position on the 
   zoom stack, Qt::Key_Escape zooms out to the zoom base.

   Changes the current position on the stack, but doesn't pop
   any rectangle.

   \note The keys codes can be changed, using
         QwtEventPattern::setKeyPattern: 3, 4, 5
*/

void QwtPlotZoomer::widgetKeyPressEvent(QKeyEvent *ke)
{
    if ( !isActive() )
    {
        if ( keyMatch(KeyUndo, ke) )
            zoom(-1);
        else if ( keyMatch(KeyRedo, ke) )
            zoom(+1);
        else if ( keyMatch(KeyHome, ke) )
            zoom(0);
    }

    QwtPlotPicker::widgetKeyPressEvent(ke);
}

/*!
  Move the current zoom rectangle.

  \param dx X offset
  \param dy Y offset

  \note The changed rectangle is limited by the zoom base
*/
void QwtPlotZoomer::moveBy(double dx, double dy)
{
    const QwtDoubleRect &rect = d_data->zoomStack[d_data->zoomRectIndex];
    move(rect.left() + dx, rect.top() + dy);
}

/*!
  Move the the current zoom rectangle.

  \param x X value
  \param y Y value

  \sa QwtDoubleRect::move
  \note The changed rectangle is limited by the zoom base
*/
void QwtPlotZoomer::move(double x, double y)
{
    if ( x < zoomBase().left() )
        x = zoomBase().left();
    if ( x > zoomBase().right() - zoomRect().width() )
        x = zoomBase().right() - zoomRect().width();

    if ( y < zoomBase().top() )
        y = zoomBase().top();
    if ( y > zoomBase().bottom() - zoomRect().height() )
        y = zoomBase().bottom() - zoomRect().height();

    if ( x != zoomRect().left() || y != zoomRect().top() )
    {
        d_data->zoomStack[d_data->zoomRectIndex].moveTo(x, y);
        rescale();
    }
}

/*!
  \brief Check and correct a selected rectangle

  Reject rectangles with a hight or width < 2, otherwise
  expand the selected rectangle to a minimum size of 11x11
  and accept it.
  
  \return true If rect is accepted, or has been changed
          to a accepted rectangle. 
*/

bool QwtPlotZoomer::accept(QwtPolygon &pa) const
{
    if ( pa.count() < 2 )
        return false;

    QRect rect = QRect(pa[0], pa[int(pa.count()) - 1]);
#if QT_VERSION < 0x040000
    rect = rect.normalize();
#else
    rect = rect.normalized();
#endif

    const int minSize = 2;
    if (rect.width() < minSize && rect.height() < minSize )
        return false; 

    const int minZoomSize = 11;

    const QPoint center = rect.center();
    rect.setSize(rect.size().expandedTo(QSize(minZoomSize, minZoomSize)));
    rect.moveCenter(center);

    pa.resize(2);
    pa[0] = rect.topLeft();
    pa[1] = rect.bottomRight();

    return true;
}

/*!
  \brief Limit zooming by a minimum rectangle

  \return zoomBase().width() / 10e4, zoomBase().height() / 10e4
*/
QwtDoubleSize QwtPlotZoomer::minZoomSize() const
{
    return QwtDoubleSize(
        d_data->zoomStack[0].width() / 10e4,
        d_data->zoomStack[0].height() / 10e4
    );
}

/*! 
  Rejects selections, when the stack depth is too deep, or
  the zoomed rectangle is minZoomSize().

  \sa minZoomSize(), maxStackDepth()
*/
void QwtPlotZoomer::begin()
{
    if ( d_data->maxStackDepth >= 0 )
    {
        if ( d_data->zoomRectIndex >= uint(d_data->maxStackDepth) )
            return;
    }

    const QwtDoubleSize minSize = minZoomSize();
    if ( minSize.isValid() )
    {
        const QwtDoubleSize sz = 
            d_data->zoomStack[d_data->zoomRectIndex].size() * 0.9999;

        if ( minSize.width() >= sz.width() &&
            minSize.height() >= sz.height() )
        {
            return;
        }
    }

    QwtPlotPicker::begin();
}

/*!
  Expand the selected rectangle to minZoomSize() and zoom in
  if accepted.

  \sa QwtPlotZoomer::accept()a, QwtPlotZoomer::minZoomSize()
*/
bool QwtPlotZoomer::end(bool ok)
{
    ok = QwtPlotPicker::end(ok);
    if (!ok)
        return false;

    QwtPlot *plot = QwtPlotZoomer::plot();
    if ( !plot )
        return false;

    const QwtPolygon &pa = selection();
    if ( pa.count() < 2 )
        return false;

    QRect rect = QRect(pa[0], pa[int(pa.count() - 1)]);
#if QT_VERSION < 0x040000
    rect = rect.normalize();
#else
    rect = rect.normalized();
#endif


    QwtDoubleRect zoomRect = invTransform(rect).normalized();

    const QwtDoublePoint center = zoomRect.center();
    zoomRect.setSize(zoomRect.size().expandedTo(minZoomSize()));
    zoomRect.moveCenter(center);

    zoom(zoomRect);

    return true;
}

/*!
  Set the selection flags
  
  \param flags Or'd value of QwtPicker::RectSelectionType and
               QwtPicker::SelectionMode. The default value is 
               QwtPicker::RectSelection & QwtPicker::ClickSelection.

  \sa selectionFlags(), SelectionType, RectSelectionType, SelectionMode
  \note QwtPicker::RectSelection will be auto added.
*/

void QwtPlotZoomer::setSelectionFlags(int flags)
{
    // we accept only rects
    flags &= ~(PointSelection | PolygonSelection);
    flags |= RectSelection;

    QwtPlotPicker::setSelectionFlags(flags);
}

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -