input bool debug = false;
input int initial_stoploss = 150;
input int risk_percent = 0;

double angle_coeff = 10.0;
int profit_step = 25;
int ts_levels[50];
int digit_coeff;
double lot;

void OnInit()
{
	// detect 5-digit broker
	if (Digits == 5 || Digits == 3)
		digit_coeff = 10;
	else
		digit_coeff = 1;

	// generate array of SL levels
	ts_levels[2] = 15 * digit_coeff;

	int k = 15 * digit_coeff;
	for (int i = 0, j = 3; i < 40; i++, j++)
	{
		k += (10 + i) * digit_coeff;
		ts_levels[i+3] = k;
	}
}

void OnTick()
{
	int result;

	if (OrdersTotal() > 0)
	{
		result = OrderSelect(0, SELECT_BY_POS, MODE_TRADES);
		
		int price_level = OrderProfit() / profit_step;

		if (price_level >= ArraySize(ts_levels))
			price_level = ArraySize(ts_levels) - 1;
		
		if (price_level > 1)	// price > 50 pips?
		{
			double trail;
		
			if (OrderType() == OP_BUY)
			{
				trail = NormalizeDouble(OrderOpenPrice() + ts_levels[price_level] * Point, Digits);

				if (trail > OrderStopLoss())
					result = OrderModify(OrderTicket(), 0, trail, OrderTakeProfit(), 0, clrWhite);
			}
			else
			{
				trail = NormalizeDouble(OrderOpenPrice() - ts_levels[price_level] * Point, Digits);

				if (trail < OrderStopLoss())
					result = OrderModify(OrderTicket(), 0, trail, OrderTakeProfit(), 0, clrWhite);
			}
		}

		return;
	}

	if (Volume[0] > 1)
		return;

	// no orders, check for new possible position
	double chikou = iIchimoku(NULL, 0, 9, 26, 52, MODE_CHIKOUSPAN, 26);
	double tenkan = iIchimoku(NULL, 0, 9, 26, 52, MODE_TENKANSEN, 26);
	double macd_main = iMACD(NULL, 0, 12, 26, 9, PRICE_CLOSE, MODE_MAIN, 1);
	double macd_sig = iMACD(NULL, 0, 12, 26, 9, PRICE_CLOSE, MODE_SIGNAL, 1);
	double stoch_curr = iStochastic(NULL, 0, 5, 3, 3, MODE_SMA, 0, MODE_SIGNAL, 1);
	double stoch_prev = iStochastic(NULL, 0, 5, 3, 3, MODE_SMA, 0, MODE_SIGNAL, 2);

	if (debug)
		PrintFormat("Close of prev bar: %.5f, Chikou: %.5f, Tenkan: %.5f, CCI angle: %d, MACD main: %.5f, MACD sig: %.5f", Close[1], chikou, tenkan, cci_angle(1), macd_main, macd_sig);
		
	// calculate lot
	if (risk_percent > 0)
		lot = AccountFreeMargin() * risk_percent / 100 / (initial_stoploss * digit_coeff * MarketInfo(Symbol(), MODE_TICKVALUE));
	else
		lot = 0.1;

	// check for buy
	if (chikou > Close[1] &&
		tenkan < chikou &&
		//Open[0] >= Close[1] &&
		is_ha_smooth_rising(1) &&
		is_ha_smooth_rising(2) &&
		is_ha_rising(1) &&
		is_ha_rising(2) &&
		cci_angle(1) > 45 &&
		macd_main > macd_sig &&
		stoch_curr > stoch_prev)
	{
		result = OrderSend(Symbol(), OP_BUY, lot, Ask, 3, NormalizeDouble(Bid - initial_stoploss*Point*digit_coeff, Digits), 0, "", 0, 0, Blue);
	}
	// check for sell
	else if (chikou < Close[1] &&
		tenkan > chikou &&
		//Open[0] <= Close[1] &&
		!is_ha_smooth_rising(1) &&
		!is_ha_smooth_rising(2) &&
		!is_ha_rising(1) &&
		!is_ha_rising(2) &&
		cci_angle(1) < -45 &&
		macd_main < macd_sig &&
		stoch_curr < stoch_prev)
	{
		result = OrderSend(Symbol(), OP_SELL, lot, Bid, 3, NormalizeDouble(Ask + initial_stoploss*Point*digit_coeff, Digits), 0, "", 0, 0, Red);
	}
}

bool is_ha_smooth_rising(int shift)
{
	double open = iCustom(NULL, 0, "Heiken_Ashi_Smoothed", 2, 6, 3, 2, 0, shift);
	double close = iCustom(NULL, 0, "Heiken_Ashi_Smoothed", 2, 6, 3, 2, 3, shift);

	if (close - open > 0)
		return true;
	else
		return false;
}

bool is_ha_rising(int shift)
{
	double open = iCustom(NULL, 0, "Heiken Ashi4", 2, shift);
	double close = iCustom(NULL, 0, "Heiken Ashi4", 3, shift);

	if (close - open > 0)
		return true;
	else
		return false;
}

int cci_angle(int shift)
{
	double curr = iCCI(NULL, 0, 14, PRICE_TYPICAL, shift);
	double prev = iCCI(NULL, 0, 14, PRICE_TYPICAL, shift + 1);

	return MathArctan((curr - prev) / angle_coeff) * 180 / M_PI;
}