Opinionated static and interactive plots for quantitative research.
The first helpers focus on return streams: quick column charts, equity curves, drawdowns, and compact performance tearsheets. Directional label visualization and trade-log charts use the same interactive Plotly styling. Implementations live in :mod:qrt.plot.interactive and are re-exported here; this module only adds the ergonomic aliases :func:line, :func:performance, and :func:tearsheet. Return-stream statistics (performance, alpha/beta, rolling diagnostics, …) live in :mod:qrt.stats.
Plot one scalar value per Series item or selected DataFrame column.
A one-row DataFrame is plotted directly. For a DataFrame with multiple rows, aggregate must name a pandas reduction such as "sum", "mean", or "last", or be a callable applied to each column.
Parameters
Name
Type
Description
Default
data
pd.Series | pd.DataFrame
Numeric values as a Series, or observations in rows and categories in columns as a DataFrame.
required
columns
str | Iterable[str] | None
DataFrame column name(s) or shell-style pattern(s). Defaults to all numeric columns. Not used for Series input.
None
aggregate
str | Callable[[pd.Series], float] | None
Reduction applied to each selected DataFrame column when the frame has multiple rows. Required for multi-row frames.
None
sorted
bool
Whether to order bars from highest to lowest value.
False
color_scheme
str | Sequence[str] | Mapping[object, str]
"sign" for gain/loss colors, a single Plotly color, a sequence cycled across bars, or a category-to-color mapping.
'sign'
positive_color
str
Color for positive values in the "sign" scheme.
'#22C55E'
negative_color
str
Color for negative values in the "sign" scheme.
'#EF4444'
zero_color
str
Color for zero values in the "sign" scheme.
'#94A3B8'
title
str | None
Figure title. Defaults to the Series name or "Bar chart".
Create an interactive scatterplot matrix for feature correlation analysis.
Linked selection highlights the same observations in every panel. color_by must name a column in data; QRT uses each row’s value in that column to determine the point color. Categorical values create discrete groups, while numeric values use a continuous scale. Numeric colors that span zero automatically center the scale at zero.
Parameters
Name
Type
Description
Default
data
pd.DataFrame
Observations in rows and features in columns.
required
columns
str | Iterable[str] | None
Numeric feature name(s) or shell-style pattern(s). By default, all numeric columns except color_by are included.
None
color_by
str | None
Exact DataFrame column name used to color observations. QRT does not infer a regime column or calculate category boundaries. String, categorical, and boolean values use discrete colors; numeric values use color_continuous_scale.
None
color_discrete_sequence
Sequence[str] | None
Colors assigned in order to categorical values. Defaults to the QRT categorical palette.
None
color_discrete_map
Mapping[object, str] | None
Exact value-to-color assignments for categories in the color_by column. Useful for stable semantic colors such as red for "risk-off".
None
color_continuous_scale
str | Sequence[str]
Plotly color-scale name or explicit color sequence for numeric values. Defaults to "RdYlGn".
'RdYlGn'
hover_data
Iterable[str] | None
Additional columns shown on hover, such as symbol or regime.
None
labels
dict[str, str] | None
Optional mapping from column names to display labels.
None
triangle
Literal['lower', 'upper', 'full']
Matrix panels to display: "lower", "upper", or "full".
'full'
diagonal
bool
Whether to show each feature plotted against itself.
True
marker_size
float
Marker diameter in pixels.
7
marker_opacity
float
Marker opacity from 0 (transparent) to 1 (opaque).
0.9
marker_line_width
float
Marker outline width in pixels.
0.6
marker_line_color
str
Marker outline color.
'#1F2937'
axis_color
str
Color used for subplot axes, ticks, and tick labels.
'#334155'
axis_line_width
float
Subplot axis-line width in pixels.
1.2
tick_length
float
Outward tick length in pixels.
5
tick_width
float
Tick width in pixels.
1.2
title
str
Figure title.
'Feature relationships'
height
int | None
Figure height in pixels. Inferred from the feature count by default.
None
width
int | None
Figure width in pixels. Overrides panel_aspect_ratio when set.
None
panel_aspect_ratio
float | None
Width-to-height ratio for each matrix panel. Defaults to 1.0 for square panels; use None for responsive container width.
The color scale is pinned to [-1, 1] and centered at zero, so panels stay comparable across feature sets. Wide feature libraries are the main use case: cluster=True reorders rows and columns by similarity, which groups redundant features into visible blocks instead of scattering them.
Parameters
Name
Type
Description
Default
data
pd.DataFrame
Observations in rows and features in columns.
required
columns
str | Iterable[str] | None
Numeric feature name(s) or shell-style pattern(s). Defaults to all numeric columns.
None
method
Literal['pearson', 'spearman', 'kendall']
Correlation method: "pearson", "spearman", or "kendall". Rank methods resist outliers and capture monotonic relationships.
'pearson'
min_periods
int | None
Minimum overlapping observations required per pair.
None
cluster
bool
Whether to order features by hierarchical clustering so similar features are adjacent.
False
triangle
Literal['lower', 'upper', 'full']
Matrix cells to display: "lower", "upper", or "full".
'full'
diagonal
bool
Whether to show the self-correlation diagonal.
True
color_continuous_scale
str | Sequence[str]
Plotly color-scale name or explicit color sequence. Defaults to "RdYlGn".
'RdYlGn'
show_values
bool | None
Whether to annotate cells with correlation values. Defaults to annotating only matrices small enough to stay readable.
None
value_format
str
Format specification used for cell annotations.
'.2f'
text_size
float
Annotation font size in pixels.
11
labels
dict[str, str] | None
Optional mapping from column names to display labels.
None
colorbar_label
str
Color-bar title.
'Correlation'
title
str
Figure title.
'Feature correlation'
cell_size
float
Target cell size in pixels, used to infer the figure size.
34
height
int | None
Figure height in pixels. Inferred from the feature count by default.
None
width
int | None
Figure width in pixels. Inferred from the feature count by default.
Create an interactive cumulative-returns chart, strategy vs an optional benchmark.
Parameters
Name
Type
Description
Default
returns
pd.Series
Strategy periodic return series.
required
benchmark
pd.Series | None
Optional benchmark periodic return series, aligned to returns on shared dates.
None
return_type
ReturnType
Whether returns/benchmark are "simple" or "log" returns.
'simple'
scale
Literal['linear', 'log', 'volatility_matched']
"linear" (plain cumulative percentage returns), "log" (log y-axis with percent tick labels, to compare compounding regimes across very different magnitudes), or "volatility_matched" (rescales the benchmark’s returns to match the strategy’s volatility before compounding, isolating differences in trend from differences in risk taken). The latter requires benchmark.
Create an interactive stacked-area chart of cumulative factor return contributions.
See :func:qrt.stats.factor_contributions for the underlying per-period return attribution (alpha + one term per factor + residual, from a full-period fit). Cumulative sums are arithmetic (not compounded), so the stacked areas always add up exactly to the strategy’s cumulative excess return, drawn overlaid as a dotted reference line.
Parameters
Name
Type
Description
Default
returns
pd.Series
Strategy periodic return series.
required
factors
pd.DataFrame
DataFrame of periodic factor return columns, aligned to returns.
Create an interactive bar chart of full-period multi-factor regression coefficients.
See :func:qrt.stats.factor_regression for the underlying calculation, e.g. the Fama-French five-factor model’s Mkt-RF/SMB/HML/RMW/CMA betas.
Parameters
Name
Type
Description
Default
returns
pd.Series
Strategy periodic return series.
required
factors
pd.DataFrame
DataFrame of periodic factor return columns, aligned to returns.
required
return_type
ReturnType
Whether returns is "simple" or "log" returns.
'simple'
rf
str | pd.Series | None
See :func:qrt.stats.factor_regression.
'RF'
covariance
CovarianceType
Standard-error estimator; see :func:qrt.stats.factor_regression.
'nonrobust'
confidence_level
float
Confidence level for the error bars. Defaults to 0.95.
0.95
include_alpha
bool
Whether to include the Alpha bar alongside the factor betas. Defaults to False since alpha’s scale/units usually differ from a factor beta (see :func:qrt.stats.factor_regression_stats for alpha shown on its own, annualized).
Labels use green upward triangles for long (1), orange dashes for neutral (0), and red downward triangles for short (-1). When label data includes touch_time or end_time, translucent outcome spans can be drawn from each event to its endpoint.
Parameters
Name
Type
Description
Default
prices
pd.Series | pd.DataFrame
Close-price Series or frame containing a close column.
required
labels
pd.Series | pd.DataFrame
Event-indexed label Series or DataFrame containing label_col. Missing labels are omitted.
required
label_col
str
DataFrame column containing values in {-1, 0, 1}.
'label'
end_col
str | None
Optional outcome-end column. Defaults to touch_time when present, then end_time.
None
show_spans
bool
Whether to shade each event’s outcome interval when an endpoint column is available.
Create an interactive Plotly line chart from selected numeric columns.
Parameters
Name
Type
Description
Default
data
pd.Series | pd.DataFrame
Series or DataFrame to plot.
required
columns
str | Iterable[str] | None
Column name(s) or shell-style pattern(s) (e.g. "*_ret") to select. Defaults to all columns.
None
title
str | None
Figure title. Defaults to the column name (single column) or a generic title (multiple columns).
None
ylabel
str | None
Y-axis label.
None
height
int
Figure height in pixels.
450
Returns
Name
Type
Description
Figure
A Plotly Figure.
mae_mfe
plot.mae_mfe(trades, *, title=None, height=430)
Create an interactive MAE/MFE excursion scatter from a trade log.
Two panels sharing the trade-return y-axis: max adverse excursion (how far each trade went against you – informs stop placement) and max favorable excursion (how much open profit existed – informs profit taking). Dashed identity lines mark the bounds return >= MAE and return <= MFE; exits near the MFE line captured most of their open profit, winners far below it round-tripped gains.
Parameters
Name
Type
Description
Default
trades
pd.DataFrame
Canonical trades-format DataFrame with mae/mfe columns.
Create an interactive table of performance metrics.
Parameters
Name
Type
Description
Default
returns
pd.Series
Strategy periodic return series.
required
benchmark
pd.Series | None
Optional benchmark periodic return series, aligned to returns on shared dates. Adds a benchmark column plus relative rows (Beta, Alpha, Correlation, R², Information Ratio, Tracking Error, Treynor Ratio) when given.
None
return_type
ReturnType
Whether returns/benchmark are "simple" or "log" returns.
'simple'
periods_per_year
int | None
Annualization frequency. Inferred from the index when not given.
None
rf
float
Annualized risk-free rate. Defaults to 0.0.
0.0
mode
Literal['basic', 'full']
"full" (default) for the complete quantstats-style metric set, "basic" for a compact headline subset. See :func:qrt.stats.metrics.
'full'
title
str
Figure title.
'Key Performance Metrics'
height
int | None
Figure height in pixels. Defaults to a size based on the number of metric rows.
Create an interactive Monte Carlo fan chart of bootstrap-resampled return simulations.
Runs :func:qrt.stats.montecarlo on the full sims simulations, so the shaded confidence band and any bust/goal probabilities reflect the entire sample, then renders only a sample of the individual paths for readability. Unlike quantstats’ plot_montecarlo (which colors paths arbitrarily and, being built on a plain permutation of returns, can only vary each path’s shape, never its terminal value — see the note on :func:qrt.stats.montecarlo), each rendered path here is colored by its own outcome:
Original (unresampled) path: bold black line, drawn on top.
Busted paths (Max Drawdown breached bust): red.
Reached goal paths (terminal return met goal): green.
Everything else: light gray.
Parameters
Name
Type
Description
Default
returns
pd.Series
Periodic return series (simple or log, per return_type).
required
sims
int
Number of simulated paths to run; statistics use all of them.
1000
return_type
ReturnType
Whether returns are "simple" or "log" returns.
'simple'
bust
float | None
Optional Max Drawdown threshold (e.g. -0.2); breaching paths are colored red.
None
goal
float | None
Optional cumulative-return threshold (e.g. 1.0); paths reaching it are colored green and a reference line is drawn at that level.
None
confidence
float
Confidence level for the shaded fan. Defaults to 0.95.
0.95
seed
int | None
Optional random seed for reproducibility.
None
block_size
float | None
Optional mean block length (in periods) for a stationary block bootstrap, preserving autocorrelation/volatility clustering that i.i.d. resampling destroys. See the Note on :func:qrt.stats.montecarlo. Defaults to None (i.i.d.).
None
periods
int | None
Optional simulation horizon in periods, decoupled from len(returns) so a long, multi-regime history can be used as the resampling pool while each simulated path only covers a realistic forward horizon (e.g. 252 for one trading year). See the Note on :func:qrt.stats.montecarlo. Defaults to None (the full length of returns).
None
sample
int
Max number of individual simulated paths rendered (statistics still use all sims). Defaults to 200.
Create interactive terminal-return and Max Drawdown distributions from a Monte Carlo run.
Complements :func:montecarlo‘s fan chart with two histograms, both built from all sims simulations: the spread of terminal cumulative returns (reward) side-by-side with the spread of each simulation’s Max Drawdown (risk). Where quantstats’ plot_montecarlo_distribution shows only the former, pairing it with the drawdown distribution surfaces the downside risk a single terminal-value histogram hides. This distinction matters more than it first appears: since :func:qrt.stats.montecarlo resamples with replacement, the terminal-return panel here carries real information (a plain permutation-based simulation, as used by quantstats, cannot vary the terminal value at all — see the note on :func:qrt.stats.montecarlo). The original (unresampled) outcome is marked on both panels, along with the goal/bust thresholds and probabilities when given.
Parameters
Name
Type
Description
Default
returns
pd.Series
Periodic return series (simple or log, per return_type).
required
sims
int
Number of simulated paths.
1000
return_type
ReturnType
Whether returns are "simple" or "log" returns.
'simple'
bust
float | None
Optional Max Drawdown threshold (e.g. -0.2), marked on the drawdown panel.
None
goal
float | None
Optional cumulative-return threshold (e.g. 1.0), marked on the return panel.
None
confidence
float
Confidence level, forwarded to :func:qrt.stats.montecarlo for the reported probabilities. Defaults to 0.95.
0.95
seed
int | None
Optional random seed for reproducibility.
None
block_size
float | None
Optional mean block length (in periods) for a stationary block bootstrap, preserving autocorrelation/volatility clustering that i.i.d. resampling destroys. See the Note on :func:qrt.stats.montecarlo. Defaults to None (i.i.d.).
None
periods
int | None
Optional simulation horizon in periods, decoupled from len(returns) so a long, multi-regime history can be used as the resampling pool while each simulated path only covers a realistic forward horizon (e.g. 252 for one trading year). See the Note on :func:qrt.stats.montecarlo. Defaults to None (the full length of returns).
None
title
str | None
Figure title. Defaults to returns.name.
None
height
int
Figure height in pixels.
420
Returns
Name
Type
Description
Figure
A Plotly Figure.
monthly_distribution
plot.monthly_distribution( returns,*, benchmark=None, return_type='simple', title='Distribution of Monthly Returns', height=400,)
Create an interactive histogram of compounded monthly returns.
Parameters
Name
Type
Description
Default
returns
pd.Series
Strategy periodic return series.
required
benchmark
pd.Series | None
Optional benchmark periodic return series, aligned to returns on shared dates, overlaid as a second histogram.
None
return_type
ReturnType
Whether returns/benchmark are "simple" or "log" returns.
Create an interactive Noise Test fan chart of noise-perturbed return path simulations.
Runs :func:qrt.stats.noise_test on the full sims simulations, so the shaded confidence band and any bust/goal probabilities reflect the entire sample, then renders only a sample of the individual perturbed paths for readability. Unlike :func:montecarlo (which bootstrap-resamples returns, varying their order/composition) or :func:variance_test (which varies the win rate over a forward horizon), each rendered path here keeps the exact historical sequence of returns but jitters the magnitude of every period’s return by multiplicative noise, testing sensitivity to day-to-day noise/volatility rather than resampling variance:
Real (original, unperturbed) path: bold black line, drawn on top.
Busted paths (Max Drawdown breached bust): red.
Reached goal paths (terminal return met goal): green.
Everything else: light gray, labeled Random.
Parameters
Name
Type
Description
Default
returns
pd.Series
Periodic return series (simple or log, per return_type).
required
sims
int
Number of simulated paths to run; statistics use all of them.
1000
return_type
ReturnType
Whether returns are "simple" or "log" returns.
'simple'
noise
float
Standard deviation of the multiplicative noise applied to each period’s return. See the Args on :func:qrt.stats.noise_test.
0.1
bust
float | None
Optional Max Drawdown threshold (e.g. -0.2); breaching paths are colored red.
None
goal
float | None
Optional cumulative-return threshold (e.g. 1.0); paths reaching it are colored green and a reference line is drawn at that level.
None
confidence
float
Confidence level for the shaded fan. Defaults to 0.95.
0.95
seed
int | None
Optional random seed for reproducibility.
None
sample
int
Max number of individual simulated paths rendered (statistics still use all sims). Defaults to 200.
Create an interactive chart of rolling multi-factor betas over time.
See :func:qrt.stats.rolling_factor_regression for the underlying calculation, e.g. the rolling Fama-French five-factor betas that reveal time-varying exposure.
Parameters
Name
Type
Description
Default
returns
pd.Series
Strategy periodic return series.
required
factors
pd.DataFrame
DataFrame of periodic factor return columns, aligned to returns.
required
window
int
Trailing window size, in periods. Defaults to 63 (~3 trading months).
63
return_type
ReturnType
Whether returns is "simple" or "log" returns.
'simple'
rf
str | pd.Series | None
See :func:qrt.stats.factor_regression.
'RF'
min_observations
int | None
See :func:qrt.stats.rolling_factor_regression.
None
title
str | None
Figure title. Defaults to a title naming window.
None
height
int
Figure height in pixels.
380
Returns
Name
Type
Description
Figure
A Plotly Figure. Each factor’s hover also shows that window’s
Figure
observation count and R², to distinguish real exposure changes from
Create an interactive price chart with entry/exit markers for a trade log.
Renders the price series with one marker per trade entry (triangle up for longs, down for shorts) and exit (x, green for winners, red for losers), plus a translucent span shading each trade by outcome. Hovering a marker shows the trade’s reason, return, holding period, and any feature-snapshot columns beyond the reserved trades-format set.
Parameters
Name
Type
Description
Default
trades
pd.DataFrame
Canonical trades-format DataFrame (see :mod:qrt.data.datasets).
required
prices
pd.Series | pd.DataFrame
Close series (or OHLCV frame with a close column) with a DatetimeIndex covering the trade span.
required
features
pd.DataFrame | None
Optional datetime-indexed frame of indicator series (e.g. moving averages computed via :mod:qrt.indicator) drawn as overlay lines on the price axis.
Create historical and point-in-time performance treemaps for portfolio assets.
The default accumulated mode includes every asset held on or before each timestamp. Returns compound only while held, then remain at their terminal value after exit. Point-in-time mode shows only the assets held at the selected timestamp and their accumulated held-period returns through that date. A finite return marks a held period when weights are omitted; with weights, a finite return and nonzero finite weight are both required. Tiles have equal area unless weights are supplied. Dynamic weights use cumulative average absolute exposure in accumulated mode and current absolute exposure in point-in-time mode.
Parameters
Name
Type
Description
Default
asset_returns
pd.DataFrame
Wide frame of simple returns, indexed by timestamp with one asset per column.
required
weights
pd.DataFrame | pd.Series | None
Optional matching weight frame, or static weight series indexed by asset. Dynamic absolute weights are averaged cumulatively for tile area; static absolute weights are used directly.
Create an interactive Variance Testing fan chart of forward win-rate-varied trade paths.
Runs :func:qrt.stats.variance_test on the full sims simulations, so the shaded confidence band and the make-money/ruin probabilities reflect the entire sample, then renders only a sample of the individual simulated paths for readability, alongside the actual historical ("Real") cumulative return over the most recent periods trades of trades for comparison (truncated to periods rather than the full history so its scale and length stay comparable to the simulated paths):
Real (actual historical) path: bold black line, drawn on top.
The simulated paths and confidence band are 0-based when computed (statistics such as make_money_probability/ruin_probability stay purely forward-looking, unaffected by history), but are rebased for display onto the last "Real" cumulative return so the fan chart continues smoothly from history instead of visually resetting to 0% at “Now” (the ruin reference line is shifted the same way).
When trades has a DatetimeIndex, the x-axis shows real calendar dates — the actual dates for "Real" and dates extrapolated forward from the last one for the simulated paths (marked with a dotted “Now” line at the boundary) — matching the date axes used throughout :mod:qrt.plot. Falls back to a plain trade-count axis otherwise.
Parameters
Name
Type
Description
Default
trades
pd.Series
Per-trade return series (simple or log, per return_type).
required
periods
int
Number of future trades to simulate per path.
required
sims
int
Number of simulated paths to run; statistics use all of them.
1000
return_type
ReturnType
Whether trades are "simple" or "log" returns.
'simple'
win_rate_variance
float
Amount by which each simulation’s win rate is randomly perturbed from the historical win rate. See the Args on :func:qrt.stats.variance_test.
0.1
ruin
float
Max Drawdown threshold (e.g. -0.9); breaching paths are colored red and marked with a reference line. See the Args on :func:qrt.stats.variance_test.
-0.9
confidence
float
Confidence level for the shaded fan. Defaults to 0.95.
0.95
seed
int | None
Optional random seed for reproducibility.
None
sample
int
Max number of individual simulated paths rendered (statistics still use all sims). Defaults to 200.