# Plot declarations and export



`self.plotting` describes strategy visuals: lines, histograms, levels, fills, markers, and bar colors. The package exports their data; it does **not** open or render an interactive chart. Use the exported payload with your own renderer.

[Plotting](https://docs.openbacktesting.com/reference/plotting/#openbacktesting-plotting-plotting) · [export_result](https://docs.openbacktesting.com/reference/plotting/#openbacktesting-plotting-export-result) · [PaneRef](https://docs.openbacktesting.com/reference/plotting/#openbacktesting-plotting-paneref) · [PlotRef](https://docs.openbacktesting.com/reference/plotting/#openbacktesting-plotting-plotref) · [FillRef](https://docs.openbacktesting.com/reference/plotting/#openbacktesting-plotting-fillref) · [MarkerRef](https://docs.openbacktesting.com/reference/plotting/#openbacktesting-plotting-markerref) · [PlottingLimits](https://docs.openbacktesting.com/reference/plotting/#openbacktesting-plotting-plottinglimits) · [PlottingError](https://docs.openbacktesting.com/reference/plotting/#openbacktesting-plotting-plottingerror)

## Declare and export visuals

```python
from openbacktesting import Backtest, Strategy, colors
from openbacktesting.plotting import export_result
from openbacktesting.test import GOOG

class VisualStrategy(Strategy):
    def init(self):
        self.average = self.ta.ema(length=20)
        self.rsi = self.ta.rsi(length=14)
        self.plotting.line(self.average, title="EMA 20", color=colors.BLUE)
        pane = self.plotting.pane("momentum", title="Momentum")
        self.plotting.line(self.rsi, title="RSI", pane=pane, color=colors.PURPLE)
        self.plotting.level(70, pane=pane, color=colors.GRAY)

    def next(self):
        if self.average.valid[-1] and self.close[-1] > self.average[-1]:
            self.plotting.bar_color(colors.GREEN)

result = Backtest(GOOG, VisualStrategy).run()
payload = export_result(result)
print(len(payload["plots"]))
```

## Select a drawing method

| Method | Arguments and returned value |
| --- | --- |
| `pane(id=None, title=None)` | Create a separate pane in `init()`; returns `PaneRef`. Omit `pane` elsewhere for the main price pane. |
| `line(source, ...)` | Single-channel indicator/data handle; returns `PlotRef`. `style="line"` or `"step"`. |
| `histogram(source, baseline=0, ...)` | Bars measured from the baseline; returns `PlotRef`. |
| `level(value, ...)` | Finite scalar horizontal level; returns `PlotRef`. |
| `fill(lower, upper, ...)` | Two compatible line/level references in the same pane; returns `FillRef`. |
| `marker(..., position="above_bar")` | Mark an event in `next()`; returns `MarkerRef`. Use `below_bar` or `price` with a finite `price` for other positions. |
| `bg_color(color, pane=None)` | Current-bar background, in `next()`; returns `None`. |
| `bar_color(color)` | Current price candle color, in `next()`; returns `None`. |

Create panes and static plots in `init()`. Sources must be same-run single-channel handles, not arrays or callbacks. Common arguments are `id` (optional unique identifier), `title` (display label), `pane`, and `color` (`Color` or six/eight-digit hex). References belong to one run and cannot be reused across backtests.

`gap_policy="break"` leaves gaps at missing values; `"connect"` connects valid observations. `offset_bars` is a nonnegative visual shift, not a change to calculation timing. A marker's `shape` is `circle`, `square`, `triangle_up`, or `triangle_down`; `text` adds a label. `anchor_bar` can associate a confirmed event with an earlier bar, without making it known earlier.

For fills, retain the returned lines, for example `lower = self.plotting.line(self.bands.lower)` and `upper = self.plotting.line(self.bands.upper)`, then `self.plotting.fill(lower, upper, color=colors.BLUE.with_transparency(85))`.

## Colors and limits

Colors accept `Color`, `"#RRGGBB"`, or `"#RRGGBBAA"`; see [Color](https://docs.openbacktesting.com/reference/colors/index.md). `bg_color(None)` and `bar_color(None)` clear the current override. The last call for that bar/target wins; colors do not carry into the next bar unless you write them again.

`Backtest(..., plotting=False)` disables historical visual collection. `PlottingLimits` adjusts positive budgets for panes, plots, points, events, text, and exported bytes; exceeding one raises `PlottingError`. Use `error.code` to identify issues such as `invalid-phase`, `invalid-reference`, or `PlottingLimitExceeded`.

The export is a plain dictionary with market data, sources, drawing declarations, and actual execution facts. Write it with `json.dump(payload, file, allow_nan=False)` if you need a file; export itself has no file or browser side effects. Markers represent strategy calls, while fills represent actual executions, which can occur on different bars.

<a id="openbacktesting-plotting-plotting"></a>



## Plotting

Access through Strategy.plotting; init declares market-data/indicator layers, and next/on_order/on_fill add markers.

<a id="openbacktesting-plotting-plotting-fill"></a>



### Plotting.fill

```python
Plotting.fill(lower, upper, id=None, title=None, color=None, gap_policy='break')
```

Fill between two layers; endpoints must share pane, axis, offset, and compatible units.

<a id="openbacktesting-plotting-plotting-histogram"></a>



### Plotting.histogram

```python
Plotting.histogram(
    source,
    id=None,
    title=None,
    pane=None,
    color=None,
    baseline=0,
    gap_policy='break',
    offset_bars=0,
)
```

Declare a histogram; a finite baseline contributes to consumer vertical-axis autoscaling.

<a id="openbacktesting-plotting-plotting-level"></a>



### Plotting.level

```python
Plotting.level(value, id=None, title=None, pane=None, color=None)
```

Declare a finite horizontal line, storing one constant rather than duplicating a full array.

<a id="openbacktesting-plotting-plotting-line"></a>



### Plotting.line

```python
Plotting.line(
    source,
    id=None,
    title=None,
    pane=None,
    color=None,
    style='line',
    gap_policy='break',
    offset_bars=0,
)
```

Declare a line or step line, defaulting to the main chart with broken gaps; offsets affect display only.

<a id="openbacktesting-plotting-plotting-marker"></a>



### Plotting.marker

```python
Plotting.marker(
    id=None,
    title=None,
    pane=None,
    *,
    position='above_bar',
    price=None,
    shape='circle',
    text='',
    color=None,
    anchor_bar=None,
)
```

Record a runtime marker; anchor_bar may refer to historical bars, while knownAtBar is always the current bar.

<a id="openbacktesting-plotting-plotting-pane"></a>



### Plotting.pane

```python
Plotting.pane(id=None, title=None)
```

Create a separate pane in init; return a reference for subsequent layers to share an automatically scaled vertical axis.

<a id="openbacktesting-plotting-plotting-bg-color"></a>



### Plotting.bg_color

```python
Plotting.bg_color(color, *, pane=None)
```

Write the current bar's pane background only in next; the last write to the same target wins.

<a id="openbacktesting-plotting-plotting-bar-color"></a>



### Plotting.bar_color

```python
Plotting.bar_color(color)
```

Color the current main-chart candle only in next, applying one override to body, wick, and border.

<a id="openbacktesting-plotting-export-result"></a>



## export_result

```python
plotting.export_result(result)
```

Return an independent PlottingResult dictionary from a successful backtest's frozen snapshot without reading the strategy instance.

## Returned drawing references

Use a `PaneRef` as a `pane` argument, and `PlotRef` values as fill boundaries. `.id` and `.title` identify a drawing. `FillRef` and `MarkerRef` identify completed declarations; do not construct reference objects yourself.

<a id="openbacktesting-plotting-paneref"></a>



## PaneRef

Separate-pane identity for the current run; pass this reference only to pane arguments.

| Attribute | Type | Meaning |
| --- | --- | --- |
| <a id="openbacktesting-plotting-paneref-id"></a>`id` | `str` | Read-only identity of the drawing in this run. |
| <a id="openbacktesting-plotting-paneref-title"></a>`title` | `str` | Display title of the drawing. |

<a id="openbacktesting-plotting-plotref"></a>



## PlotRef

Line, histogram, or horizontal-line identity usable as a fill endpoint.

| Attribute | Type | Meaning |
| --- | --- | --- |
| <a id="openbacktesting-plotting-plotref-id"></a>`id` | `str` | Read-only identity of the drawing in this run. |
| <a id="openbacktesting-plotting-plotref-title"></a>`title` | `str` | Display title of the drawing. |

<a id="openbacktesting-plotting-fillref"></a>



## FillRef

Fill identity between two compatible layers.

| Attribute | Type | Meaning |
| --- | --- | --- |
| <a id="openbacktesting-plotting-fillref-id"></a>`id` | `str` | Read-only identity of the drawing in this run. |
| <a id="openbacktesting-plotting-fillref-title"></a>`title` | `str` | Display title of the drawing. |

<a id="openbacktesting-plotting-markerref"></a>



## MarkerRef

Identity of one runtime marker.

| Attribute | Type | Meaning |
| --- | --- | --- |
| <a id="openbacktesting-plotting-markerref-id"></a>`id` | `str` | Read-only identity of the drawing in this run. |
| <a id="openbacktesting-plotting-markerref-title"></a>`title` | `str` | Display title of the drawing. |

<a id="openbacktesting-plotting-plottinglimits"></a>



## PlottingLimits

```python
plotting.PlottingLimits(
    panes=32,
    plots=256,
    points=10000000,
    events=1000000,
    text=1048576,
    bytes=268435456,
)
```

Collection budgets; all limits are positive integers, and bytes is checked during explicit export.

| Attribute | Type | Meaning |
| --- | --- | --- |
| <a id="openbacktesting-plotting-plottinglimits-panes"></a>`panes` | `int` | Maximum panes, including the main pane. |
| <a id="openbacktesting-plotting-plottinglimits-plots"></a>`plots` | `int` | Maximum plots, including fills. |
| <a id="openbacktesting-plotting-plottinglimits-points"></a>`points` | `int` | Maximum retained numeric/mask points. |
| <a id="openbacktesting-plotting-plottinglimits-events"></a>`events` | `int` | Maximum color, marker, fill, and account events. |
| <a id="openbacktesting-plotting-plottinglimits-text"></a>`text` | `int` | Maximum UTF-8 bytes of labels and other text. |
| <a id="openbacktesting-plotting-plottinglimits-bytes"></a>`bytes` | `int` | Maximum compact JSON export bytes. |

<a id="openbacktesting-plotting-plottingerror"></a>



## PlottingError

Plotting contract error; code is a stable category for caller dispatch.

<a id="openbacktesting-plotting-plottingerror-code"></a>



**`code`** — Stable error category; see the plotting guide for details.

[Colors](https://docs.openbacktesting.com/reference/colors/index.md) · [Indicators](https://docs.openbacktesting.com/reference/indicator-api/index.md) · [User manual](https://docs.openbacktesting.com/index.md)
