如何防止 QChartView 缩放到负的 x 或 y 轴值

3
我希望防止QChartView缩放到负x或y轴值。因此,我试图在我的QChartView子类中拦截mouseReleaseEvent,然后在执行缩放之前修改rubberBandRect的坐标。但是,似乎在鼠标释放后,rubberBandRect坐标始终为零,因此我认为我没有使用正确的rubberBandRect。
我正在尝试根据QChartView文档进行调整(已加重):
void QChartView :: mouseReleaseEvent(QMouseEvent * event)
如果释放了左鼠标按钮并启用了橡皮筋,则接受事件event并将视图缩放到由橡皮筋指定的矩形中。
当我尝试查看下面代码片段中rubberBandRect的实际值时,无论我如何使用光标缩放,矩形的x / y和高度/宽度值始终为零。
我也看了这个问题的答案:Qt如何连接rubberBandChanged信号,但是在那个情况下,他们想要在主窗口中实现这个功能,这不是我想要的。谢谢!
class MyQChartView : public QtCharts::QChartView
{
    Q_OBJECT
public:
    MyQChartView(QWidget *parent = 0);
    //...
protected:
    void mouseReleaseEvent(QMouseEvent *event);
    void keyPressEvent(QKeyEvent *event);

};


void MyQChartView::mouseReleaseEvent(QMouseEvent *event)
{
    
    //always shows zeroes for the x and y position
    if(event->button() == Qt::LeftButton){
        std::cout << "x: " << this->rubberBandRect().x() << " y: " << this->rubberBandRect().y() << std::endl;
        
        QChartView::mouseReleaseEvent(event);
    }
    
    //any other event
    QChartView::mouseReleaseEvent(event);
}

rubberBand() 函数返回什么?你是否使用 setRubberBand 将其设置为非 NoRubberBand 的值? - Maxim Skvortsov
@MaximSkvortsov 橡皮筋设置为矩形橡皮筋(未在上面的片段中显示)。 - qDibeX7NB
如果是这样,请查看源代码:https://code.woboq.org/qt5/qtcharts/src/charts/qchartview.cpp.html#_ZN8QtCharts10QChartView17mouseReleaseEventEP11QMouseEvent 必须设置为适当的值。 - Maxim Skvortsov
1个回答

3
经过大量实验,我认为我找到了最佳解决方法。需要制作一个rubberBand指针然后使用findChild获取实际的rubberband。鼠标释放后,我获取图形区域坐标以及rubberband坐标。接下来我制作了一个边界框(bounded_geometry),如果rubberband超出边界,则限制其值。然后我对bounded geometry box进行缩放操作zoomIn。仅修改rubberband无法起作用,因为这些坐标不是浮点数,舍入误差会导致错误的缩放。
class MyQChartView : public QtCharts::QChartView
{
    Q_OBJECT
public:
    MyQChartView(QWidget *parent = 0):
    QChartView(parent)
    {
        myChart = new QtCharts::QChart();
        setRubberBand(QtCharts::QChartView::RectangleRubberBand);
        rubberBandPtr = this->findChild<QRubberBand *>();
        this->setChart(myChart);
        //...other things
    }
    //...
protected:
    void mouseReleaseEvent(QMouseEvent *event);
    void keyPressEvent(QKeyEvent *event);
private:
    QRubberBand * rubberBandPtr;
    QtCharts::QChart * myChart;
};


void MyQChartView::mouseReleaseEvent(QMouseEvent *event)
{
    if(event->button() == Qt::LeftButton){
        //first get the plot area and save the needed values (could change each time)
        QRectF plotArea = myChart->plotArea();
        qreal xbound = plotArea.x(); //values < xbound are out of bounds on x axis
        qreal ybound = plotArea.y() + plotArea.height(); // !!! note that values > ybound are out of bounds (i.e. negative y values)
        
        QPointF rb_tl = rubberBandPtr->geometry().topLeft();
        QPointF rb_br = rubberBandPtr->geometry().bottomRight();
        
        QRectF bounded_geometry = rubberBandPtr->geometry();
        
        if(rb_tl.x() < xbound){
            bounded_geometry.setX(xbound);
        }
        if(rb_br.y() > ybound){ //note that values > ybound are out of bounds
            bounded_geometry.setBottom(ybound);
        }
        
        myChart->zoomIn(bounded_geometry);        
        rubberBandPtr->close();

        return;
    }
    
    //any other event
    QChartView::mouseReleaseEvent(event);
}

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接