Skip to content

CustomSymbols

Summary

Represents collection of custom symbols.

Signature

1
public abstract interface CustomSymbols

Namespace

cAlgo.API

Examples

  1
  2
  3
  4
  5
  6
  7
  8
  9
 10
 11
 12
 13
 14
 15
 16
 17
 18
 19
 20
 21
 22
 23
 24
 25
 26
 27
 28
 29
 30
 31
 32
 33
 34
 35
 36
 37
 38
 39
 40
 41
 42
 43
 44
 45
 46
 47
 48
 49
 50
 51
 52
 53
 54
 55
 56
 57
 58
 59
 60
 61
 62
 63
 64
 65
 66
 67
 68
 69
 70
 71
 72
 73
 74
 75
 76
 77
 78
 79
 80
 81
 82
 83
 84
 85
 86
 87
 88
 89
 90
 91
 92
 93
 94
 95
 96
 97
 98
 99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
344
345
346
347
 using System;
 using cAlgo.API;
 using cAlgo.API.Internals;
 using System.Linq;
 namespace cAlgo.Plugins;
 [Plugin(AccessRights = AccessRights.None)]
 public class CustomSymbolTest : Plugin
 {
     private const string InitialDescription = "This is custom symbol initial description";
     private const string ChangedDescription = "This is custom symbol changed description";
     private bool _isLoadMoreEnabled = true;
     private CustomSymbol _customSymbol;
     private CustomBars _customBars;
     protected override void OnStart()
     {
         var panel = new StackPanel();
         var addCustomSymbolWithBaseButton = new Button { Text = "Add custom symbol with Base Symbol" };
         addCustomSymbolWithBaseButton.Click += OnAddCustomSymbolWithBaseButtonClick;
         panel.AddChild(addCustomSymbolWithBaseButton);
         var addCustomSymbolWithoutBaseButton = new Button { Text = "Add custom symbol without Base Symbol" };
         addCustomSymbolWithoutBaseButton.Click += OnAddCustomSymbolWithoutBaseButtonClick;
         panel.AddChild(addCustomSymbolWithoutBaseButton);
         var removeCustomSymbolButton = new Button { Text = "Remove custom symbol" };
         removeCustomSymbolButton.Click += OnRemoveCustomSymbolButtonClick;
         panel.AddChild(removeCustomSymbolButton);
         var displayChartInfoButton = new Button { Text = "Display Charts Info" };
         displayChartInfoButton.Click += OnDisplayChartInfoButtonClick;
         panel.AddChild(displayChartInfoButton);
         var changeDescriptionButton = new Button { Text = "Change Description" };
         changeDescriptionButton.Click += OnChangeDescriptionButtonClick;
         panel.AddChild(changeDescriptionButton);
         var updateSymbolPropertiesButton = new Button { Text = "Update Symbol Properties" };
         updateSymbolPropertiesButton.Click += OnUpdateSymbolPropertiesButtonClick;
         panel.AddChild(updateSymbolPropertiesButton);
         var updateSymbolBaseAssetButton = new Button { Text = "Update Symbol Base Asset" };
         updateSymbolBaseAssetButton.Click += OnUpdateSymbolBaseAssetButtonClick;
         panel.AddChild(updateSymbolBaseAssetButton);
         var updateSymbolQuoteAssetButton = new Button { Text = "Update Symbol Quote Asset" };
         updateSymbolQuoteAssetButton.Click += OnUpdateSymbolQuoteAssetButtonClick;
         panel.AddChild(updateSymbolQuoteAssetButton);
         var showSymbolPropertiesButton = new Button { Text = "Show Symbol Properties" };
         showSymbolPropertiesButton.Click += args => ShowSymbolProperties();
         panel.AddChild(showSymbolPropertiesButton);
         var showSymbolAssetsButton = new Button { Text = "Show Symbol Assets" };
         showSymbolAssetsButton.Click += args => ShowSymbolAssets();
         panel.AddChild(showSymbolAssetsButton);
         var pauseOrResumeLoadMoreButton = new Button { Text = "Pause / Resume Load More" };
         pauseOrResumeLoadMoreButton.Click += OnPauseOrResumeLoadMoreButtonClick;
         panel.AddChild(pauseOrResumeLoadMoreButton);
         var showRegularBarsInfoButton = new Button { Text = "Show Regular Bars Info" };
         showRegularBarsInfoButton.Click += OnShowRegularBarsInfoButtonClick;
         panel.AddChild(showRegularBarsInfoButton);
         var addBarsButton = new Button { Text = "Add Bars For Active Chart Symbol" };
         addBarsButton.Click += OnAddBarsButtonClick;
         panel.AddChild(addBarsButton);
         var removeBarsButton = new Button { Text = "Remove Bars For Active Chart Symbol" };
         removeBarsButton.Click += OnRemoveBarsButtonClick;
         panel.AddChild(removeBarsButton);
         var updateLastBarButton = new Button { Text = "Update Last Bar" };
         updateLastBarButton.Click += OnUpdateLastBarButtonClick;
         panel.AddChild(updateLastBarButton);
         var updateSymbolSentimentButton = new Button { Text = "Update Symbol Sentiment" };
         updateSymbolSentimentButton.Click += OnUpdateSymbolSentimentButtonClick;
         panel.AddChild(updateSymbolSentimentButton);
         var showSymbolSentimentButton = new Button { Text = "Show Symbol Sentiment" };
         showSymbolSentimentButton.Click += _ => ShowSymbolSentiment();
         panel.AddChild(showSymbolSentimentButton);
         var updateSymbolDynamicLeverageButton = new Button { Text = "Update Symbol Dynamic Leverage" };
         updateSymbolDynamicLeverageButton.Click += OnUpdateSymbolDynamicLeverageButtonClick;
         panel.AddChild(updateSymbolDynamicLeverageButton);
         var showSymbolDynamicLeverageButton = new Button { Text = "Show Symbol Dynamic Leverage" };
         showSymbolDynamicLeverageButton.Click += _ => ShowSymbolDynamicLeverage();
         panel.AddChild(showSymbolDynamicLeverageButton);
         var updateSymbolHolidaysButton = new Button { Text = "Update Symbol Holidays" };
         updateSymbolHolidaysButton.Click += OnUpdateSymbolHolidaysButtonClick;
         panel.AddChild(updateSymbolHolidaysButton);
         var showSymbolHolidaysButton = new Button { Text = "Show Symbol Holidays" };
         showSymbolHolidaysButton.Click += OnShowSymbolHolidaysButtonClick;
         panel.AddChild(showSymbolHolidaysButton);
         var updateSymbolSessionsButton = new Button { Text = "Update Symbol Sessions" };
         updateSymbolSessionsButton.Click += OnUpdateSymbolSessionsButtonClick;
         panel.AddChild(updateSymbolSessionsButton);
         var showSymbolSessionsButton = new Button { Text = "Show Symbol Sessions" };
         showSymbolSessionsButton.Click += OnShowSymbolSessionsButtonClick
         panel.AddChild(showSymbolSessionsButton);
         var updateSymbolFuturesSettingsButton = new Button { Text = "Update Symbol Futures Settings" };
         updateSymbolFuturesSettingsButton.Click += OnUpdateSymbolFuturesSettingsButtonClick;
         panel.AddChild(updateSymbolFuturesSettingsButton);
         var showSymbolFuturesSettingsButton = new Button { Text = "Show Symbol Futures Settings" };
         showSymbolFuturesSettingsButton.Click += OnShowSymbolFuturesSettingsButtonClick;
         panel.AddChild(showSymbolFuturesSettingsButton);
         var block = Asp.SymbolTab.AddBlock("Custom symbol Test");
         block.Child = panel;
         block.Height = 550;
         ChartManager.FramesAdded += OnChartManagerFramesAdded;
         Symbols.Added += OnSymbolAdded;
         Symbols.Removed += OnSymbolRemoved;
     }
     private void OnShowSymbolFuturesSettingsButtonClick(ButtonClickEventArgs obj)
     {
         Print($"Last Trade Time: {_customSymbol.Symbol.FuturesSettings.LastTradeTime} | Expiration Time: {_customSymbol.Symbol.FuturesSettings.ExpirationTime} | Maintenance Margin: {_customSymbol.Symbol.FuturesSettings.MaintenanceMargin}");
     }
     private void OnUpdateSymbolFuturesSettingsButtonClick(ButtonClickEventArgs obj)
     {
         _customSymbol.FuturesSettings = new CustomSymbolFuturesSettings(Server.Time, Server.Time.AddMonths(Random.Shared.Next(1, 10)), Random.Shared.NextDouble() * 100 + 1000);
     }
     private void OnShowSymbolSessionsButtonClick(ButtonClickEventArgs obj)
     {
         Print($"Sessions Count: {_customSymbol.Symbol.MarketHours.Sessions.Count}");
         foreach (var session in _customSymbol.Symbol.MarketHours.Sessions)
         {
             Print($"Start Day: {session.StartDay} | End Day: {session.EndDay} | Start Time: {session.StartTime} | End Time: {session.EndTime}");
         }
     }
     private void OnUpdateSymbolSessionsButtonClick(ButtonClickEventArgs obj)
     {
         var startDay = (DayOfWeek)Random.Shared.Next(0, 6);
         var endDay = (DayOfWeek)((int)startDay + 1);
         var startTime = TimeSpan.FromHours(Random.Shared.Next(0, 22));
         var endTime = startTime.Add(TimeSpan.FromHours(1));
         _customSymbol.MarketHours.Sessions.Add(new CustomSymbolTradingSession(startDay, endDay, startTime, endTime));
     }
     private void OnShowSymbolHolidaysButtonClick(ButtonClickEventArgs obj)
     {
         Print($"Holidays Count: {_customSymbol.Symbol.MarketHours.Holidays.Count}");
         foreach (var holiday in _customSymbol.Symbol.MarketHours.Holidays)
         {
             Print($"Name: {holiday.Name} | Start: {holiday.StartTime:o} | End: {holiday.EndTime:o} | Is Recurring: {holiday.IsRecurring}");
         }
     }
     private void OnUpdateSymbolHolidaysButtonClick(ButtonClickEventArgs obj)
     {
         var startTime = Server.Time.AddMonths(Random.Shared.Next(1, 3));
         var endTime = startTime.AddDays(1);
         var isRecurring = Random.Shared.Next(0, 1) > 0;
         _customSymbol.MarketHours.Holidays.Add(new CustomSymbolTradingHoliday("Test " + Random.Shared.Next().ToString(), startTime, endTime, isRecurring));
     }
     private void ShowSymbolDynamicLeverage()
     {
         Print($"Dynamic Leverage Count: {_customSymbol.Symbol.DynamicLeverage.Count}");
         foreach (var leverage in _customSymbol.Symbol.DynamicLeverage)
         {
             Print($"Volume: {leverage.Volume} | Leverage: {leverage.Leverage}");
         }
     }
     private void OnUpdateSymbolDynamicLeverageButtonClick(ButtonClickEventArgs obj)
     {
         _customSymbol.DynamicLeverage.Add(new CustomSymbolLeverageTier(Random.Shared.NextDouble() * 100 + 1000, 100 + Random.Shared.Next(0, 100)));
     }
     private void OnUpdateSymbolSentimentButtonClick(ButtonClickEventArgs obj)
     {
         _customSymbol.Sentiment.BuyPercentage = _customSymbol.Sentiment.BuyPercentage < 99 ? _customSymbol.Sentiment.BuyPercentage + 1 : _customSymbol.Sentiment.BuyPercentage - 1;
     }
     private void ShowSymbolSentiment()
     {
         Print($"Buy: {_customSymbol.Symbol.Sentiment.BuyPercentage} | Sell: {_customSymbol.Symbol.Sentiment.SellPercentage}");
     }
     private void OnSymbolAdded(SymbolAddedEventArgs args)
     {
         Print($"Symbol Added: {args.SymbolName}");
     }
     private void OnSymbolRemoved(SymbolRemovedEventArgs args)
     {
         Print($"Symbol Removed: {args.SymbolName}");
     }
     private void OnChartManagerFramesAdded(FramesAddedEventArgs obj)
     {
         if (obj.AddedFrames[0] is not ChartFrame chartFrame)
             return;
         Print($"New chart frame added, {chartFrame.Symbol.Name} {chartFrame.TimeFrame.Name}");
     }
     private void OnUpdateLastBarButtonClick(ButtonClickEventArgs obj)
     {
         var changeAmount = (_customBars.Bars.LastBar.High - _customBars.Bars.LastBar.Low) * (Random.Shared.NextDouble() + 0.5) * 2;
         Print($"Changing Last Bar: {_customBars.Bars.LastBar} | change: {changeAmount}");
         _customBars.UpdateLastBar(_customBars.Bars.LastBar.Open, _customBars.Bars.LastBar.Open + changeAmount, _customBars.Bars.LastBar.Open - changeAmount, _customBars.Bars.LastBar.Close + changeAmount, (int)_customBars.Bars.LastBar.TickVolume + 1);
     }
     private void OnRemoveCustomSymbolButtonClick(ButtonClickEventArgs obj)
     {
         if (!CustomSymbols.Remove(_customSymbol))
             return;
         Print($"custom symbol '{_customSymbol.Name}' has been removed.");
         _customSymbol = null;
     }
     private void OnUpdateSymbolBaseAssetButtonClick(ButtonClickEventArgs obj)
     {
         _customSymbol.BaseAsset = Assets.GetAsset(Assets.First(a =&gt; a != _customSymbol.BaseAsset.Name && a != _customSymbol.QuoteAsset.Name));
         ShowSymbolAssets();
     }
     private void OnUpdateSymbolQuoteAssetButtonClick(ButtonClickEventArgs obj)
     {
         _customSymbol.QuoteAsset = Assets.GetAsset(Assets.First(a =&gt; a != _customSymbol.BaseAsset.Name && a != _customSymbol.QuoteAsset.Name));
         ShowSymbolAssets();
     }
     private void ShowSymbolAssets()
     {
         Print($"Base Asset: {_customSymbol.Symbol.BaseAsset.Name} | Quote Asset: {_customSymbol.Symbol.QuoteAsset.Name}");
     }
     private void OnDisplayChartInfoButtonClick(ButtonClickEventArgs obj)
     {
         foreach (var frame in ChartManager)
         {
             if (frame is not ChartFrame chartFrame)
                 continue;
             Print($"Chart, {chartFrame.Symbol.Name} {chartFrame.TimeFrame.Name}");
         }
     }
     private void OnChangeDescriptionButtonClick(ButtonClickEventArgs obj)
     {
         _customSymbol.Description = _customSymbol.Description == InitialDescription ? ChangedDescription : InitialDescription;
         Print($"Changed description to: {_customSymbol.Description}");
     }
     private void OnUpdateSymbolPropertiesButtonClick(ButtonClickEventArgs obj)
     {
         _customSymbol.PipDigits = _customSymbol.PipDigits + 1;
         _customSymbol.TickDigits = _customSymbol.TickDigits + 1;
         _customSymbol.VolumeInUnitsMin = _customSymbol.VolumeInUnitsMin - 10;
         _customSymbol.VolumeInUnitsStep = _customSymbol.VolumeInUnitsStep + 10;
         _customSymbol.VolumeInUnitsMax = _customSymbol.VolumeInUnitsMax + 10;
         _customSymbol.Commission = _customSymbol.Commission + 1;
         _customSymbol.GracePeriod = _customSymbol.GracePeriod + 1;
         _customSymbol.LotSize = _customSymbol.LotSize * 2;
         _customSymbol.PnLConversionFeeRate = _customSymbol.PnLConversionFeeRate + 1;
         _customSymbol.CommissionType = SymbolCommissionType.PercentageOfTradingVolume;
         _customSymbol.MinCommission = _customSymbol.MinCommission + 1;
         _customSymbol.MinCommissionType = SymbolMinCommissionType.QuoteAsset;
         _customSymbol.AdministrativeCharge3DaysRollover = DayOfWeek.Thursday;
         _customSymbol.AdministrativeCharge = _customSymbol.AdministrativeCharge + 1;
         _customSymbol.SwapPeriod = _customSymbol.SwapPeriod + 1;
         _customSymbol.WeekendSwaps = !_customSymbol.WeekendSwaps;
         _customSymbol.SwapLong = _customSymbol.SwapLong + 1;
         _customSymbol.SwapShort = _customSymbol.SwapShort + 1;
         _customSymbol.SwapTimeInMinutes = _customSymbol.SwapTimeInMinutes + 1;
         _customSymbol.Swap3DaysRollover = DayOfWeek.Tuesday;
         _customSymbol.SwapCalculationType = SymbolSwapCalculationType.Percentage;
         _customSymbol.MinDistanceType = SymbolMinDistanceType.Pips;
         _customSymbol.MinTakeProfitDistance = _customSymbol.MinTakeProfitDistance + 1;
         _customSymbol.MinStopLossDistance = _customSymbol.MinStopLossDistance + 1;
         ShowSymbolProperties();
     }
     private void ShowSymbolProperties()
     {
         foreach (var property in _customSymbol.Symbol.GetType().GetProperties())
         {
             Print($"{property.Name}: {property.GetValue(_customSymbol.Symbol)}");
         }
     }
     private void OnPauseOrResumeLoadMoreButtonClick(ButtonClickEventArgs obj)
     {
         _isLoadMoreEnabled = !_isLoadMoreEnabled;
     }
     private void OnAddBarsButtonClick(ButtonClickEventArgs obj)
     {
         if (ChartManager.ActiveFrame is not ChartFrame { Chart: var chart })
             return;
         var bars = _customSymbol.AddBars(chart.TimeFrame);
         Print($"Added Bars, Count: {bars.Bars.Count}, Get: {bars == _customSymbol.GetBars(chart.TimeFrame)}");
     }
     private void OnRemoveBarsButtonClick(ButtonClickEventArgs obj)
     {
         if (ChartManager.ActiveFrame is not ChartFrame { Chart: var chart })
             return;
         var result = _customSymbol.RemoveBars(chart.TimeFrame);
         Print($"Removed Bars, Result: {result}, Get is null: {_customSymbol.GetBars(chart.TimeFrame) == null}");
     }
     private void OnShowRegularBarsInfoButtonClick(ButtonClickEventArgs obj)
     {
         Print($"Regular Bars, Count: {_customBars.Bars.Count}, LastBar: {_customBars.Bars.LastBar}, FirstBar: {_customBars.Bars[0]}");
     }
     private void OnAddCustomSymbolWithBaseButtonClick(ButtonClickEventArgs obj)
     {
         var baseSymbol = Symbols.GetSymbol("EURUSD");
         _customSymbol = CustomSymbols.Add("Custom Symbol With Base", baseSymbol);
         _customSymbol.Symbol.Sentiment.Updated += OnSymbolSentimentUpdated;
         _customSymbol.Description = InitialDescription;
         _customSymbol.BarsNeeded = OnCustomSymbolBarsNeeded;
         baseSymbol.Tick += OnBaseSymbolTick;
         _customSymbol.UpdateQuote(baseSymbol.Bid, baseSymbol.Ask);
         Print($"custom symbol '{_customSymbol.Name}' has been added.");
     }
     private void OnAddCustomSymbolWithoutBaseButtonClick(ButtonClickEventArgs obj)
     {
         var baseAsset = Account.Asset;
         var quoteAsset = Assets.GetAsset(Assets.FirstOrDefault(assetName =&gt; assetName != baseAsset.Name));
         _customSymbol = CustomSymbols.Add("Custom Symbol Without Base", baseAsset, quoteAsset);
         _customSymbol.Symbol.Sentiment.Updated += OnSymbolSentimentUpdated;
         _customSymbol.Description = InitialDescription;
         _customSymbol.BarsNeeded = OnCustomSymbolBarsNeeded;
         var trackingSymbol = Symbols.GetSymbol("EURUSD");
         trackingSymbol.Tick += OnBaseSymbolTick;
         _customSymbol.UpdateQuote(trackingSymbol.Bid, trackingSymbol.Ask);
         Print($"custom symbol '{_customSymbol.Name}' has been added.");
     }
     private void OnSymbolSentimentUpdated(SymbolSentimentUpdatedEventArgs args)
     {
         Print($"SentimentUpdated, Buy: {args.Sentiment.BuyPercentage} | Sell: {args.Sentiment.SellPercentage}");
     }
     private void OnBaseSymbolTick(SymbolTickEventArgs args)
     {
         if (_customSymbol is null)
         {
             args.Symbol.Tick -= OnBaseSymbolTick;
             return;
         }
         _customSymbol.UpdateQuote(args.Symbol.Bid, args.Symbol.Ask);
     }
     private void OnCustomSymbolBarsNeeded(CustomSymbolBarsNeededArgs args)
     {
         Print($"Bars Needed for custom symbol, Symbol: {args.CustomBars.Symbol}, Name: {args.CustomSymbol.Name}");
         _customBars = args.CustomBars;
         MarketData.GetBarsAsync(args.CustomBars.TimeFrame, "EURUSD", bars =&gt;
         {
             Print($"Bars Loaded: {bars.Count}");
             Sleep(TimeSpan.FromSeconds(2));
             args.CustomBars.AppendBars(bars.Select(bar =&gt; new CustomBar(bar.OpenTime, bar.Open, bar.High, bar.Low, bar.Close, (int)bar.TickVolume)));
             args.CustomBars.NeedsMore += _ =&gt;
             {
                 if (!_isLoadMoreEnabled)
                 {
                     Print("Needs more requested but load more is disabled");
                     return;
                 }
                 Print($"Bars NeedsMore");
                 bars.LoadMoreHistoryAsync(loadedMoreArgs =&gt;
                 {
                     Print($"Bars Loaded more: {loadedMoreArgs.Count}");
                     if (loadedMoreArgs.Count == 0)
                         return;
                     Sleep(TimeSpan.FromSeconds(2));
                     args.CustomBars.PrependBars(bars.Take(loadedMoreArgs.Count).Select(bar =&gt; new CustomBar(bar.OpenTime, bar.Open, bar.High, bar.Low, bar.Close, (int)bar.TickVolume)));
                 });
             };
             bars.BarOpened += _ =&gt;
             {
                 if (_customSymbol is null)
                     return;
                 args.CustomBars.AppendBar(new CustomBar(bars.LastBar.OpenTime, bars.LastBar.Open, bars.LastBar.High, bars.LastBar.Low, bars.LastBar.Close, bars.LastBar.TickVolume));
             };
             bars.Tick += _ =&gt;
             {
                 if (_customSymbol is null)
                     return;
                 args.CustomBars.UpdateLastBar(bars.LastBar.Open, bars.LastBar.High, bars.LastBar.Low, bars.LastBar.Close, bars.LastBar.TickVolume);
             };
         });
     }
 }
  1
  2
  3
  4
  5
  6
  7
  8
  9
 10
 11
 12
 13
 14
 15
 16
 17
 18
 19
 20
 21
 22
 23
 24
 25
 26
 27
 28
 29
 30
 31
 32
 33
 34
 35
 36
 37
 38
 39
 40
 41
 42
 43
 44
 45
 46
 47
 48
 49
 50
 51
 52
 53
 54
 55
 56
 57
 58
 59
 60
 61
 62
 63
 64
 65
 66
 67
 68
 69
 70
 71
 72
 73
 74
 75
 76
 77
 78
 79
 80
 81
 82
 83
 84
 85
 86
 87
 88
 89
 90
 91
 92
 93
 94
 95
 96
 97
 98
 99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
 import clr
 clr.AddReference("cAlgo.API")
 from cAlgo.API import *
 from System import Action, TimeSpan, Array, DayOfWeek
 import random
 class Test():
     InitialDescription = "This is custom symbol initial description"
     ChangedDescription = "This is custom symbol changed description"
     def on_start(self):   
         self.isLoadMoreEnabled = True
         self.customSymbol = None
         panel = StackPanel()
         addCustomSymbolWithBaseButton = Button()
         addCustomSymbolWithBaseButton.Text = "Add custom symbol with Base Symbol"
         addCustomSymbolWithBaseButton.Click += self.on_add_custom_symbol_with_base_button_click
         panel.AddChild(addCustomSymbolWithBaseButton)
         addCustomSymbolWithoutBaseButton = Button()
         addCustomSymbolWithoutBaseButton.Text = "Add custom symbol without Base Symbol"
         addCustomSymbolWithoutBaseButton.Click += self.on_add_custom_symbol_without_base_button_click
         panel.AddChild(addCustomSymbolWithoutBaseButton)
         removeCustomSymbolButton = Button()
         removeCustomSymbolButton.Text = "Remove custom symbol"
         removeCustomSymbolButton.Click += self.on_remove_custom_symbol_button_click
         panel.AddChild(removeCustomSymbolButton)
         displayChartInfoButton = Button()
         displayChartInfoButton.Text = "Display Charts Info"
         displayChartInfoButton.Click += self.on_display_chart_info_button_click
         panel.AddChild(displayChartInfoButton)
         changeDescriptionButton = Button()
         changeDescriptionButton.Text = "Change Description"
         changeDescriptionButton.Click += self.on_change_description_button_click
         panel.AddChild(changeDescriptionButton)
         updateSymbolPropertiesButton = Button()
         updateSymbolPropertiesButton.Text = "Update Symbol Properties"
         updateSymbolPropertiesButton.Click += self.on_update_symbol_properties_button_click
         panel.AddChild(updateSymbolPropertiesButton)
         updateSymbolBaseAssetButton = Button()
         updateSymbolBaseAssetButton.Text = "Update Symbol Base Asset"
         updateSymbolBaseAssetButton.Click += self.on_update_symbol_base_asset_button_click
         panel.AddChild(updateSymbolBaseAssetButton)
         updateSymbolQuoteAssetButton = Button()
         updateSymbolQuoteAssetButton.Text = "Update Symbol Quote Asset"
         updateSymbolQuoteAssetButton.Click += self.on_update_symbol_quote_asset_button_click
         panel.AddChild(updateSymbolQuoteAssetButton)
         showSymbolPropertiesButton = Button()
         showSymbolPropertiesButton.Text = "Show Symbol Properties"
         showSymbolPropertiesButton.Click += lambda _: self.show_symbol_properties()
         panel.AddChild(showSymbolPropertiesButton)
         showSymbolAssetsButton = Button()
         showSymbolAssetsButton.Text = "Show Symbol Assets"
         showSymbolAssetsButton.Click += lambda _: self.show_symbol_assets()
         panel.AddChild(showSymbolAssetsButton)
         pauseOrResumeLoadMoreButton = Button()
         pauseOrResumeLoadMoreButton.Text = "Pause / Resume Load More"
         pauseOrResumeLoadMoreButton.Click += self.on_pause_or_resume_load_more_button_click
         panel.AddChild(pauseOrResumeLoadMoreButton)
         showRegularBarsInfoButton = Button()
         showRegularBarsInfoButton.Text = "Show Regular Bars Info"
         showRegularBarsInfoButton.Click += self.on_show_regular_bars_info_button_click
         panel.AddChild(showRegularBarsInfoButton)
         addBarsButton = Button()
         addBarsButton.Text = "Add Bars For Active Chart Symbol"
         addBarsButton.Click += self.on_add_bars_button_click
         panel.AddChild(addBarsButton)
         removeBarsButton = Button()
         removeBarsButton.Text = "Remove Bars For Active Chart Symbol"
         removeBarsButton.Click += self.on_remove_bars_button_click
         panel.AddChild(removeBarsButton)
         updateLastBarButton = Button()
         updateLastBarButton.Text = "Update Last Bar"
         updateLastBarButton.Click += self.on_update_last_bar_button_click
         panel.AddChild(updateLastBarButton)
         updateSymbolSentimentButton = Button()
         updateSymbolSentimentButton.Text = "Update Symbol Sentiment"
         updateSymbolSentimentButton.Click += self.on_update_symbol_sentiment_button_click
         panel.AddChild(updateSymbolSentimentButton)
         showSymbolSentimentButton = Button()
         showSymbolSentimentButton.Text = "Show Symbol Sentiment"
         showSymbolSentimentButton.Click += lambda _: self.show_symbol_sentiment()
         panel.AddChild(showSymbolSentimentButton)
         updateSymbolDynamicLeverageButton = Button()
         updateSymbolDynamicLeverageButton.Text = "Update Symbol Dynamic Leverage"
         updateSymbolDynamicLeverageButton.Click += self.on_update_symbol_dynamic_leverage_button_click
         panel.AddChild(updateSymbolDynamicLeverageButton)
         showSymbolDynamicLeverageButton = Button()
         showSymbolDynamicLeverageButton.Text = "Show Symbol Dynamic Leverage"
         showSymbolDynamicLeverageButton.Click += lambda _: self.show_symbol_dynamic_leverage()
         panel.AddChild(showSymbolDynamicLeverageButton)
         updateSymbolHolidaysButton = Button()
         updateSymbolHolidaysButton.Text = "Update Symbol Holidays"
         updateSymbolHolidaysButton.Click += self.on_update_symbol_holidays_button_click
         panel.AddChild(updateSymbolHolidaysButton)
         showSymbolHolidaysButton = Button()
         showSymbolHolidaysButton.Text = "Show Symbol Holidays"
         showSymbolHolidaysButton.Click += self.on_show_symbol_holidays_button_click
         panel.AddChild(showSymbolHolidaysButton)
         updateSymbolSessionsButton = Button()
         updateSymbolSessionsButton.Text = "Update Symbol Sessions"
         updateSymbolSessionsButton.Click += self.on_update_symbol_sessions_button_click
         panel.AddChild(updateSymbolSessionsButton)
         showSymbolSessionsButton = Button()
         showSymbolSessionsButton.Text = "Show Symbol Sessions"
         showSymbolSessionsButton.Click += self.on_show_symbol_sessions_button_click
         panel.AddChild(showSymbolSessionsButton)
         updateSymbolFuturesSettingsButton = Button()
         updateSymbolFuturesSettingsButton.Text = "Update Symbol Futures Settings"
         updateSymbolFuturesSettingsButton.Click += self.on_update_symbol_futures_settings_button_click
         panel.AddChild(updateSymbolFuturesSettingsButton)
         showSymbolFuturesSettingsButton = Button()
         showSymbolFuturesSettingsButton.Text = "Show Symbol Futures Settings"
         showSymbolFuturesSettingsButton.Click += self.on_show_symbol_futures_settings_button_click
         panel.AddChild(showSymbolFuturesSettingsButton)
         block = api.Asp.SymbolTab.AddBlock("Custom symbol Test")
         block.Child = panel
         block.Height = 550
         api.ChartManager.FramesAdded += self.on_chart_manager_frames_addded
         api.Symbols.Added += self.on_symbol_added
         api.Symbols.Removed += self.on_symbol_removed
     def on_add_custom_symbol_with_base_button_click(self, args):
         baseSymbol = api.Symbols.GetSymbol("EURUSD")
         self.customSymbol = api.CustomSymbols.Add("Custom Symbol With Base", baseSymbol)
         self.customSymbol.Symbol.Sentiment.Updated += self.on_symbol_sentiment_updated
         self.customSymbol.Description = self.InitialDescription
         self.customSymbol.BarsNeeded = Action[CustomSymbolBarsNeededArgs](self.on_custom_symbol_bars_needed)
         baseSymbol.Tick += self.on_base_symbol_tick
         self.customSymbol.UpdateQuote(baseSymbol.Bid, baseSymbol.Ask)
         print(f"custom symbol '{self.customSymbol.Name}' has been added.")
     def on_add_custom_symbol_without_base_button_click(self, args):
         baseAsset = api.Account.Asset
         quoteAsset = api.Assets.GetAsset(next((assetName for assetName in api.Assets if assetName != baseAsset.Name)))
         self.customSymbol = api.CustomSymbols.Add("Custom Symbol Without Base", baseAsset, quoteAsset)
         self.customSymbol.Symbol.Sentiment.Updated += self.on_symbol_sentiment_updated
         self.customSymbol.Description = self.InitialDescription
         self.customSymbol.BarsNeeded = Action[CustomSymbolBarsNeededArgs](self.on_custom_symbol_bars_needed)
         trackingSymbol = api.Symbols.GetSymbol("EURUSD")
         trackingSymbol.Tick += self.on_base_symbol_tick
         self.customSymbol.UpdateQuote(trackingSymbol.Bid, trackingSymbol.Ask)
         print(f"custom symbol '{self.customSymbol.Name}' has been added.")
     def on_symbol_sentiment_updated(self, args):
         print(f"SentimentUpdated, Buy: {args.Sentiment.BuyPercentage} | Sell: {args.Sentiment.SellPercentage}")
     def on_custom_symbol_bars_needed(self, args):
         print(f"Bars Needed for custom symbol, Symbol: {args.CustomBars.Symbol}, Name: {args.CustomSymbol.Name}")
         self.customBars = args.CustomBars
         api.MarketData.GetBarsAsync(args.CustomBars.TimeFrame, "EURUSD", Action[Bars](self.on_bars_received))
     def on_bars_received(self, bars):
         print(f"Bars Loaded: {bars.Count}")
         api.Sleep(2000)
         self.customBars.AppendBars(self.to_array([CustomBar(bar.OpenTime, bar.Open, bar.High, bar.Low, bar.Close, int(bar.TickVolume)) for bar in bars], CustomBar))
         self.customBars.NeedsMore += lambda args: self.on_custom_bars_needs_more(bars, args.CustomBars)
         bars.BarOpened += lambda args: self.on_bar_opened(self.customBars, args.Bars)
         bars.Tick += lambda args: self.on_tick(self.customBars, args.Bars)
     def on_custom_bars_needs_more(self, bars, customBars):
         if self.isLoadMoreEnabled is False:
             print("Needs more requested but load more is disabled")
             return
         print("Bars NeedsMore")
         bars.LoadMoreHistoryAsync(Action[BarsHistoryLoadedEventArgs](lambda args: self.on_bars_more_history_loaded(customBars, bars, args.Count)))
     def on_bars_more_history_loaded(self, customBars, bars, loadedCount):
         print(f"Bars Loaded more: {loadedCount}")
         if loadedCount == 0:
             return
         api.Sleep(2000)
         loadedBars = []
         for i, bar in enumerate(bars):
             if i >= loadedCount:
                 break
             loadedBars.append(CustomBar(bar.OpenTime, bar.Open, bar.High, bar.Low, bar.Close, int(bar.TickVolume)))
         customBars.PrependBars(self.to_array(loadedBars, CustomBar))
     def on_bar_opened(self, customBars, bars):
         if self.customSymbol is None:
             return
         customBars.AppendBar(CustomBar(bars.LastBar.OpenTime, bars.LastBar.Open, bars.LastBar.High, bars.LastBar.Low, bars.LastBar.Close, bars.LastBar.TickVolume))
     def on_tick(self, customBars, bars):
         if self.customSymbol is None:
             return
         customBars.UpdateLastBar(bars.LastBar.Open, bars.LastBar.High, bars.LastBar.Low, bars.LastBar.Close, bars.LastBar.TickVolume)
     def on_base_symbol_tick(self, args):
         if self.customSymbol is None:
             args.Symbol.Tick -= self.on_base_symbol_tick
             return
         self.customSymbol.UpdateQuote(args.Symbol.Bid, args.Symbol.Ask)
     def on_remove_custom_symbol_button_click(self, args):
         if api.CustomSymbols.Remove(self.customSymbol):
             return
         print(f"custom symbol '{self.customSymbol.Name}' has been removed.")
         self.customSymbol = None
     def on_display_chart_info_button_click(self, args):
         for frame in api.ChartManager:
             if isinstance(frame.__implementation__, ChartFrame) == False:
                 continue
             chartFrame = ChartFrame(frame)
             print(f"Chart, {chartFrame.Symbol.Name} {chartFrame.TimeFrame.Name}")
     def on_change_description_button_click(self, args):
         self.customSymbol.Description = self.ChangedDescription if self.customSymbol.Description == self.InitialDescription else self.InitialDescription
         print(f"Changed description to: {self.customSymbol.Description}")
     def on_update_symbol_properties_button_click(self, args):
         self.customSymbol.PipDigits = self.customSymbol.PipDigits + 1
         self.customSymbol.TickDigits = self.customSymbol.TickDigits + 1
         self.customSymbol.VolumeInUnitsMin = self.customSymbol.VolumeInUnitsMin - 10
         self.customSymbol.VolumeInUnitsStep = self.customSymbol.VolumeInUnitsStep + 10
         self.customSymbol.VolumeInUnitsMax = self.customSymbol.VolumeInUnitsMax + 10
         self.customSymbol.Commission = self.customSymbol.Commission + 1
         self.customSymbol.GracePeriod = self.customSymbol.GracePeriod + 1
         self.customSymbol.LotSize = self.customSymbol.LotSize * 2
         self.customSymbol.PnLConversionFeeRate = self.customSymbol.PnLConversionFeeRate + 1
         self.customSymbol.CommissionType = SymbolCommissionType.PercentageOfTradingVolume
         self.customSymbol.MinCommission = self.customSymbol.MinCommission + 1
         self.customSymbol.MinCommissionType = SymbolMinCommissionType.QuoteAsset
         self.customSymbol.AdministrativeCharge3DaysRollover = DayOfWeek.Thursday
         self.customSymbol.AdministrativeCharge = self.customSymbol.AdministrativeCharge + 1
         self.customSymbol.SwapPeriod = self.customSymbol.SwapPeriod + 1
         self.customSymbol.WeekendSwaps = not self.customSymbol.WeekendSwaps
         self.customSymbol.SwapLong = self.customSymbol.SwapLong + 1
         self.customSymbol.SwapShort = self.customSymbol.SwapShort + 1
         self.customSymbol.SwapTimeInMinutes = self.customSymbol.SwapTimeInMinutes + 1
         self.customSymbol.Swap3DaysRollover = DayOfWeek.Tuesday
         self.customSymbol.SwapCalculationType = SymbolSwapCalculationType.Percentage
         self.customSymbol.MinDistanceType = SymbolMinDistanceType.Pips
         self.customSymbol.MinTakeProfitDistance = self.customSymbol.MinTakeProfitDistance + 1
         self.customSymbol.MinStopLossDistance = self.customSymbol.MinStopLossDistance + 1
         self.show_symbol_properties()
     def to_array(self, iterable, itemType):
         length = len(iterable)
         array = Array[itemType](length)
         for i in range(length):
             array[i] = iterable[i]
         return array
     def show_symbol_properties(self):
         for propertyInfo in self.customSymbol.Symbol.GetType().GetProperties():
             print(f"{propertyInfo.Name}: {propertyInfo.GetValue(self.customSymbol.Symbol)}")
     def on_update_symbol_base_asset_button_click(self, args):
         self.customSymbol.BaseAsset = api.Assets.GetAsset(next((assetName for assetName in api.Assets if assetName != self.customSymbol.BaseAsset.Name and assetName != self.customSymbol.QuoteAsset.Name)))
         self.show_symbol_assets()
     def on_update_symbol_quote_asset_button_click(self, args):
         self.customSymbol.QuoteAsset = api.Assets.GetAsset(next((assetName for assetName in api.Assets if assetName != self.customSymbol.BaseAsset.Name and assetName != self.customSymbol.QuoteAsset.Name)))
         self.show_symbol_assets()        
     def show_symbol_assets(self):
         print(f"Base Asset: {self.customSymbol.Symbol.BaseAsset.Name} | Quote Asset: {self.customSymbol.Symbol.QuoteAsset.Name}")
     def on_pause_or_resume_load_more_button_click(self, args):
         self.isLoadMoreEnabled = not self.isLoadMoreEnabled
     def on_show_regular_bars_info_button_click(self, args):
         print(f"Regular Bars, Count: {self.customBars.Bars.Count}, LastBar: {self.customBars.Bars.LastBar}, FirstBar: {self.customBars.Bars[0]}")
     def on_add_bars_button_click(self, args):
         if isinstance(api.ChartManager.ActiveFrame.__implementation__, ChartFrame) == False:
             return
         chart = ChartFrame(api.ChartManager.ActiveFrame).Chart
         bars = self.customSymbol.AddBars(chart.TimeFrame)
         print(f"Added Bars, Count: {bars.Bars.Count}, Get: {bars == self.customSymbol.GetBars(chart.TimeFrame)}")
     def on_remove_bars_button_click(self, args):
         if isinstance(api.ChartManager.ActiveFrame.__implementation__, ChartFrame) == False:
             return
         chart = ChartFrame(api.ChartManager.ActiveFrame).Chart
         result = self.customSymbol.RemoveBars(chart.TimeFrame)
         print(f"Removed Bars, Result: {result}, Get is None: {self.customSymbol.GetBars(chart.TimeFrame) is None}")
     def on_update_last_bar_button_click(self, args):
         changeAmount = (self.customBars.Bars.LastBar.High - self.customBars.Bars.LastBar.Low) * (random.random() + 0.5) * 2
         print(f"Changing Last Bar: {self.customBars.Bars.LastBar} | change: {changeAmount}")
         bars = self.customBars.Bars
         self.customBars.UpdateLastBar(bars.LastBar.Open, bars.LastBar.Open + changeAmount, bars.LastBar.Open - changeAmount, bars.LastBar.Close + changeAmount, int(bars.LastBar.TickVolume + 1))
     def on_update_symbol_sentiment_button_click(self, args):
         self.customSymbol.Sentiment.BuyPercentage = self.customSymbol.Sentiment.BuyPercentage + 1 if self.customSymbol.Sentiment.BuyPercentage < 99 else self.customSymbol.Sentiment.BuyPercentage - 1
     def show_symbol_sentiment(self):
         print(f"Buy: {self.customSymbol.Symbol.Sentiment.BuyPercentage} | Sell: {self.customSymbol.Symbol.Sentiment.SellPercentage}")
     def on_update_symbol_dynamic_leverage_button_click(self, args):
         self.customSymbol.DynamicLeverage.Add(CustomSymbolLeverageTier(random.random() * 100 + 1000, 100 + random.randint(0, 100)))
     def show_symbol_dynamic_leverage(self):
         print(f"Dynamic Leverage Count: {self.customSymbol.Symbol.DynamicLeverage.Count}")
         for leverage in self.customSymbol.Symbol.DynamicLeverage:
             print(f"Volume: {leverage.Volume} | Leverage: {leverage.Leverage}")
     def on_update_symbol_holidays_button_click(self, args):
         startTime = api.Server.Time.AddMonths(random.randint(1, 3))
         endTime = startTime.AddDays(1)
         isRecurring = random.randint(0, 1) > 0
         self.customSymbol.MarketHours.Holidays.Add(CustomSymbolTradingHoliday(f"Test {self.customSymbol.MarketHours.Holidays.Count}", startTime, endTime, isRecurring))
     def on_show_symbol_holidays_button_click(self, args):
         print(f"Holidays Count: {self.customSymbol.Symbol.MarketHours.Holidays.Count}")
         for holiday in self.customSymbol.Symbol.MarketHours.Holidays:
             print(f"Name: {holiday.Name} | Start: {holiday.StartTime} | End: {holiday.EndTime} | Is Recurring: {holiday.IsRecurring}")
     def on_update_symbol_sessions_button_click(self, args):
         startDay = DayOfWeek(random.randint(0, 6))
         endDay = DayOfWeek(int(startDay) + 1)
         startTime = TimeSpan.FromHours(random.randint(0, 22))
         endTime = startTime.Add(TimeSpan.FromHours(1))
         self.customSymbol.MarketHours.Sessions.Add(CustomSymbolTradingSession(startDay, endDay, startTime, endTime))
     def on_show_symbol_sessions_button_click(self, args):
         print(f"Sessions Count: {self.customSymbol.Symbol.MarketHours.Sessions.Count}")
         for session in self.customSymbol.Symbol.MarketHours.Sessions:
             print(f"Start Day: {session.StartDay} | End Day: {session.EndDay} | Start Time: {session.StartTime} | End Time: {session.EndTime}")
     def on_update_symbol_futures_settings_button_click(self, args):
         self.customSymbol.FuturesSettings = CustomSymbolFuturesSettings(api.Server.Time, api.Server.Time.AddMonths(random.randint(1, 10)), random.random() * 100 + 1000)
     def on_show_symbol_futures_settings_button_click(self, args):
         symbol = self.customSymbol.Symbol
         print(f"Last Trade Time: {symbol.FuturesSettings.LastTradeTime} | Expiration Time: {symbol.FuturesSettings.ExpirationTime} | Maintenance Margin: {symbol.FuturesSettings.MaintenanceMargin}")
     def on_chart_manager_frames_addded(self, args):
         for frame in args.AddedFrames:
             if isinstance(frame.__implementation__, ChartFrame) == False:
                 continue
             chartFrame = ChartFrame(frame)
             print(f"New chart frame added, {chartFrame.Symbol.Name} {chartFrame.TimeFrame.Name}")
     def on_symbol_added(self, args):
         print(f"Symbol Added: {args.SymbolName}")
     def on_symbol_removed(self, args):
         print(f"Symbol Removed: {args.SymbolName}")

See Also

Methods

Add (2)

Add (1 of 2)

Summary

Adds a new custom symbol.

Signature

1
public abstract CustomSymbol Add(string name, Asset baseAsset, Asset quoteAsset)

Parameters

Name Type Description
name string Custom symbol unique name.
baseAsset Asset Symbol base asset.
quoteAsset Asset Symbol quote asset.

Return Value

CustomSymbol

Add (2 of 2)

Summary

Adds a new custom symbol based on existing symbol.

Signature

1
public abstract CustomSymbol Add(string name, Symbol baseSymbol)

Parameters

Name Type Description
name string Custom symbol unique name.
baseSymbol Symbol Base symbol.

Return Value

CustomSymbol

Remove

Summary

Removes a custom symbol.

Signature

1
public abstract bool Remove(CustomSymbol customSymbol)

Parameters

Name Type Description
customSymbol CustomSymbol Custom symbol

Return Value

bool

Get

Summary

Returns a custom symbol by it's name.

Signature

1
public abstract CustomSymbol Get(string name)

Parameters

Name Type Description
name string Name of custom symbol

Return Value

CustomSymbol