How to Create Custom Chart Visualizations with Qt6 Charts in FinceptTerminal

FinceptTerminal's ChartFactory abstraction layer simplifies creating custom chart visualizations with Qt6 Charts by providing static factory methods that automatically apply application-wide themes, returning ready-to-use QChartView widgets for line, bar, and sparkline visualizations.

FinceptTerminal ships with a thin-layer ChartFactory that hides the boilerplate of Qt6 Charts while automatically applying the application's theme. The factory lives in fincept-qt/src/ui/charts/ChartFactory.h and ChartFactory.cpp and builds three ready-to-use chart types that you can embed directly into any Qt layout.

Understanding the ChartFactory Architecture

The ChartFactory centralizes theme handling so any custom chart you create automatically stays in sync with user-selected themes or runtime theme changes. This eliminates the need to manually configure colors, fonts, or axis styling for every new chart instance.

Theme Integration via ThemeManager

All charts are themed through ChartFactory::apply_theme, which pulls the current ThemeTokens from ThemeManager (see ThemeManager.cpp). The theme supplies background colors, text colors, border colors, and a palette of six chart colors (ThemeTokens::chart_colors).

The theme resolution process works as follows:

const auto& t = ThemeManager::instance().tokens();   // ChartFactory.cpp:L10-L12

This obtains the active ThemeTokens struct defined in ui/theme/ThemeTokens.h, which contains all color and font tokens used throughout the UI.

Built-in Chart Types

The factory provides three primary visualization patterns:

Factory method Typical use-case Returned widget
line_chart Price history, time-series, indicator plots QChartView* with a QLineSeries
bar_chart Volume bars, categorical comparisons QChartView* with a QBarSeries
sparkline Tiny inline trend lines (no axes) QChartView* with a QLineSeries and a fixed size

Creating Themed Charts with Factory Methods

Because the factory returns a QChartView*, you can embed the chart directly into any Qt layout just like any other widget. Each method handles series creation, chart assembly, and theme application automatically.

Line Charts for Time-Series Data

Use line_chart for rendering continuous data like price histories or indicator plots. The method signature accepts a title, a vector of data points, and an optional color string.

#include "ui/charts/ChartFactory.h"

QVector<fincept::ui::ChartFactory::DataPoint> points;
points << fincept::ui::ChartFactory::DataPoint{0, 101}
       << fincept::ui::ChartFactory::DataPoint{1, 105}
       << fincept::ui::ChartFactory::DataPoint{2, 103};

QChartView* priceChart = fincept::ui::ChartFactory::line_chart(
    "Price (USD)", points, {});      // uses theme accent colour

layout->addWidget(priceChart);

Source: ChartFactory.cpp – line-chart implementation lines 25-45.

The implementation creates a QLineSeries, sets the pen color using the theme accent or provided color, and configures default axes:

series->setPen(QPen(QColor(line_color), 1.5));          // ChartFactory.cpp:L28-L30
auto* chart = new QChart;                              // ChartFactory.cpp:L34-L35
chart->addSeries(series);                              // ChartFactory.cpp:L35-L36
chart->createDefaultAxes();                            // ChartFactory.cpp:L38

Bar Charts for Categorical Data

Use bar_chart for volume bars or categorical comparisons. The method accepts categories as QStringList and values as QVector<double>.

QStringList categories = {"AAPL", "MSFT", "GOOG"};
QVector<double> volumes = {120.5, 98.2, 134.8};

QChartView* volumeChart = fincept::ui::ChartFactory::bar_chart(
    "Daily Volume", categories, volumes, "#4caf50"); // explicit green colour

layout->addWidget(volumeChart);

Source: ChartFactory.cpp – bar-chart implementation lines 47-78.

The factory creates a QBarSeries with QBarSet instances, applying the color to each set:

set->setColor(QColor(bar_color));                      // ChartFactory.cpp:L51-L53

Use sparkline for tiny inline trend lines without axes, ideal for table cells or compact dashboards. The method accepts a fixed width and height.

QVector<double> trend = {0.1, 0.12, 0.09, 0.15, 0.13};

QChartView* miniTrend = fincept::ui::ChartFactory::sparkline(
    trend, {}, 120, 30);   // default colour from theme, 120×30 px

layout->addWidget(miniTrend);

Source: ChartFactory.cpp – sparkline implementation lines 82-107.

The sparkline disables axes, legend, and margins, setting a transparent background:

axis->setLabelsColor(QColor(t.text_secondary));        // ChartFactory.cpp:L19-L21

Extending ChartFactory for Custom Visualizations

If you need a custom visualization (e.g., a multi-line chart, a stacked bar, or a candlestick series), you can extend the factory while reusing its theme infrastructure.

Adding a Multi-Line Chart Method

To create a chart displaying multiple series:

  1. Add a new static method to ChartFactory.h.
  2. Create the required Qt Charts series (QLineSeries instances).
  3. Reuse apply_theme to keep the look consistent.
  4. Expose a color argument that defaults to t.accent but allows callers to pick any of the six palette colors (t.chart_colors[i]).
// In ChartFactory.h
static QChartView* multi_line_chart(const QString& title,
                                    const QVector<QVector<DataPoint>>& seriesData,
                                    const QVector<QString>& colors = {});

// In ChartFactory.cpp
QChartView* ChartFactory::multi_line_chart(const QString& title,
                                           const QVector<QVector<DataPoint>>& seriesData,
                                           const QVector<QString>& colors) {
    const auto& t = ThemeManager::instance().tokens();
    auto* chart = new QChart;
    chart->setTitle(title);
    chart->setTitleBrush(QBrush(QColor(t.text_secondary)));

    for (int i = 0; i < seriesData.size(); ++i) {
        auto* series = new QLineSeries;
        const QString col = (i < colors.size() && !colors[i].isEmpty())
                            ? colors[i] : t.chart_colors[i % t.chart_colors.size()];
        series->setPen(QPen(QColor(col), 1.5));
        for (const auto& pt : seriesData[i])
            series->append(pt.x, pt.y);
        chart->addSeries(series);
    }
    chart->createDefaultAxes();
    apply_theme(chart);
    auto* view = new QChartView(chart);
    view->setRenderHint(QPainter::Antialiasing);
    return view;
}

This extension reuses apply_theme so the new chart inherits the same background, axis colors, and margins as the built-in charts.

Key Files and Implementation Details

File Role Link
fincept-qt/src/ui/charts/ChartFactory.h Public interface for creating themed charts ChartFactory.h
fincept-qt/src/ui/charts/ChartFactory.cpp Implements line, bar, sparkline and theming logic ChartFactory.cpp
fincept-qt/src/ui/theme/ThemeTokens.h Defines the colour/font tokens consumed by the chart factory ThemeTokens.h
fincept-qt/src/ui/theme/ThemeManager.cpp Provides the active ThemeTokens instance and emits theme changes ThemeManager.cpp
fincept-qt/src/screens/polymarket/PolymarketPriceChart.cpp Real-world example of using ChartFactory::line_chart to render a price chart PolymarketPriceChart.cpp

Summary

  • ChartFactory in fincept-qt/src/ui/charts/ChartFactory.cpp provides static methods to create custom chart visualizations with Qt6 Charts without boilerplate.
  • The factory automatically applies themes via apply_theme, ensuring charts sync with ThemeManager and ThemeTokens from ui/theme/ThemeTokens.h.
  • Three built-in types are available: line_chart for time-series, bar_chart for categorical data, and sparkline for compact inline trends.
  • Each method returns a QChartView* that can be embedded directly into Qt layouts.
  • Extending the factory for custom series (candlestick, multi-line, stacked bar) requires implementing the Qt Charts series logic and reusing apply_theme for consistency.

Frequently Asked Questions

How does ChartFactory handle theme changes at runtime?

ChartFactory relies on ThemeManager::instance().tokens() to resolve colors dynamically. When you call factory methods, they capture the current theme state. For runtime theme changes, the existing chart views already apply the theme at construction; to update live charts, you would need to rebuild the chart widget or extend the factory to support dynamic theme refresh by reconnecting to ThemeManager signals.

Can I use custom colours outside the theme palette?

Yes. While factory methods default to t.accent or t.chart_colors, each method accepts an optional color string parameter. For example, in bar_chart, you can pass "#4caf50" to override the theme. The multi_line_chart extension demonstrates passing explicit colors via the colors vector parameter, falling back to the palette only when unspecified.

What is the performance impact of using QChartView for real-time data?

According to the implementation in ChartFactory.cpp, charts are standard QChartView widgets with anti-aliasing enabled. For high-frequency real-time updates, you should limit the dataset size or implement data decimation before passing points to line_chart. The factory itself does not implement buffering optimizations; it is a thin wrapper that creates the series and axes, so performance depends on standard Qt6 Charts rendering capabilities.

How do I extend ChartFactory to support candlestick charts?

To add candlestick support, create a new static method in ChartFactory.h that returns QChartView*. In the implementation, instantiate QCandlestickSeries, populate it with QCandlestickSet objects for your open/high/low/close data, and add the series to a QChart. Finally, call ChartFactory::apply_theme(chart) to ensure the axes and background match the application theme, then return the chart wrapped in a QChartView with anti-aliasing enabled.

Have a question about this repo?

These articles cover the highlights, but your codebase questions are specific. Give your agent direct access to the source. Share this with your agent to get started:

Share the following with your agent to get started:
curl -s "https://instagit.com/install.md"

Works with
Claude Codex Cursor VS Code OpenClaw Any MCP Client

Maintain an open-source project? Get it listed too →