Hello,
I really like the ability to plot a second symbol on the "price" pane, and that works well. My question is there a way to place an average connected to the second axis associated with the second price pane symbol?
Thank you in advance,
Bryce
I really like the ability to plot a second symbol on the "price" pane, and that works well. My question is there a way to place an average connected to the second axis associated with the second price pane symbol?
Thank you in advance,
Bryce
Rename
QUOTE:
is there a way to place an average connected to the second axis associated with the second price pane symbol?
I don't follow. You want to create a Price pane with two separate y-axes?
Yes, ScottPlot lets you do that. And version 4.1 is installed with WL. You'll need to code the setup in C# of course, but it's easy to do. See the example below.
Alternatively, you could transform both price plots with the ROC indicator so the single y-axes is in percentage change, then both plots will fit on one WL pane. That would be simplest.
There isn't an easy way that I can think of. You'd have to rescale and plot the second symbol yourself to use the same scaling for the indicator(s).
I'd say to keep it simple and plot the second symbol and associated indicators in a separate pane.
I'd say to keep it simple and plot the second symbol and associated indicators in a separate pane.
Superticker,
Your example is very deluxe. Is there an example C# that demonstrates the screenshot?
Bryce
Your example is very deluxe. Is there an example C# that demonstrates the screenshot?
Bryce
I would start by searching the WL forum for ScottPlot examples. There are quite a few.
Then if you have questions, post them in that forum topic.
And check out this link for a simple plot. https://scottplot.net/cookbook/4.1/#multi-axis
Then if you have questions, post them in that forum topic.
And check out this link for a simple plot. https://scottplot.net/cookbook/4.1/#multi-axis
Superticker,
Thank you for the pointer to the many examples. This should be very helpful, especially after I get a debugger installed and attached to my strategy. One very basic question is the examples are all generated using the Plot object and there is an abstraction from "Price" pane to the actual price Plot object. How do I get the ScottPlot object?
Thank you for the pointer to the many examples. This should be very helpful, especially after I get a debugger installed and attached to my strategy. One very basic question is the examples are all generated using the Plot object and there is an abstraction from "Price" pane to the actual price Plot object. How do I get the ScottPlot object?
QUOTE:
How do I get the ScottPlot object?
There are several ways. The ScottPlot examples are creating a *.png file, so you need to open that file to see the plot with a Windows photo program.
The way I do it is with the WL finantic.InteractiveGraphics extension, which is sold separately. If you're going to be using ScottPlot a lot, then I would use that approach instead because it's more flexible. https://www.wealth-lab.com/extension/detail/finantic.InteractiveGraphics
The last paragraph of Post #1 also mentions transforming the two time series using the ROC indicator so both can share the same percentage change y-axis on a WL pane. And that's illustrated below with IBM and SPY. The WL code is pretty straightforward. And I use this approach on my broker's trading platform.
CODE:
using WealthLab.Backtest; using WealthLab.Core; using WealthLab.Indicators; namespace WealthScript2 { public class SimplePlot : UserStrategyBase { public override void Initialize(BarHistory bars) { IndicatorBase rocStock = ROC.Series(bars.Close, 1); BarHistory spy = GetHistory(bars, "SPY"); IndicatorBase rocIndex = ROC.Series(spy.Close, 1); PlotIndicator(rocStock,WLColor.Green); PlotIndicator(rocIndex, WLColor.DodgerBlue, paneTag: rocStock.PaneTag); } public override void Execute(BarHistory bars, int idx) { } } }
I attempted to code the above case in ScottPlot. The OffsetX is off, so the time scale is starting at the wrong point. I don't know how to correct that, so you will need to play with it. But this result will give you an idea of how ScottPlot 4.1 works.
Normally, I use ScottPlot for a scatter plot of the results of a backtest (for performance visualization), so its code would appear in Cleanup{} or BacktestComplete{}, but in this weird application the graph data is established in Initialize{}, so the ScottPlot code is placed there instead.
CODE:
using System; using System.Drawing; using WealthLab.Backtest; using WealthLab.Core; using WealthLab.Indicators; using ScottPlot; namespace WealthScript2 { public class SimplePlot : UserStrategyBase { public override void Initialize(BarHistory bars) { IndicatorBase rocStock = ROC.Series(bars.Close, 1); BarHistory spy = GetHistory(bars, "SPY"); IndicatorBase rocIndex = ROC.Series(spy.Close, 1); PlotIndicator(rocStock,WLColor.Green); PlotIndicator(rocIndex, WLColor.DodgerBlue, paneTag: rocStock.PaneTag); Plot plt = new Plot(800, 400); plt.AddSignal(bars.Close.Values.ToArray(), color: Color.CornflowerBlue).FillBelow(Color.Blue, Color.Transparent); ScottPlot.Plottable.SignalPlot indexPlot = plt.AddSignal(spy.Close.Values.ToArray(), color: Color.Green); indexPlot.YAxisIndex = 1; //Index=1, build YAxis scale on right //indexPlot.OffsetX = bars.Close.DateTimes[0].ToOADate(); //set start date plt.XAxis.TickLabelFormat("MMM\nyyyy", dateTimeFormat: true); //display tick labels using a time format plt.YAxis.Ticks(true); plt.YAxis2.Ticks(true); //display YAxis ticks on left & right plt.YAxis.Grid(false); plt.YAxis2.Grid(true); //display YAxis grids for right (Equity) side plt.YAxis.Label("Price of " + bars.Symbol + " ($)", Color.CornflowerBlue); plt.YAxis2.Label("Price of " + spy.Symbol + " ($)", Color.Green); plt.Title(@"Price plot for " + bars.Symbol); plt.SaveFig(Environment.GetFolderPath(Environment.SpecialFolder.Desktop) + @"\simplePlot.png"); } public override void Execute(BarHistory bars, int idx) { } } }
Normally, I use ScottPlot for a scatter plot of the results of a backtest (for performance visualization), so its code would appear in Cleanup{} or BacktestComplete{}, but in this weird application the graph data is established in Initialize{}, so the ScottPlot code is placed there instead.
I got the ScottPlot code running correctly. But the resulting ScottPlot code isn't pretty. I would create a static method in your Visual Studio static class, WLUtility, with all the ScottPlot code so it never appears in any of your WL strategies. In fact, I never allow any foreign data types in my WL strategies; all external frameworks are called indirectly through local custom libraries. That way I avoid name clashes between different frameworks.
CODE:
using System; using System.Drawing; using WealthLab.Backtest; using WealthLab.Core; using WealthLab.Indicators; using ScottPlot; namespace WealthScript2 { public class SimplePlot : UserStrategyBase { public override void Initialize(BarHistory bars) { IndicatorBase rocStock = ROC.Series(bars.Close, 1); BarHistory spy = GetHistory(bars, "SPY"); IndicatorBase rocIndex = ROC.Series(spy.Close, 1); PlotIndicator(rocStock,WLColor.Green); PlotIndicator(rocIndex, WLColor.DodgerBlue, paneTag: rocStock.PaneTag); Plot plt = new Plot(800, 400); plt.Legend(location: Alignment.UpperLeft); ScottPlot.Plottable.SignalPlot stockPlot = plt.AddSignal(bars.Close.Values.ToArray(), color: Color.CornflowerBlue, label: bars.Symbol); stockPlot.FillBelow(Color.Blue, Color.Transparent); ScottPlot.Plottable.SignalPlot indexPlot = plt.AddSignal(spy.Close.Values.ToArray(), color: Color.Green, label: spy.Symbol); indexPlot.YAxisIndex = 1; //Index=1, build YAxis scale on right double[] tickPositions = new double[11]; string[] tickLabels = new string[11]; double pos = 0.0; for (int idx = 0; idx < 11; idx++, pos += bars.Count/10.1) { tickPositions[idx] = pos; tickLabels[idx] = bars.Close.DateTimes[(int)pos].ToString("MMM\nyyyy"); } plt.XTicks(tickPositions, tickLabels); plt.YAxis.Ticks(true); plt.YAxis2.Ticks(true); //display YAxis ticks on left & right plt.YAxis.Grid(false); plt.YAxis2.Grid(true); //display YAxis grids for right (SPY index) side plt.YAxis.Label("Price of " + bars.Symbol + " ($)", Color.CornflowerBlue); plt.YAxis2.Label("Price of " + spy.Symbol + " ($)", Color.Green); plt.Title(@"Price plot for " + bars.Symbol + " with " + spy.Symbol); plt.SaveFig(Environment.GetFolderPath(Environment.SpecialFolder.Desktop) + @"\simplePlot.png"); } public override void Execute(BarHistory bars, int idx) { } } }
Your Response
Post
Edit Post
Login is required