Qt-QtCharts
1. 基本概念
QtCharts 是 Qt 框架中的一个模块,提供了一套用于数据可视化的图表组件。它允许开发者轻松创建各种类型的交互式图表,集成到 Qt 应用程序中。
QtCharts 是 Qt 的图表模块,提供多种图表类型:
QLineSeries - 折线图
QAreaSeries - 面积图
QBarSeries - 柱状图
QPieSeries - 饼图
QScatterSeries - 散点图
QSplineSeries - 平滑曲线
2.案例
2.1QLineSeries - 折线图
案例:
#include "mainwindow.h"
#include "ui_mainwindow.h"MainWindow::MainWindow(QWidget *parent): QMainWindow(parent), ui(new Ui::MainWindow)
{ui->setupUi(this);// 创建折线系列QLineSeries *series = new QLineSeries();series->setName("数据趋势1");QLineSeries *series1 = new QLineSeries();series1->setName("数据趋势2");// 添加数据方式一QVector<double> xData = {0, 1, 2, 3, 4, 5, 6, 7, 8, 9};QVector<double> yData = {10.5, 15.2, 8.7, 22.1, 18.3, 25.6, 12.8, 30.4, 28.9, 35.2};for (int i = 0; i < xData.size(); ++i) {series->append(xData[i], yData[i]);}// 添加数据方式二for (int i = 0; i < 10; ++i) {series1->append(i, qSin(i) + 0.42* i);}// 创建图表QChart *chart = new QChart();chart->addSeries(series);chart->addSeries(series1);chart->createDefaultAxes();//为图表自动创建默认的坐标轴。// 获取坐标轴并设置合适的范围QValueAxis* axisX = qobject_cast<QValueAxis*>(chart->axes(Qt::Horizontal).first());QValueAxis* axisY = qobject_cast<QValueAxis*>(chart->axes(Qt::Vertical).first());if (axisX && axisY) {// 根据您的数据设置合适的坐标轴范围axisX->setRange(0, 9); // X轴从0到9// Y轴范围根据您的实际数据调整axisY->setRange(0, 40); // 设置Y轴从0到40,这样能完全显示您的数据// 可选:设置坐标轴标题axisX->setTitleText("X轴");axisY->setTitleText("Y轴");}chart->setTitle("实际数据折线图");// 创建图表视图并设置抗锯齿QChartView *chartView = new QChartView(chart);chartView->setRenderHint(QPainter::Antialiasing);// 创建布局并添加图表视图QVBoxLayout *layout = new QVBoxLayout(ui->centralwidget);layout->addWidget(chartView);
}MainWindow::~MainWindow()
{delete ui;
}
结果:

2.2QAreaSeries - 面积图
#include "mainwindow.h"
#include "ui_mainwindow.h"
#include <QRandomGenerator>
MainWindow::MainWindow(QWidget *parent): QMainWindow(parent), ui(new Ui::MainWindow)
{ui->setupUi(this);// 创建上下边界线QLineSeries *upperSeries = new QLineSeries();QLineSeries *lowerSeries = new QLineSeries();upperSeries->setName("上限");lowerSeries->setName("下限");// 添加数据点upperSeries->append(1, 20);upperSeries->append(2, 25);upperSeries->append(3, 22);upperSeries->append(4, 28);upperSeries->append(5, 26);upperSeries->append(6, 30);lowerSeries->append(1, 10);lowerSeries->append(2, 15);lowerSeries->append(3, 12);lowerSeries->append(4, 18);lowerSeries->append(5, 16);lowerSeries->append(6, 20);// 创建面积系列QAreaSeries *areaSeries = new QAreaSeries(upperSeries, lowerSeries);areaSeries->setName("数据范围");areaSeries->setColor(QColor(135, 206, 250, 100)); // 浅蓝色,半透明// 创建图表QChart *chart = new QChart();chart->addSeries(areaSeries);chart->setTitle("数据波动范围");chart->setAnimationOptions(QChart::SeriesAnimations);// 创建坐标轴chart->createDefaultAxes();chart->axisX()->setTitleText("时间");chart->axisY()->setTitleText("数值");// 显示图例chart->legend()->setVisible(true);chart->legend()->setAlignment(Qt::AlignBottom);// 创建图表视图QChartView *chartView = new QChartView(chart);chartView->setRenderHint(QPainter::Antialiasing);// 设置布局if (!ui->centralwidget->layout()) {QVBoxLayout *layout = new QVBoxLayout(ui->centralwidget);layout->addWidget(chartView);} else {ui->centralwidget->layout()->addWidget(chartView);}}MainWindow::~MainWindow()
{delete ui;
}
结果:

2.3QBarSeries - 柱状图
#include "mainwindow.h"
#include "ui_mainwindow.h"MainWindow::MainWindow(QWidget *parent): QMainWindow(parent), ui(new Ui::MainWindow)
{ui->setupUi(this);// 创建柱状系列QBarSeries *series = new QBarSeries();// 创建数据集合QBarSet *set0 = new QBarSet("第一季度");QBarSet *set1 = new QBarSet("第二季度");*set0 << 10 << 15 << 20 << 25;*set1 << 12 << 18 << 22 << 28;series->append(set0);series->append(set1);// 创建图表QChart *chart = new QChart();chart->addSeries(series);chart->setTitle("季度销售对比");chart->setAnimationOptions(QChart::SeriesAnimations);// 设置X轴类别QStringList categories;categories << "1月" << "2月" << "3月" << "4月";QBarCategoryAxis *axisX = new QBarCategoryAxis();axisX->append(categories);chart->addAxis(axisX, Qt::AlignBottom);series->attachAxis(axisX);chart->createDefaultAxes();// 创建图表视图并设置抗锯齿QChartView *chartView = new QChartView(chart);chartView->setRenderHint(QPainter::Antialiasing);// 创建布局并添加图表视图QVBoxLayout *layout = new QVBoxLayout(ui->centralwidget);layout->addWidget(chartView);
}MainWindow::~MainWindow()
{delete ui;
}
结果:

2.4QPieSeries - 饼图
#include "mainwindow.h"
#include "ui_mainwindow.h"MainWindow::MainWindow(QWidget *parent): QMainWindow(parent), ui(new Ui::MainWindow)
{ui->setupUi(this);// 创建饼图系列QPieSeries *series = new QPieSeries();series->setHoleSize(0.2); // 设置空心大小,0为实心,0.2为20%空心// 添加数据切片QPieSlice *slice1 = series->append("产品A", 30);QPieSlice *slice2 = series->append("产品B", 25);QPieSlice *slice3 = series->append("产品C", 20);QPieSlice *slice4 = series->append("产品D", 15);QPieSlice *slice5 = series->append("产品E", 10);// 设置切片颜色slice1->setColor(QColor(255, 99, 132));slice2->setColor(QColor(54, 162, 235));slice3->setColor(QColor(255, 205, 86));slice4->setColor(QColor(75, 192, 192));slice5->setColor(QColor(153, 102, 255));// 突出显示第一个切片slice1->setExploded(true);slice1->setLabelVisible(true);slice1->setLabelColor(Qt::black);// 设置所有切片标签可见for (QPieSlice *slice : series->slices()) {slice->setLabelVisible(true);slice->setLabel(slice->label() + " " + QString::number(slice->percentage() * 100, 'f', 1) + "%");}// 创建图表QChart *chart = new QChart();chart->addSeries(series);chart->setTitle("产品销售额占比");chart->legend()->setVisible(true);chart->legend()->setAlignment(Qt::AlignRight);// 创建图表视图QChartView *chartView = new QChartView(chart);chartView->setRenderHint(QPainter::Antialiasing);// 设置布局QVBoxLayout *layout = new QVBoxLayout(ui->centralwidget);layout->addWidget(chartView);}MainWindow::~MainWindow()
{delete ui;
}
结果:

2.5QScatterSeries - 散点图
#include "mainwindow.h"
#include "ui_mainwindow.h"
#include <QRandomGenerator>
MainWindow::MainWindow(QWidget *parent): QMainWindow(parent), ui(new Ui::MainWindow)
{ui->setupUi(this);// 创建散点系列QScatterSeries *series = new QScatterSeries();series->setName("数据分布");series->setMarkerSize(12.0); // 设置点的大小series->setColor(QColor(255, 0, 0)); // 红色点series->setBorderColor(QColor(0, 0, 0)); // 黑色边框series->setMarkerShape(QScatterSeries::MarkerShapeCircle); // 圆形点// 添加随机数据点for (int i = 0; i < 20; ++i) {double x = QRandomGenerator::global()->bounded(100) / 10.0; // 0.0 到 9.9double y = QRandomGenerator::global()->bounded(100) / 10.0; // 0.0 到 9.9series->append(x, y);}// 创建图表QChart *chart = new QChart();chart->addSeries(series);chart->setTitle("数据分布散点图");chart->setAnimationOptions(QChart::SeriesAnimations);// 创建坐标轴QValueAxis *axisX = new QValueAxis();axisX->setTitleText("X 轴");axisX->setRange(0, 10);QValueAxis *axisY = new QValueAxis();axisY->setTitleText("Y 轴");axisY->setRange(0, 10);chart->addAxis(axisX, Qt::AlignBottom);chart->addAxis(axisY, Qt::AlignLeft);series->attachAxis(axisX);series->attachAxis(axisY);// 显示图例chart->legend()->setVisible(true);chart->legend()->setAlignment(Qt::AlignBottom);// 创建图表视图QChartView *chartView = new QChartView(chart);chartView->setRenderHint(QPainter::Antialiasing);// 设置布局QVBoxLayout *layout = new QVBoxLayout(ui->centralwidget);layout->addWidget(chartView);}MainWindow::~MainWindow()
{delete ui;
}
结果:

2.6QSplineSeries - 平滑曲线
#include "mainwindow.h"
#include "ui_mainwindow.h"
#include <QRandomGenerator>
MainWindow::MainWindow(QWidget *parent): QMainWindow(parent), ui(new Ui::MainWindow)
{ui->setupUi(this);// 创建平滑曲线系列QSplineSeries *series = new QSplineSeries();series->setName("温度变化");// 添加数据点(使用样条插值)series->append(0, 15);series->append(2, 18);series->append(4, 16);series->append(6, 20);series->append(8, 22);series->append(10, 19);series->append(12, 24);series->append(14, 21);series->append(16, 23);series->append(18, 25);series->append(20, 22);series->append(22, 20);series->append(24, 18);// 设置线条样式series->setColor(QColor(0, 128, 0)); // 绿色线条QPen pen = series->pen();pen.setWidth(3);pen.setStyle(Qt::DashLine); // 虚线样式series->setPen(pen);// 创建图表QChart *chart = new QChart();chart->addSeries(series);chart->setTitle("24小时温度变化曲线");chart->setAnimationOptions(QChart::SeriesAnimations);// 创建坐标轴QValueAxis *axisX = new QValueAxis();axisX->setTitleText("时间(小时)");axisX->setLabelFormat("%d");axisX->setRange(0, 24);axisX->setTickCount(13);QValueAxis *axisY = new QValueAxis();axisY->setTitleText("温度(℃)");axisY->setLabelFormat("%d");axisY->setRange(10, 30);chart->addAxis(axisX, Qt::AlignBottom);chart->addAxis(axisY, Qt::AlignLeft);series->attachAxis(axisX);series->attachAxis(axisY);// 显示图例chart->legend()->setVisible(true);chart->legend()->setAlignment(Qt::AlignBottom);// 创建图表视图QChartView *chartView = new QChartView(chart);chartView->setRenderHint(QPainter::Antialiasing);// 设置布局if (!ui->centralwidget->layout()) {QVBoxLayout *layout = new QVBoxLayout(ui->centralwidget);layout->addWidget(chartView);} else {ui->centralwidget->layout()->addWidget(chartView);}
}MainWindow::~MainWindow()
{delete ui;
}
结果:

