private void CalculateSlOrTpTarget(bool slChosen = true) { var orders = gridOrders.GetRowValues<MarketOrder>(false).Where(o => o.ID != 0).ToList(); if (orders.Count == 0) return; if (orders.Select(o => o.Symbol).Distinct().Count() != 1) { MessageBox.Show(Localizer.GetString("MessageCannotSetupCommonSlTp")); return; } var symbol = orders[0].Symbol; var active = DalSpot.Instance.GetActiveFromPair(symbol, false); // посчитать цену паритета var priceParity = 0f; var priceParityDenom = orders.Sum(o => o.Side*o.Volume); if (priceParityDenom != 0) priceParity = orders.Sum(o => o.Side*o.Volume*o.PriceEnter)/priceParityDenom; // выбрать цель - пункты или контрвалюта, указать смещение от паритета var dlg = new CloseTargetDlg(active, priceParity); if (dlg.ShowDialog() != DialogResult.OK) return; // для ордеров вычислить TP - SL, соответствующий указанной цене / пунктам var target = dlg.TargetNumber; float price = 0; if (dlg.Units == CloseTargetDlg.UnitType.Points) // пунктам... { var sumSign = orders.Sum(o => o.Side); if (sumSign == 0) { MessageBox.Show(Localizer.GetString("MessageSumPointsBuysAndSellsAreNil")); return; } var sideTotal = Math.Sign(sumSign); target = DalSpot.Instance.GetAbsValue(symbol, target); price = sideTotal * target + orders.Sum(o => o.Side * o.PriceEnter) / sumSign; } else if (dlg.Units == CloseTargetDlg.UnitType.Counter) { // прибыль в контрвалюте? var sumVolume = orders.Sum(o => o.Side * o.Volume); if (sumVolume == 0) { MessageBox.Show(Localizer.GetString("MessageSumVolmBuysAndSellsAreNil")); return; } //var sideTotal = Math.Sign(sumVolume); price = (target + orders.Sum(o => o.Side * o.PriceEnter * o.Volume)) / sumVolume; } else { // цена price = dlg.TargetNumber; } // получить текущую цену, для сравнения var quote = QuoteStorage.Instance.ReceiveValue(symbol); if (quote == null) { MessageBox.Show(Localizer.GetString("MessageNoQuote") + " " + symbol); return; } // предупредить пользователя int countTp = 0, countSl = 0; foreach (var order in orders) { var isSl = (order.Side > 0 && price < quote.bid) || (order.Side < 0 && price > quote.bid); if (isSl) countSl++; else countTp++; } var priceStr = price.ToStringUniformPriceFormat(); var msgParts = new List<string>(); if (countSl > 0) msgParts.Add( string.Format(Localizer.GetString("MessagePtrWillBeSetForNPosFmt"), countSl) + " SL = " + priceStr); if (countTp > 0) msgParts.Add(string.Format(Localizer.GetString("MessagePtrWillBeSetForNPosFmt"), countTp) + " TP = " + priceStr); if (MessageBox.Show(string.Join(Environment.NewLine, msgParts) + ". " + Localizer.GetString("TitleProceed") + "?", Localizer.GetString("TitleConfirmation"), MessageBoxButtons.YesNo) == DialogResult.No) return; // таки выставить SL - TP foreach (var order in orders) { var isSl = (order.Side > 0 && price < quote.bid) || (order.Side < 0 && price > quote.bid); if (isSl) order.StopLoss = price; else order.TakeProfit = price; // отправить запрос на изменение ордера MainForm.Instance.SendEditMarketRequestSafe(order); } }
private void CalculateSlOrTpTarget(bool slChosen = true) { var orders = gridOrders.GetRowValues <MarketOrder>(false).Where(o => o.ID != 0).ToList(); if (orders.Count == 0) { return; } if (orders.Select(o => o.Symbol).Distinct().Count() != 1) { MessageBox.Show(Localizer.GetString("MessageCannotSetupCommonSlTp")); return; } var symbol = orders[0].Symbol; var active = DalSpot.Instance.GetActiveFromPair(symbol, false); // посчитать цену паритета var priceParity = 0f; var priceParityDenom = orders.Sum(o => o.Side * o.Volume); if (priceParityDenom != 0) { priceParity = orders.Sum(o => o.Side * o.Volume * o.PriceEnter) / priceParityDenom; } // выбрать цель - пункты или контрвалюта, указать смещение от паритета var dlg = new CloseTargetDlg(active, priceParity); if (dlg.ShowDialog() != DialogResult.OK) { return; } // для ордеров вычислить TP - SL, соответствующий указанной цене / пунктам var target = dlg.TargetNumber; float price = 0; if (dlg.Units == CloseTargetDlg.UnitType.Points) // пунктам... { var sumSign = orders.Sum(o => o.Side); if (sumSign == 0) { MessageBox.Show(Localizer.GetString("MessageSumPointsBuysAndSellsAreNil")); return; } var sideTotal = Math.Sign(sumSign); target = DalSpot.Instance.GetAbsValue(symbol, target); price = sideTotal * target + orders.Sum(o => o.Side * o.PriceEnter) / sumSign; } else if (dlg.Units == CloseTargetDlg.UnitType.Counter) { // прибыль в контрвалюте? var sumVolume = orders.Sum(o => o.Side * o.Volume); if (sumVolume == 0) { MessageBox.Show(Localizer.GetString("MessageSumVolmBuysAndSellsAreNil")); return; } //var sideTotal = Math.Sign(sumVolume); price = (target + orders.Sum(o => o.Side * o.PriceEnter * o.Volume)) / sumVolume; } else { // цена price = dlg.TargetNumber; } // получить текущую цену, для сравнения var quote = QuoteStorage.Instance.ReceiveValue(symbol); if (quote == null) { MessageBox.Show(Localizer.GetString("MessageNoQuote") + " " + symbol); return; } // предупредить пользователя int countTp = 0, countSl = 0; foreach (var order in orders) { var isSl = (order.Side > 0 && price < quote.bid) || (order.Side <0 && price> quote.bid); if (isSl) { countSl++; } else { countTp++; } } var priceStr = price.ToStringUniformPriceFormat(); var msgParts = new List <string>(); if (countSl > 0) { msgParts.Add( string.Format(Localizer.GetString("MessagePtrWillBeSetForNPosFmt"), countSl) + " SL = " + priceStr); } if (countTp > 0) { msgParts.Add(string.Format(Localizer.GetString("MessagePtrWillBeSetForNPosFmt"), countTp) + " TP = " + priceStr); } if (MessageBox.Show(string.Join(Environment.NewLine, msgParts) + ". " + Localizer.GetString("TitleProceed") + "?", Localizer.GetString("TitleConfirmation"), MessageBoxButtons.YesNo) == DialogResult.No) { return; } // таки выставить SL - TP foreach (var order in orders) { var isSl = (order.Side > 0 && price < quote.bid) || (order.Side <0 && price> quote.bid); if (isSl) { order.StopLoss = price; } else { order.TakeProfit = price; } // отправить запрос на изменение ордера MainForm.Instance.SendEditMarketRequestSafe(order); } }