/// <summary> /// logic close position /// логика зыкрытия позиции /// </summary> private void LogicClosePosition() { List <Position> openPositions = _tab.PositionsOpenAll; for (int i = 0; openPositions != null && i < openPositions.Count; i++) { if (openPositions[i].State != PositionStateType.Open) { continue; } if (openPositions[i].Direction == Side.Buy) { decimal priceClose = _lastPcDown; _tab.CloseAtTrailingStop(openPositions[i], priceClose, priceClose - Slippage.ValueInt * _tab.Securiti.PriceStep); } else { decimal priceClose = _lastPcUp; _tab.CloseAtTrailingStop(openPositions[i], priceClose, priceClose + Slippage.ValueInt * _tab.Securiti.PriceStep); } } }
/// <summary> /// проверить выход из позиции /// </summary> private decimal CheckExit(Position position, List <IPattern> patterns, List <Candle> candles, int index, decimal price) { if (CheckInter(patterns, candles, index, WeigthToExit)) { // если выходим по паттернам return(GetPriceExit(position, price, ExitToPatternsSleepage)); } if (TrailingStopIsOn) { if (position.Direction == Side.Buy) { decimal newTrail = candles[candles.Count - 1].Close - candles[candles.Count - 1].Close * (TreilingStopValue / 100); _tab.CloseAtTrailingStop(position, newTrail, newTrail - _tab.Securiti.PriceStep * StopOrderSleepage); } else { decimal newTrail = candles[candles.Count - 1].Close + candles[candles.Count - 1].Close * (TreilingStopValue / 100); _tab.CloseAtTrailingStop(position, newTrail, newTrail + _tab.Securiti.PriceStep * StopOrderSleepage); } } // проверить выход по времени if (ExitFromSomeCandlesIsOn) { if (GetIndexInter(position.TimeOpen, candles) + ExitFromSomeCandlesValue <= index) { return(GetPriceExit(position, price, ExitFromSomeCandlesSleepage)); } } return(0); }
void Save_profit() // для выставления профита портфеля { if (sav_profit_metod_vkl == false) { return; } List <Position> positions = _tab.PositionsOpenAll; if (positions.Count != 0) { decimal g = Greed(); // вычисляет жадность decimal zn = _tab.PositionsLast.ProfitPortfolioPunkt; // смотрим прибыльность Percent_birgi(); market_price = _tab.PriceCenterMarketDepth; decimal pr_poz = _tab.PositionsLast.EntryPrice; if (pr_poz < market_price + _kom / 2 + _do_profit_temp) // цена открытия позиции ниже рынка +комиссия + расстояние от профита { if (zn > g) // прибыль больше жадности { _tab.CloseAtTrailingStop(positions[0], market_price - _do_profit_temp, market_price - _do_profit_temp - slippage.ValueDecimal * _tab.Securiti.PriceStep); Console.WriteLine(" прибыль больше жадности - включился трейлинг Прибыли от " + _temp_greed + " $ " + (_tab.PriceCenterMarketDepth - _do_profit_temp - slippage.ValueDecimal * _tab.Securiti.PriceStep)); } } else if (zn > g && prof_on.ValueDecimal <= percent_tovara) // если товара уже больше значения prof_on и есть прибыль в сделке - выставляем трейлик стоп прибыли { _tab.CloseAtTrailingStop(positions[0], market_price - _kom / 2 - _do_profit_temp, market_price - _kom / 2 - _do_profit_temp - slippage.ValueDecimal * _tab.Securiti.PriceStep); Console.WriteLine(" сработал else if - товара больше " + prof_on.ValueDecimal + " %, Включили трейлинг Прибыли от _gde_stop_tmp "); } } }
/// <summary> /// logic close position /// логика зыкрытия позиции /// </summary> private void LogicClosePosition() { List <Position> openPositions = _tab.PositionsOpenAll; for (int i = 0; openPositions != null && i < openPositions.Count; i++) { if (openPositions[i].State != PositionStateType.Open) { continue; } List <decimal> ma = _Ssma.DataSeries.ByName("Ma"); decimal lastma = ma[ma.Count - 1]; if (openPositions[i].Direction == Side.Buy) { decimal newfr = GetLastFractail(Fractail.DataSeries.ByName("SeriesDown")); _tab.CloseAtTrailingStop(openPositions[i], newfr, newfr - Slipage.ValueDecimal); _tab.CloseAtProfit(openPositions[i], lastma + Slipage.ValueDecimal, lastma); } else { decimal newfr = GetLastFractail(Fractail.DataSeries.ByName("SeriesUp")); _tab.CloseAtTrailingStop(openPositions[i], newfr, newfr + Slipage.ValueDecimal); _tab.CloseAtProfit(openPositions[i], lastma - Slipage.ValueDecimal, lastma); } } }
private void LogicClosePosition(List <Position> positions, List <Candle> candles) { if (positions == null || positions.Count == 0) { return; } for (int i = 0; i < positions.Count; i++) { if (positions[i].State != PositionStateType.Open) { continue; } if (positions[i].State == PositionStateType.Closing) { continue; } if (ExitType.ValueString == "Sma") { if (positions[i].Direction == Side.Buy) { if (candles[candles.Count - 1].Close < _sma.DataSeries[0].Last) { _tab.CloseAtMarket(positions[i], positions[i].OpenVolume); } } else { if (candles[candles.Count - 1].Close > _sma.DataSeries[0].Last) { _tab.CloseAtMarket(positions[i], positions[i].OpenVolume); } } } else if (ExitType.ValueString == "Traling") { if (positions[i].Direction == Side.Buy) { _tab.CloseAtTrailingStop(positions[i], candles[candles.Count - 1].Close - candles[candles.Count - 1].Close * TralingStopLength.ValueDecimal / 100, candles[candles.Count - 1].Close - candles[candles.Count - 1].Close * TralingStopLength.ValueDecimal / 100); } else { _tab.CloseAtTrailingStop(positions[i], candles[candles.Count - 1].Close + candles[candles.Count - 1].Close * TralingStopLength.ValueDecimal / 100, candles[candles.Count - 1].Close + candles[candles.Count - 1].Close * TralingStopLength.ValueDecimal / 100); } } } }
/// <summary> /// logic close position /// логика зыкрытия позиции /// </summary> private void LogicClosePosition(List <Candle> candles, Position position) { if (position.Direction == Side.Buy) { _tab.CloseAtTrailingStop(position, _lastClose - _lastClose * TrailStop.ValueDecimal / 100, _lastClose - _lastClose * TrailStop.ValueDecimal / 100); } if (position.Direction == Side.Sell) { _tab.CloseAtTrailingStop(position, _lastClose + _lastClose * TrailStop.ValueDecimal / 100, _lastClose + _lastClose * TrailStop.ValueDecimal / 100); } }
void Save_profit() // для выставления профита портфеля { if (sav_profit_metod_vkl == false) { return; } List <Position> positions = _tab.PositionsOpenAll; if (positions.Count != 0) { Percent_birgi(); market_price = _tab.PriceCenterMarketDepth; decimal pr_poz = _tab.PositionsLast.EntryPrice; if (pr_poz < market_price + _kom / 2 + profit.ValueInt) { decimal g = Greed(); // вычисляет жадность decimal zn = _tab.PositionsLast.ProfitPortfolioPunkt; // смотрим прибыльность if (zn > g) { _tab.CloseAtTrailingStop(positions[0], _tab.PriceCenterMarketDepth - profit.ValueInt, _tab.PriceCenterMarketDepth - profit.ValueInt - slippage.ValueDecimal * _tab.Securiti.PriceStep); Console.WriteLine(" Включился трейлинг Прибыли от " + _temp_greed + " $ " + (_tab.PriceCenterMarketDepth - profit.ValueInt - slippage.ValueDecimal * _tab.Securiti.PriceStep)); } } } }
// Методы входящие в логику робота void Save_prifit() // для выставления профита портфеля // добавить! в релиз + _kom { Percent_birgi(); // расчет величины в пунктах процента биржи List <Position> positions = _vkl.PositionsOpenAll; if (_vkl.MarketDepth.Bids[0].Price > _vkl.PositionsLast.EntryPrice + Step(DeltaVerx + OtProfit) + _kom) // добавить! в релиз + _kom { _vkl.CloseAtTrailingStop(positions[0], _vkl.MarketDepth.Bids[0].Price + Step(OtProfit) + _kom, _vkl.MarketDepth.Bids[0].Price - Step(OtProfit)); } Piramida(); }
/// <summary> /// close one pos /// логика закрытия позиции /// </summary> private void ReloadTrailingPosition(Position position) { List <Position> openPositions = _tab.PositionsOpenAll; for (int i = 0; openPositions != null && i < openPositions.Count; i++) { if (openPositions[i].Direction == Side.Buy) { decimal valueDown = _bollinger.DataSeries[1].Values[_bollinger.DataSeries[1].Values.Count - 1]; _tab.CloseAtTrailingStop( openPositions[i], valueDown, valueDown - Slippage.ValueInt * _tab.Securiti.PriceStep); } else { decimal valueUp = _bollinger.DataSeries[0].Values[_bollinger.DataSeries[0].Values.Count - 1]; _tab.CloseAtTrailingStop( openPositions[i], valueUp, valueUp + Slippage.ValueInt * _tab.Securiti.PriceStep); } } }
void Save_prifit() // для выставления профита портфеля { if (vkl_profit.ValueBool == false) { return; } Percent_birgi(); // расчет величины в пунктах процента биржи List <Position> positions = _vklad.PositionsOpenAll; if (_vklad.MarketDepth.Bids[0].Price > _vklad.PositionsLast.EntryPrice + profit.ValueInt + _kom + slippage.ValueDecimal * _vklad.Securiti.PriceStep) { _vklad.CloseAtTrailingStop(positions[0], _vklad.MarketDepth.Bids[0].Price - profit.ValueInt, _vklad.MarketDepth.Asks[0].Price - profit.ValueInt - slippage.ValueDecimal * _vklad.Securiti.PriceStep); } }
/// <summary> /// Установка трейлинг стопа (не используется в стратегии!) /// </summary> /// <param name="position">Позиция для которой устанавливается трейлинг стоп</param> private void SetTrailingStop(Position position) { // размер трейлинг стопа в процентах (при использовании трейлинг стопа в стратегии перенести в настроечные параметры) int trailingStopPercent = 7; // цена активации стоп ордера decimal priceActivation; // цена стоп ордера decimal priceOrder; // установка трейлинг стопа для позиции лонг if (position.Direction == Side.Buy) { // цена активации ставится величину трейлинг стопа от минимума последней свечи priceActivation = _lowLastCandle * (1 - trailingStopPercent / 100.0m); // цена стоп ордера ставится ниже на величину двух проскальзываний от цены активации priceOrder = priceActivation - 2 * Slippage.ValueInt * _tab.Securiti.PriceStep; _tab.CloseAtTrailingStop(position, priceActivation, priceOrder); } // установка трейлинг стопа для позиции шорт else if (position.Direction == Side.Sell) { // цена активации ставится на величину трейлинг стопа от максимума последней свечи priceActivation = _highLastCandle * (1.0m + trailingStopPercent / 100.0m); // цена стоп ордера ставится выше на величину двух проскальзываний от цены активации priceOrder = priceActivation + 2 * Slippage.ValueInt * _tab.Securiti.PriceStep; _tab.CloseAtTrailingStop(position, priceActivation, priceOrder); } return; }
private void ClosePositionLogic(Position position, List <Candle> candles) { if (position.State == PositionStateType.Closing) { return; } decimal stopPrice = position.EntryPrice - position.EntryPrice * BaseStopPercent.ValueDecimal / 100; if (position.Direction == Side.Sell) { stopPrice = position.EntryPrice + position.EntryPrice * BaseStopPercent.ValueDecimal / 100; } decimal smaValue = _sma.DataSeries[0].Last; decimal lastCandlePrice = candles[candles.Count - 1].Close; if (position.Direction == Side.Buy && smaValue > stopPrice && lastCandlePrice > smaValue) { stopPrice = smaValue; } if (position.Direction == Side.Sell && smaValue < stopPrice && lastCandlePrice < smaValue) { stopPrice = smaValue; } decimal priceOrder = stopPrice; if (StartProgram == StartProgram.IsOsTrader) { if (position.Direction == Side.Buy) { priceOrder = priceOrder - _tab.Securiti.PriceStep * Slippage.ValueInt; } if (position.Direction == Side.Sell) { priceOrder = priceOrder + _tab.Securiti.PriceStep * Slippage.ValueInt; } } _tab.CloseAtTrailingStop(position, stopPrice, priceOrder); }
// Торговая логика: private void _tab_CandleFinishedEvent(List <Candle> candles) { if (IsOn.ValueBool == false) { return; } // Берем индикатор priceChannel, все его значения и сравниваем с длинной свечек if (_priceChannel.LenghtUpLine > candles.Count || _priceChannel.LenghtDownLine > candles.Count) { return; // Если верняя или нижняя длинна индикатора больше количества свечек - выходим } List <Position> positions = _tab.PositionsOpenAll; // Для торговли реальными деньгами на биржах криптовалют decimal portfo РАЗКОММЕНТИРОВАТЬ!!! //decimal portfo = _tab.Portfolio.GetPositionOnBoard().Find(pos => pos.SecurityNameCode == ticket).ValueCurrent; decimal lastPrice = candles[candles.Count - 1].Close; // Сохраняем в переменной lastPrice цену закрытия последней свечи // Логика входа в позицию Long if (positions.Count == 0) { decimal channel = _priceChannel.ValuesUp[_priceChannel.ValuesUp.Count - 2]; // Берем предпоследнее значение верхней линии канала if (lastPrice > channel) { // Для входа в позицию используем лучшую цену продажи + проскальзывание _tab.BuyAtLimit(GetVolume(), _tab.PriceBestAsk + _tab.Securiti.PriceStep * Slippage.ValueDecimal); } } // Логика выхода из позиции Long else if (positions.Count != 0) { decimal stopActivation = lastPrice - lastPrice * (StopValue.ValueDecimal / 100); // Беру последнюю цену и отнимаю от нее параметр, который ввел в оптим. decimal stopOrderPrice = stopActivation - _tab.Securiti.PriceStep * Slippage.ValueDecimal; _tab.CloseAtTrailingStop(positions[0], stopActivation, stopOrderPrice); } }
/// <summary> /// событие завершения свечи /// </summary> /// <param name="candles">массив свечек</param> /// <param name="tab">источник по которому произошло событие</param> private void NewCandleEvent(List <Candle> candles, BotTabSimple tab) { // 1 Если поза есть, то по трейлинг стопу закрываем // 2 Позы нет. Открывать лонг, если последние N свечей мы были над скользящей средней if (Regime.ValueString == "Off") { return; } if (candles.Count < 10) { return; } if (candles.Count - 1 - CandlesLookBack.ValueInt - 1 <= 0) { return; } List <Position> positions = tab.PositionsOpenAll; if (positions.Count == 0) { // логика открытия Aindicator sma = (Aindicator)tab.Indicators[0]; for (int i = candles.Count - 1; i >= 0 && i > candles.Count - 1 - CandlesLookBack.ValueInt; i--) { decimal curSma = sma.DataSeries[0].Values[i]; if (curSma == 0) { return; } if (candles[i].Close < curSma) { return; } } if (candles[candles.Count - 1 - CandlesLookBack.ValueInt - 1].Close > sma.DataSeries[0].Values[candles.Count - 1 - CandlesLookBack.ValueInt - 1]) { return; } tab.BuyAtLimit(Volume.ValueDecimal, tab.PriceBestAsk + tab.Securiti.PriceStep * Slippage.ValueInt); } else { Position pos = positions[0]; if (pos.State != PositionStateType.Open) { return; } decimal close = candles[candles.Count - 1].High; decimal priceActivation = close - close * TrailStop.ValueDecimal / 100; decimal priceOrder = priceActivation - tab.Securiti.PriceStep * Slippage.ValueInt; tab.CloseAtTrailingStop(pos, priceActivation, priceOrder); } }
private void _tab_MarketDepthUpdateEvent(MarketDepth marketDepth) // начало торгов { List <Position> positions = _tab.PositionsOpenAll; if (positions.Count != 0) { if (price > _tab.PositionsLast.EntryPrice) { StopLoss(); } } decimal priceOrder = price + profit.ValueInt + slippage.ValueDecimal * _tab.Securiti.PriceStep; decimal priceActivation = price + profit.ValueInt; if (positions.Count != 0) { if (price < _tab.PositionsLast.EntryPrice - profit.ValueInt - _kom - slippage.ValueDecimal) { _tab.CloseAtTrailingStop(positions[0], priceActivation, priceOrder); Console.WriteLine(" Включился Трейлинг Профит по - " + priceActivation); } } if (vkl_Robota.ValueBool == false) { return; } Percent_birgi(); Balans_tovara(); if (price < _uroven.ValueDecimal) { decimal vol = tovar / part_tovara.ValueInt; if (_tab.PositionsOpenAll.Count == 0) { if (vol > Lot() + min_lot.ValueDecimal / 4) { //объем входа- >> _tab.SellAtMarket(Okruglenie(vol - min_lot.ValueDecimal / 4)); Console.WriteLine(" начали продавать часть товара) по цене " + price + " На объем " + (vol - min_lot.ValueDecimal / 4) * price); Thread.Sleep(1500); } } if (positions.Count != 0) { if (price < _tab.PositionsLast.EntryPrice - _kom - do_piram.ValueDecimal) { Piramid(); } } } if (_tab.PositionsOpenAll.Count == 0) // сдвиг уровня работы { if (price > _uroven.ValueDecimal) // цена выше уровня работы + величина движения + комиссия { decimal r = price - _uroven.ValueDecimal; // вычисляем разницу (на сколько изменилась цена) if (r > dvig.ValueInt) { _uroven.ValueDecimal = _uroven.ValueDecimal + (r - ot_rinka.ValueInt); Console.WriteLine(" Позиций нет, уровень срабатывания поднимаем, теперь " + _uroven.ValueDecimal); } } } }
/// <summary> /// logic close position /// логика зыкрытия позиции /// </summary> private void LogicClosePosition() { List <Position> openPositions = _tab.PositionsOpenAll; for (int i = 0; openPositions != null && i < openPositions.Count; i++) { if (openPositions[i].State != PositionStateType.Open) { continue; } /* * if (openPositions[i].Direction == Side.Buy) * { * if(FastMA.Values[FastMA.Values.Count - 2] > SlowMA.Values[SlowMA.Values.Count - 2] * && FastMA.Values[FastMA.Values.Count - 1] < SlowMA.Values[SlowMA.Values.Count - 1]) * { * _tab.CloseAllAtMarket(); * return; * } * } * else * { * if (FastMA.Values[FastMA.Values.Count - 2] < SlowMA.Values[SlowMA.Values.Count - 2] * && FastMA.Values[FastMA.Values.Count - 1] > SlowMA.Values[SlowMA.Values.Count - 1]) * { * _tab.CloseAllAtMarket(); * return; * } * } */ if (openPositions[i].Direction == Side.Buy) { /* * if((_tab.CandlesAll.Last().Close - openPositions[i].EntryPrice)/ openPositions[i].EntryPrice > 0.005m) * { * decimal st = openPositions[i].EntryPrice + 3 * openPositions[i].EntryPrice * openPositions[i].ComissionValue / 100; * _tab.CloseAtTrailingStop(openPositions[i], st, st - Slipage.ValueDecimal); * } */ decimal priceClose = _lastPcDown; decimal newfr = GetLastFractail(Fractail.DataSeries.ByName("SeriesDown")); //_tab.CloseAtTrailingStop(openPositions[i], priceClose, priceClose - Slipage.ValueDecimal); _tab.CloseAtTrailingStop(openPositions[i], newfr, newfr - Slipage.ValueDecimal); } else { /* * if ((openPositions[i].EntryPrice -_tab.CandlesAll.Last().Close ) / openPositions[i].EntryPrice > 0.005m) * { * decimal st = openPositions[i].EntryPrice - 3 * openPositions[i].EntryPrice * openPositions[i].ComissionValue / 100; * _tab.CloseAtTrailingStop(openPositions[i], st, st - Slipage.ValueDecimal); * } */ decimal priceClose = _lastPcUp; decimal newfr = GetLastFractail(Fractail.DataSeries.ByName("SeriesUp")); //_tab.CloseAtTrailingStop(openPositions[i], priceClose, priceClose + Slipage.ValueDecimal); _tab.CloseAtTrailingStop(openPositions[i], newfr, newfr + Slipage.ValueDecimal); } } }