这里是新的 Qt 用户(也不是狂热的 C++ 程序员,如果我的术语不准确,请见谅)。我正在学习如何开发自己的数字仪表盘。我已经设法使用 QQuickPaintedItem 创建了我自己的图形对象(水平条形图)。我还设法通过网络将这些对象连接到我自己定制设计的 ECU。
我想在水平条形图中添加一个“onClicked”事件,以便在用户单击/按下对象时显示一个新窗口(QWidget?)。这个新窗口将显示水平条形图所关联的各个设备的配置参数。我的意图是设计一个针对压力、温度等设备的通用 QML 窗口。例如,按下“Oil Temp”、“Intake Air Temp”或“Coolant Temp”对象将带您进入温度设备的通用 QML 窗口,并且将显示按下的任何设备的参数。
我有几个问题如下:
如何向水平条形图添加“onClicked”事件?我假设我需要使用MouseEvents,但是,在我的情况下,鼠标事件的确切实现正在逃避我。我假设一旦注册了点击事件,我就可以发送一个信号来打开我的新窗口。示例将非常有帮助。
我应该使用 QWidget 打开新窗口,还是有更好的选择?我希望新窗口完全取代主窗口。当新窗口打开时,我也不希望主窗口在后台发送/接收网络请求。你能指点我的任何例子吗?
水平条形图.cpp
#include "horizontalBarGraph.h"
HorizontalBarGraph::HorizontalBarGraph(QQuickItem *parent)
:QQuickPaintedItem(parent),
_horizontalBarGraphWidth(266),
_minValue(0),
_maxValue(100),
_actualValue(50),
_sensorName("Sensor Name"),
_units("Units"),
_llEnabled(true),
_llValue(20),
_lEnabled(true),
_lValue(40),
_hhEnabled(true),
_hhValue(80),
_hEnabled(true),
_hValue(60)
{
}
void HorizontalBarGraph::paint(QPainter *painter)
{
QRectF rect = this->boundingRect();
painter->setRenderHint(QPainter::Antialiasing);
QPen pen = painter->pen();
pen.setCapStyle(Qt::FlatCap);
QFont bottomFont("Arial", 14, QFont::Bold);
QFont topFont("Arial", 16, QFont::Bold);
QColor yellow(245, 225, 27);
QColor red(226, 32, 40);
QColor blue(71, 92, 167);
QColor gray192(192, 192, 192);
QColor gray212(212, 212, 212);
QColor gray224(224, 224, 224);
//minValue, actualValue, maxValue
painter->save();
painter->setFont(bottomFont);
pen.setColor(gray224);
painter->setPen(pen);
painter->drawText(rect.adjusted(0, _horizontalBarGraphHeight - _yBarChart2, _widthValue - _horizontalBarGraphWidth, 0), Qt::AlignHCenter | Qt::AlignTop, QString::number((_minValue), 'f', 0)); //Draws minValue
painter->drawText(rect.adjusted(_horizontalBarGraphWidth - _widthValue, _horizontalBarGraphHeight - _yBarChart2, 0, 0), Qt::AlignHCenter | Qt::AlignTop, QString::number((_maxValue), 'f', 0)); //Draws maxValue
painter->drawText(rect.adjusted(0, _horizontalBarGraphHeight - _yBarChart2, 0, 0), Qt::AlignHCenter | Qt::AlignTop, QString::number((_actualValue), 'f', 1)); //Draws actualValue
painter->restore();
//Bar chart background
painter->save();
painter->fillRect(rect.adjusted(_xBarChart, _yBarChart1, -_xBarChart, -_yBarChart2), gray224);
painter->restore();
//Lo
painter->save();
if(_lEnabled)
{
_scaleOutput = scale(_lValue, _minValue, _maxValue, _xBarChart, _horizontalBarGraphWidth - _xBarChart);
if(_actualValue <= _lValue)
{
painter->fillRect(rect.adjusted(_xBarChart, _yBarChart1, _scaleOutput - _horizontalBarGraphWidth, -_yBarChart2), yellow);
} else
{
painter->fillRect(rect.adjusted(_xBarChart, _yBarChart1, _scaleOutput - _horizontalBarGraphWidth, -_yBarChart2), gray212);
}
}
painter->restore();
//LoLo
painter->save();
if(_llEnabled)
{
_scaleOutput = scale(_llValue, _minValue, _maxValue, _xBarChart, _horizontalBarGraphWidth - _xBarChart);
if(_actualValue <= _llValue)
{
painter->fillRect(rect.adjusted(_xBarChart, _yBarChart1, _scaleOutput - _horizontalBarGraphWidth, -_yBarChart2), red);
} else
{
painter->fillRect(rect.adjusted(_xBarChart, _yBarChart1, _scaleOutput - _horizontalBarGraphWidth, -_yBarChart2), gray192);
}
}
painter->restore();
//Hi
painter->save();
if(_hEnabled)
{
_scaleOutput = scale(_hValue, _minValue, _maxValue, _xBarChart, _horizontalBarGraphWidth - _xBarChart);
if(_actualValue >= _hValue)
{
painter->fillRect(rect.adjusted(_scaleOutput, _yBarChart1, -_xBarChart, -_yBarChart2), yellow);
} else
{
painter->fillRect(rect.adjusted(_scaleOutput, _yBarChart1, -_xBarChart, -_yBarChart2), gray212);}
}
painter->restore();
//HiHi
painter->save();
if(_hhEnabled)
{
_scaleOutput = scale(_hhValue, _minValue, _maxValue, _xBarChart, _horizontalBarGraphWidth - _xBarChart);
if(_actualValue >= _hhValue)
{
painter->fillRect(rect.adjusted(_scaleOutput, _yBarChart1, -_xBarChart, -_yBarChart2), red);
} else
{
painter->fillRect(rect.adjusted(_scaleOutput, _yBarChart1, -_xBarChart, -_yBarChart2), gray192);}
}
painter->restore();
//Sensor name, Units
painter->save();
painter->setFont(topFont);
pen.setColor(gray224);
painter->setPen(pen);
painter->drawText(rect.adjusted(_xBarChart, 0, 0, -_horizontalBarGraphHeight + _yBarChart1 - _heightBarChart / 2), Qt::AlignLeft | Qt::AlignBottom, _sensorName); //Draws sensor name
painter->drawText(rect.adjusted(0, 0, -_xBarChart, -_horizontalBarGraphHeight + _yBarChart1 - _heightBarChart / 2), Qt::AlignRight | Qt::AlignBottom, _units); //Draws units
painter->restore();
//Arrow
painter->save();
QPainterPath path;
_scaleOutput = scale(_actualValue, _minValue, _maxValue, _xBarChart, _horizontalBarGraphWidth - _xBarChart);
path.moveTo(_scaleOutput - _heightBarChart / 2, _yBarChart1 - _heightBarChart / 2);
path.lineTo(_scaleOutput + _heightBarChart / 2, _yBarChart1 - _heightBarChart / 2);
path.lineTo(_scaleOutput, _yBarChart1 + _heightBarChart / 2);
path.closeSubpath();
painter->fillPath(path, blue);
painter->restore();
//Bounding box
painter->save();
_drawBoundingBox = false;
if(_llEnabled && _actualValue <= _llValue)
{
_drawBoundingBox = true;
_boundingBoxColor = red;
} else if (_lEnabled && _actualValue <= _lValue)
{
_drawBoundingBox = true;
_boundingBoxColor = yellow;
} else if (_hhEnabled && _actualValue >= _hhValue)
{
_drawBoundingBox = true;
_boundingBoxColor = red;
} else if (_hEnabled && _actualValue >= _hValue)
{
_drawBoundingBox = true;
_boundingBoxColor = yellow;
}
if(_drawBoundingBox && _boundingBoxFlash)
{
pen.setColor(_boundingBoxColor);
pen.setWidthF(_boundingBoxStrokeWidth);
painter->setPen(pen);
painter->drawRect(rect.adjusted(0, 0, 0, 0));
}
painter->restore();
}
qreal HorizontalBarGraph::getHorizontalBarGraphWidth()
{
return _horizontalBarGraphWidth;
}
qreal HorizontalBarGraph::getHorizontalBarGraphHeight()
{
return _horizontalBarGraphHeight;
}
qreal HorizontalBarGraph::getMinValue()
{
return _minValue;
}
qreal HorizontalBarGraph::getMaxValue()
{
return _maxValue;
}
qreal HorizontalBarGraph::getActualValue()
{
return _actualValue;
}
QString HorizontalBarGraph::getSensorName()
{
return _sensorName;
}
QString HorizontalBarGraph::getUnits()
{
return _units;
}
bool HorizontalBarGraph::isLlEnabled()
{
return _llEnabled;
}
qreal HorizontalBarGraph::getLlValue()
{
return _llValue;
}
bool HorizontalBarGraph::isLEnabled()
{
return _lEnabled;
}
qreal HorizontalBarGraph::getLValue()
{
return _lValue;
}
bool HorizontalBarGraph::isHEnabled()
{
return _hEnabled;
}
qreal HorizontalBarGraph::getHValue()
{
return _hValue;
}
bool HorizontalBarGraph::isHhEnabled()
{
return _hhEnabled;
}
qreal HorizontalBarGraph::getHhValue()
{
return _hhValue;
}
bool HorizontalBarGraph::isBoundingBoxFlashing()
{
return _boundingBoxFlash;
}
void HorizontalBarGraph::setHorizontalBarGraphWidth(qreal width)
{
if(_horizontalBarGraphWidth == width)
return;
_horizontalBarGraphWidth = width;
update();
emit widthChanged();
}
void HorizontalBarGraph::setHorizontalBarGraphHeight(qreal height)
{
if(_horizontalBarGraphHeight == height)
return;
//This object was designed to have a constant height. This method is technically not needed,
//but qt appears to require it.
//_horizontalBarGraphHeight = height;
//update();
//emit heightChanged();
}
void HorizontalBarGraph::setMinValue(qreal minValue)
{
if(_minValue == minValue)
return;
_minValue = minValue;
update();
emit minValueChanged();
}
void HorizontalBarGraph::setMaxValue(qreal maxValue)
{
if(_maxValue == maxValue)
return;
_maxValue = maxValue;
update();
emit maxValueChanged();
}
void HorizontalBarGraph::setActualValue(qreal actualValue)
{
if(_actualValue == actualValue)
return;
_actualValue = actualValue;
update();
emit actualValueChanged();
}
void HorizontalBarGraph::setSensorName(QString sensorName)
{
if(_sensorName == sensorName)
return;
_sensorName = sensorName;
update();
emit sensorNameChanged();
}
void HorizontalBarGraph::setUnits(QString units)
{
if(_units == units)
return;
_units = units;
update();
emit unitsChanged();
}
void HorizontalBarGraph::enableLl(bool llEnabled)
{
if(_llEnabled == llEnabled)
return;
_llEnabled = llEnabled;
update();
emit enableLlChanged();
}
void HorizontalBarGraph::setLlValue(qreal llValue)
{
if(_llValue == llValue)
return;
_llValue = llValue;
update();
emit llValueChanged();
}
void HorizontalBarGraph::enableL(bool lEnabled)
{
if(_lEnabled == lEnabled)
return;
_lEnabled = lEnabled;
update();
emit enableLChanged();
}
void HorizontalBarGraph::setLValue(qreal lValue)
{
if(_lValue == lValue)
return;
_lValue = lValue;
update();
emit lValueChanged();
}
void HorizontalBarGraph::enableH(bool hEnabled)
{
if(_hEnabled == hEnabled)
return;
_hEnabled = hEnabled;
update();
emit enableHChanged();
}
void HorizontalBarGraph::setHValue(qreal hValue)
{
if(_hValue == hValue)
return;
_hValue = hValue;
update();
emit hValueChanged();
}
void HorizontalBarGraph::enableHh(bool hhEnabled)
{
if(_hhEnabled == hhEnabled)
return;
_hhEnabled = hhEnabled;
update();
emit enableHhChanged();
}
void HorizontalBarGraph::setHhValue(qreal hhValue)
{
if(_hhValue == hhValue)
return;
_hhValue = hhValue;
update();
emit hhValueChanged();
}
void HorizontalBarGraph::setBoundingBoxFlash(bool flash)
{
if(_boundingBoxFlash == flash)
return;
_boundingBoxFlash = flash;
update();
emit boundingBoxFlashChanged();
}
qreal HorizontalBarGraph::scale(qreal input, qreal inputMin, qreal inputMax, qreal outputMin, qreal outputMax)
{
qreal output = (outputMax - outputMin) * (input - inputMin) / (inputMax - inputMin) + outputMin;
if(output > outputMax)
output = outputMax;
if(output < outputMin)
output = outputMin;
return output;
}
水平条形图.h
#ifndef HORIZONTALBARGRAPH_H
#define HORIZONTALBARGRAPH_H
#include <QObject>
#include <QQuickPaintedItem>
#include <QPainter>
class HorizontalBarGraph : public QQuickPaintedItem
{
Q_OBJECT
Q_PROPERTY(qreal horizontalBarGraphWidth READ getHorizontalBarGraphWidth WRITE setHorizontalBarGraphWidth NOTIFY horizontalBarGraphWidthChanged)
Q_PROPERTY(qreal horizontalBarGraphHeight READ getHorizontalBarGraphHeight WRITE setHorizontalBarGraphHeight NOTIFY horizontalBarGraphHeightChanged)
Q_PROPERTY(qreal minValue READ getMinValue WRITE setMinValue NOTIFY minValueChanged)
Q_PROPERTY(qreal maxValue READ getMaxValue WRITE setMaxValue NOTIFY maxValueChanged)
Q_PROPERTY(qreal actualValue READ getActualValue WRITE setActualValue NOTIFY actualValueChanged)
Q_PROPERTY(QString sensorName READ getSensorName WRITE setSensorName NOTIFY sensorNameChanged)
Q_PROPERTY(QString units READ getUnits WRITE setUnits NOTIFY unitsChanged)
Q_PROPERTY(bool llEnable READ isLlEnabled WRITE enableLl NOTIFY enableLlChanged)
Q_PROPERTY(qreal llValue READ getLlValue WRITE setLlValue NOTIFY llValueChanged)
Q_PROPERTY(bool lEnable READ isLEnabled WRITE enableL NOTIFY enableLChanged)
Q_PROPERTY(qreal lValue READ getLValue WRITE setLValue NOTIFY lValueChanged)
Q_PROPERTY(bool hhEnable READ isHhEnabled WRITE enableHh NOTIFY enableHhChanged)
Q_PROPERTY(qreal hhValue READ getHhValue WRITE setHhValue NOTIFY hhValueChanged)
Q_PROPERTY(bool hEnable READ isHEnabled WRITE enableH NOTIFY enableHChanged)
Q_PROPERTY(qreal hValue READ getHValue WRITE setHValue NOTIFY hValueChanged)
Q_PROPERTY(bool boundingBoxFlash READ isBoundingBoxFlashing WRITE setBoundingBoxFlash NOTIFY boundingBoxFlashChanged)
public:
HorizontalBarGraph(QQuickItem *parent = nullptr);
virtual void paint(QPainter *painter);
qreal getHorizontalBarGraphWidth();
qreal getHorizontalBarGraphHeight();
qreal getMinValue();
qreal getMaxValue();
qreal getActualValue();
QString getSensorName();
QString getUnits();
bool isLlEnabled();
qreal getLlValue();
bool isLEnabled();
qreal getLValue();
bool isHhEnabled();
qreal getHhValue();
bool isHEnabled();
qreal getHValue();
bool isBoundingBoxFlashing();
void setHorizontalBarGraphWidth(qreal width);
void setHorizontalBarGraphHeight(qreal height);
void setMinValue(qreal minValue);
void setMaxValue(qreal maxValue);
void setActualValue(qreal actualValue);
void setSensorName(QString sensorName);
void setUnits(QString units);
void enableLl(bool llEnabled);
void setLlValue(qreal llValue);
void enableL(bool lEnabled);
void setLValue(qreal lValue);
void enableHh(bool hhEnabled);
void setHhValue(qreal hhValue);
void enableH(bool hEnabled);
void setHValue(qreal hValue);
void setBoundingBoxFlash(bool flash);
signals:
void horizontalBarGraphWidthChanged();
void horizontalBarGraphHeightChanged();
void minValueChanged();
void maxValueChanged();
void actualValueChanged();
void sensorNameChanged();
void unitsChanged();
void enableLlChanged();
void llValueChanged();
void enableLChanged();
void lValueChanged();
void enableHhChanged();
void hhValueChanged();
void enableHChanged();
void hValueChanged();
void boundingBoxFlashChanged();
private:
qreal _horizontalBarGraphWidth;
qreal _horizontalBarGraphHeight = 75;
qreal _minValue;
qreal _maxValue;
qreal _actualValue;
QString _sensorName;
QString _units;
bool _llEnabled;
qreal _llValue;
bool _lEnabled;
qreal _lValue;
bool _hhEnabled;
qreal _hhValue;
bool _hEnabled;
qreal _hValue;
qreal _xBarChart = 25;
qreal _yBarChart1 = 35;
qreal _yBarChart2 = 25;
qreal _heightBarChart = _horizontalBarGraphHeight - _yBarChart1 - _yBarChart2;
qreal _widthValue = _xBarChart * 2;
qreal _scaleOutput;
qreal _boundingBoxStrokeWidth = 7.5;
bool _drawBoundingBox;
QColor _boundingBoxColor;
bool _boundingBoxFlash;
qreal scale(qreal input, qreal inputMin, qreal inputMax, qreal outputMin, qreal outputMax);
};
#endif // HORIZONTALBARGRAPH_H