Qt图表绘制(QtCharts)-绘制简单的烛台图(10)🌻
更多精彩内容 |
---|
👉个人内容分类汇总 👈 |
注意:我使用的QtCharts是基于Qt 5.12.12版本 |
1、概述🍂
Qt Charts 模块提供了一组易于使用的图表组件,能够创建时尚、交互式、以数据为中心的用户界面。
它使用
Qt Graphics View
框架,因此可以轻松地将图表集成到现代用户界面中。Qt Charts 可以用作 QWidgets、QGraphicsWidget 或 QML 类型。 用户可以通过选择图表主题之一轻松创建令人印象深刻的图表。
这一个Demo干了啥:🤏🤏🤏
- 在
initChart()
函数中演示了如何使用QtCharts绘制简单的的烛台图;- Qt示例中通过继承
QTextStream
类实现读取数据功能,感觉过于复杂,为了便于学习将读取数据功能直接封装成一个getData()
函数;- 在源码中包含使用的详细注释和注意事项 ;
- 将UI和代码分离,使实现图表绘制的代码更单一简洁,便于学习。
2、实现步骤🌱
-
打开
.pro
文件,输入Qt += charts
,引入Qt Charts模块; -
打开ui设计器,选择一个
Graphics View
控件,鼠标右键提升为; -
输入
QChartView
,点击添加、提升; -
在窗口右上角就可以看见控件类型变成
QChartView
了,然后将控件命名为chartView; 注意:由于QChartView需要引入命名空间,所以这里提升后编译时不通过的。 -
在代码中添加QtCharts头文件,引入命名空间;一般我们最好在
cpp文件
中添加头文件和引入命名空间,尽量避免在.h文件
中引入(这里为了方便,代码简洁直接在头文件中引入命名空间),而在cpp文件中引入命名空间需要在ui_widget.h文件前,否则编译会失败,因为在ui文件中会用到QChartView类。#include <QtCharts> // 导入QtCharts所有的头文件,也可以单独导入某一个 // 引入qchart命名空间(注意:如果是在ui中提升为QChartView, // 则QT_CHARTS_USE_NAMESPACE一定要放在#include "ui_widget.h"前面,否则编译会失败) QT_CHARTS_USE_NAMESPACE
3、主要使用的类🌷
类名 | 作用 |
---|---|
QCandlestickSeries | 创建一个用于绘制烛台图的数据集对象 |
QCandlestickSet | 单个烛台数据对象,有打开、高、低、关闭和时间戳五个值组成 |
QBarCategoryAxis | 将类别添加到图表的轴 |
QValueAxis | 将数值添加到图表的轴 |
QPainter | 在小部件和其他绘制设备上执行低级绘制(用于绘制一个五角星图案) |
4、主要代码🌳
widget.h
文件
#ifndef WIDGET_H
#define WIDGET_H
#include <QWidget>
#include <qcandlestickset.h>
QT_BEGIN_NAMESPACE
namespace Ui { class Widget; }
QT_END_NAMESPACE
QT_CHARTS_USE_NAMESPACE // 为了便于
class Widget : public QWidget
{
Q_OBJECT
public:
Widget(QWidget *parent = nullptr);
~Widget();
private:
void initChart(); // 初始化绘制图表
QList<QCandlestickSet *> getData(); // 获取需要绘制数据
private:
Ui::Widget *ui;
};
#endif // WIDGET_H
widget.cpp
文件
#include "widget.h"
#include <QBarCategoryAxis>
#include <QCandlestickSeries>
#include <QDateTime>
#include <QValueAxis>
#include <qdebug.h>
#include "ui_widget.h"
Widget::Widget(QWidget *parent)
: QWidget(parent)
, ui(new Ui::Widget)
{
ui->setupUi(this);
this->setWindowTitle("QtCharts绘图-蜡烛图Demo");
initChart();
}
Widget::~Widget()
{
delete ui;
}
/**
* @brief 初始化绘制图表
*/
void Widget::initChart()
{
QCandlestickSeries* series = new QCandlestickSeries(); // 创建一个蜡烛图数据集对象,用于绘制蜡烛图
series->setName("今日股票走势"); // 设置名称
series->setIncreasingColor(QColor(Qt::green)); // 设置增长的烛台颜色(当烛台的关闭值高于打开值时,烛台会增加)
series->setDecreasingColor(QColor(Qt::red)); // 设置减少的烛台的颜色(当烛台的打开值高于关闭值时,烛台正在减小)
const QList<QCandlestickSet *> dataList = getData(); // 获取用于绘制烛台的数据
series->append(dataList);
ui->chartView->chart()->addSeries(series); // 将创建的烛台图数据集对象添加进chart
ui->chartView->chart()->setTitle("烛台图标题"); // 设置图表标题
ui->chartView->chart()->setAnimationOptions(QChart::SeriesAnimations); // 设置图表动画效果(会影响性能)
ui->chartView->chart()->createDefaultAxes(); // 根据已有的series生成对应类型的XY轴
ui->chartView->chart()->legend()->setVisible(true); // 显示图例
ui->chartView->chart()->legend()->setAlignment(Qt::AlignBottom); // 图例显示在图表底部
ui->chartView->setRenderHint(QPainter::Antialiasing); // 设置抗锯齿
// 获取Y轴,并将类型转换为QValueAxis
QValueAxis* axisY = qobject_cast<QValueAxis*>(ui->chartView->chart()->axes(Qt::Vertical).at(0));
axisY->applyNiceNumbers(); // 调整Y轴范围,使可用显示所有数据,便于观看
// 获取X轴,并将类型转换为QBarCategoryAxis
QBarCategoryAxis* axisX = qobject_cast<QBarCategoryAxis*>(ui->chartView->chart()->axes(Qt::Horizontal).at(0));
QStringList categories;
for(auto set : dataList)
{
QString strTime = QDateTime::fromMSecsSinceEpoch(set->timestamp()).toString("dd");
categories.append(strTime);
}
axisX->setCategories(categories); // 以数据的时间设置X轴的类别(不能重复)
}
/**
* @brief 读取文件中用来绘制图表的数据
* @return 返回所有需要绘制的数据,如果count等于0则表示没有数据
*/
QList<QCandlestickSet *> Widget::getData()
{
QList<QCandlestickSet *> dataList;
QFile file(":/acme.txt");
if(!file.open(QIODevice::ReadOnly | QIODevice::Text)) // 打开数据文件并判断是否打开失败
{
qWarning() << "打开文件失败!";
return dataList;
}
while (!file.atEnd())
{
QString line = file.readLine(); // 读取一行数据
if(line.startsWith("#") // 如果字符串以#开头,则返回true;否则返回false。
|| line.isEmpty()) // 判断是否读取到空数据
continue;
QStringList strList = line.split(" ", QString::SkipEmptyParts); // 以空格拆分字符串
if(strList.count() != 5) // 判断数据是否完整有效
continue;
const qreal timestamp = strList.at(0).toDouble();
const qreal open = strList.at(1).toDouble();
const qreal high = strList.at(2).toDouble();
const qreal low = strList.at(3).toDouble();
const qreal close = strList.at(4).toDouble();
// 创建单个烛台数据对象,有打开、高、低、关闭和时间戳五个值组成
QCandlestickSet* candlestickSet = new QCandlestickSet();
candlestickSet->setTimestamp(timestamp);
candlestickSet->setOpen(open);
candlestickSet->setHigh(high);
candlestickSet->setLow(low);
candlestickSet->setClose(close);
dataList.append(candlestickSet);
}
return dataList;
}
- 资源文件
came.txt
# Acme Ltd Historical Data (July 2015)
# timestamp, open, high, low, close
1435708800000 126.90 126.94 125.99 126.60
1435795200000 126.69 126.69 126.69 126.69
1436140800000 124.85 126.23 124.85 126.00
1436227200000 125.89 126.15 123.77 125.69
1436313600000 124.64 124.64 122.54 122.54
1436400000000 123.85 124.06 119.22 120.07
1436486400000 121.94 123.85 121.21 123.28
1436745600000 125.03 125.76 124.32 125.66
1436832000000 126.04 126.37 125.04 125.61
1436918400000 125.72 127.15 125.58 126.82
1437004800000 127.74 128.57 127.35 128.51
1437091200000 129.08 129.62 128.31 129.62
1437350400000 130.97 132.97 130.70 132.07
1437436800000 132.85 132.92 130.32 130.75
1437523200000 121.99 125.50 121.99 125.22
1437609600000 126.20 127.09 125.06 125.16
1437696000000 125.32 125.74 123.90 124.50
1437955200000 123.09 123.61 122.12 122.77
1438041600000 123.38 123.91 122.55 123.38
1438128000000 123.15 123.50 122.27 122.99
1438214400000 122.32 122.57 121.71 122.37
1438300800000 122.60 122.64 120.91 121.30
5、实现效果🌹
6、源代码🍀
👣👣👣👣👣👣👣👣👣👣👣👣