Files
Jungfraujoch/viewer/charts/JFJochDatasetInfoChartView.h
T
leonarski_fandClaude Opus 4.8 961836837f viewer: salmon group boxes; dataset-info x-axis spans the whole dataset
- Fusion fills QGroupBox interiors with a flat light colour, so the settings window
  lost its salmon look. A tiny app stylesheet (QGroupBox { background: transparent })
  makes them show the salmon window background again; entry widgets stay white via
  the palette.
- The dataset-info chart now fixes the x-axis to the whole dataset [0, n) (the
  largest run = the original file), so a subset run is drawn at its real image
  positions instead of being stretched to fill the plot. Subsets with binning bin
  by ordinal and place each point at its mapped image number (correct for the
  common contiguous sub-range).

Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
2026-06-22 16:56:18 +02:00

109 lines
3.5 KiB
C++

// SPDX-FileCopyrightText: 2025 Filip Leonarski, Paul Scherrer Institute <filip.leonarski@psi.ch>
// SPDX-License-Identifier: GPL-3.0-only
#pragma once
#include <QtCharts/QChartView>
#include <QtCharts/QValueAxis>
#include <QtCharts/QLineSeries>
#include <QtCharts/QScatterSeries>
#include <QMouseEvent>
#include <QGraphicsLineItem>
#include <QTimer>
#include <QPointer>
#include <QColor>
#ifdef JFJOCH_USE_FFTW
#include <fftw3.h>
#endif
#include "../../common/GoniometerAxis.h"
#include "../../reader/JFJochReaderDataset.h"
class JFJochDatasetInfoChartView : public QChartView {
Q_OBJECT
QPointer<QLineSeries> series = nullptr;
QPointer<QScatterSeries> currentSeries = nullptr;
QGraphicsLineItem *m_hoverLine = nullptr;
QTimer *m_hoverLoadTimer = nullptr;
int64_t m_hoverPendingIdx = -1;
std::vector<float> values;
QString primaryName_; // legend name of the active (primary) run
int64_t binning = 1;
int64_t curr_image = 0;
bool m_minYZeroEnabled = true;
bool m_yOneOverD = false;
bool m_xUseGoniometerAxis = true;
std::optional<GoniometerAxis> goniometer_axis;
std::optional<float> image_time_us;
void updateChart();
// Build regular (index or goniometer) chart
void buildTimeDomainChart();
public:
// One overlay line (a non-active run), drawn alongside the primary series with a legend entry.
// x maps each value to an image number on the shared x-axis (empty => 0,1,2,... by index).
struct NamedSeries { QString name; std::vector<float> values; QColor color; std::vector<float> x; };
private:
std::vector<NamedSeries> overlays_;
QColor primary_color_; // colour of the active (primary) run, if assigned
std::vector<float> primary_x_; // x (image numbers) for the primary series; empty => index
int64_t full_range_ = 0; // total images in the dataset; fixes the x-axis to [0, n)
// Append (binned) finite points of vals to s at x positions (xs empty => index), extending [mn,mx].
void appendSeries(QLineSeries *s, const std::vector<float> &vals, const std::vector<float> &xs,
double &mn, double &mx) const;
// FFT view toggle
bool m_showFFT = false;
#ifdef JFJOCH_USE_FFTW
// Cached FFT data for hover/status bar etc.
void buildFFTChart();
std::vector<double> m_fftMagnitudes;
std::vector<double> m_fftFrequenciesHz;
#endif
signals:
void imageSelected(int64_t number);
void writeStatusBar(QString string, int timeout_ms = 0);
private slots:
void onHoverLoadTimeout();
void setBinning(int64_t val);
private:
void mousePressEvent(QMouseEvent *event) override;
void mouseMoveEvent(QMouseEvent *event) override;
void leaveEvent(QEvent *event) override;
void contextMenuEvent(QContextMenuEvent *event) override;
public:
explicit JFJochDatasetInfoChartView(QWidget *parent = nullptr);
void setImage(int64_t val);
public slots:
void resetZoom();
public:
// Load the primary (active) run's values plus any overlay runs. one_over_d2 applies the same
// d -> 1/d^2 transform to every series; primaryName/overlay names drive the legend.
void loadValues(const std::vector<float> &input,
int64_t image,
bool one_over_d2,
const JFJochReaderDataset *dataset = nullptr,
const QString &primaryName = QString(),
std::vector<NamedSeries> overlays = {},
const QColor &primaryColor = QColor(),
std::vector<float> primaryX = {},
int64_t fullRange = 0);
};