
이 전략은 이동 평균에 기반한 트렌드 추종형 거래 전략이다. 그것은 세 개의 다른 파라미터가 설정된 헐 이동 평균을 사용하여 가격 트렌드 방향을 판단하고, 빠른 ATR 필터와 결합하여 잠재적인 트렌드 반전의 조기 인식을 실현한다. 세 개의 평행선이 상승 또는 하향으로 교차 할 때, 구매 또는 판매 신호를 발령한다. 이 전략은 이동 중지 및 이동 중지 기능을 동시에 갖추고 있으며, 위험을 효과적으로 제어 할 수 있다.
이 전략은 세 개의 헐 이동 평균을 사용하여 가격 동향을 판단합니다. 빠른 헐 MA, 중속 헐 MA 및 느린 헐 MA를 포함합니다.
단선에서 중간선을 통과하면, 가격이 상승 추세에 들어간다는 것을 나타내고, 구매 신호를 낸다.
만약 하위선 아래로 중간선이 지나간다면, 가격이 하향 경향에 들어간다는 것을 의미하며, 판매 신호를 낸다.
트렌드 반전의 식별에 대한 민감성을 높이기 위해, 전략은 RSI 기반의 빠른 ATR 필터를 도입했다. 이 필터는 가격의 변동성을 측정할 수 있으며, 가격 트렌드가 변하면 그 값이 눈에 띄게 변한다. 따라서, ATR 필터의 상하 파격에 따라 가격 트렌드의 반전을 미리 판단 할 수 있습니다.
구체적으로, filtr 함수는 빠른 ATR 필터의 계산 논리를 구현한다. RSI의 값을 기반으로 ATR의 크기를 계산한다. ATR 값이 RSI 곡선을 상위 또는 아래로 뚫을 때, 가격 경향의 전환을 나타낼 수 있다.
또한, 전략에는 이동식 중지 및 이동식 중지 조건이 설정되어 있으며, 설정된 중지 손실 비율과 중지 비율에 따라 자동 위험 관리가 가능합니다.
세 개의 Hull MA 평균선을 사용하여 트렌드 방향을 판단하여 시장 소음을 효과적으로 필터링하여 중장선 트렌드를 식별 할 수 있습니다.
빠른 ATR 필터를 사용하면 트렌드 반전의 사전 판단이 가능합니다.
트렌드 반전 기회를 자동으로 포지션을 조정하고 매매를 중단하지 마십시오.
모바일 스톱 스톱은 위험과 수익의 동적인 균형을 설정합니다.
다양한 시장과 거래 품종에 맞는 사용자 정의 가능한 매개 변수
MA 교차 전략은 다중 헤드 가짜 신호와 허공 헤드 가짜 신호를 생성할 수 있으며, ATR 필터가 보조 검증을 필요로 한다.
큰 변동이 있는 시장에서 MA는 자주 교차하기 쉽기 때문에 ATR 곡선의 움직임을 주의 깊게 관찰해야 합니다.
스톱포트는 너무 작아서 손해가 발생하기 쉽고, 너무 커서 손해를 제어하기 어렵다. 상황에 따라 매개 변수를 조정해야 한다.
이 전략은 동향적인 상황에 더 적합하며, 충격적인 상황에서는 적합하지 않습니다.
매개 변수를 최적화하여 최적의 MA 및 ATR 주기 조합을 선택하여 가짜 신호를 줄일 수 있습니다.
MA 타입을 DEMA, TEMA 등의 EMA 변종으로 바꾸어 더 많은 소음을 필터링할 수 있는지 확인해보세요.
ATR 필터는 Keltner channel MIDDLE 라인을 사용하여 트렌드 반전의 판단을 향상시킬 수 있습니다.
다양한 MA 변수 조합을 테스트하여 최적의 변수 쌍을 찾을 수 있습니다.
ATR 주기 변수를 테스트하여 최적의 평준화를 찾을 수 있습니다.
양력 지표가 추가되어 진위 또는 진위 여부를 판단할 수 있다.
신호의 신뢰성을 높이기 위해 MACD와 같은 다른 지표가 추가되었는지 테스트 할 수 있습니다.
이 전략은 이동 평균 판단 트렌드 방향, ATR 필터 사전 탐지 반전 및 자동 상쇄 관리 위험의 여러 기능을 통합한다. 그것은 자동으로 트렌드를 추적하고, 시간 내에 상쇄 기회를 잡을 수 있으며, 파라미터 최적화를 통해 다른 품종과 주기에 적용할 수 있으며, 매우 실용적인 트렌드 추적 방식의 거래 전략이다. 그것의 장점은 간단한 명확한 전략 논리와 효율적인 위험 제어 수단이다. 그러나 오류 신호 및 상쇄점 설정 문제에 대해서도 주의를 기울여야 한다.
/*backtest
start: 2023-10-06 00:00:00
end: 2023-11-05 00:00:00
period: 1h
basePeriod: 15m
exchanges: [{"eid":"Futures_Binance","currency":"BTC_USDT"}]
*/
//@version=3
//
//*** START of COMMENT OUT [Alerts]
//strategy(title="[Backtest]QQE Cross v6.0 by JustUncleL", shorttitle="[BT]QQEX v6.0", overlay=true,
// pyramiding=0, default_qty_value=1000, commission_value=0.1,
// commission_type=strategy.commission.percent, initial_capital=10000)
//*** END of COMMENT OUT [Alerts]
//<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<//
//>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>//
//*** START of COMMENT OUT [BackTest]
strategy(
title="[Alerts]QQE Cross v6.0 by JustUncleL",
shorttitle="[AL]QQEX v6.0",
overlay=true)
FromMonth = input(defval=1, title="From Month", minval=1, maxval=12)
FromDay = input(defval=1, title="From Day", minval=1, maxval=31)
FromYear = input(defval=2009, title="From Year")
ToMonth = input(defval=1, title="To Month", minval=1, maxval=12)
ToDay = input(defval=1, title="To Day", minval=1, maxval=31)
ToYear = input(defval=9999, title="To Year")
start = timestamp(FromYear, FromMonth, FromDay, 00, 00) // backtest start window
finish = timestamp(ToYear, ToMonth, ToDay, 23, 59) // backtest finish window
window = true // create function "within window of time"
trade_dir = input('Long Only', options=['Long Only', 'Short Only', 'Long and Short'], title='Trade Direction')
tp1_perc = input(25, step=0.25, minval=0, title='Take Profit Signal 1 Qty Percent')/100
tp2_perc = input(25, step=0.25, minval=0, title='Take Profit Signal 2 Qty Percent')/100
sl_perc = input(2, step=0.25, minval=0, title='Stop Loss Percent')/100
dir = trade_dir == 'Long Only' ? strategy.direction.long :
trade_dir == 'Short Only' ? strategy.direction.short : strategy.direction.all
strategy.risk.allow_entry_in(dir)
//*** END of COMMENT OUT [BackTest]
//
// Author: JustUncleL
// Date: 10-July-2016
// Version: v6, Major Release Nov-2018
//
// Description:
// A following indicator is Trend following that uses fast QQE crosses with Moving Averages
// for trend direction filtering. QQE or Qualitative Quantitative Estimation is based
// on the relative strength index (RSI), but uses a smoothing technique as an additional
// transformation. Three crosses can be selected (all selected by default):
// - Smooth RSI signal crossing ZERO (XZ)
// - Smooth RSI signal crossing Fast QQE line (XQ), this is like an early warning swing signal.
// - Smooth RSI signal exiting the RSI Threshhold Channel (XC), this is like a confirmed swing signal.
// An optimumal Smooth RSI threshold level is between 5% and 10% (default=10), it helps reduce
// the false swings.
// These signals can be selected to Open Short/Long and/or Close a trade, default is XC open
// trade and XQ (or opposite open) to Close trade.
//
// The (LONG/SHORT) alerts can be optionally filtered by the Moving Average Ribbons:
// - For LONG alert the Close must be above the fast MA Ribbon and
// fast MA Ribbon must be above the slow MA Ribbon.
// - For SHORT alert the Close must be below the fast MA Ribbon and
// fast MA Ribbon must be below the slow MA Ribbon.
// and/or directional filter:
// - For LONG alert the Close must be above the medium MA and the
// directional of both MA ribbons must be Bullish.
// - For SELL alert the Close must be below the medium MA and the
// directional of both MA ribbons must be Bearish.
//
// This indicator is designed to be used as a Signal to Signal trading BOT
// in automatic or semi-automatic way (start and stop when conditions are suitable).
// - For LONG and SHORT alerts I recommend you use "Once per Bar" alarm option
// - For CLOSE alerts I recommend you use "Once per Bar Close" alarm option
// (* The script has been designed so that long/short signals come at start of candles *)
// (* and close signals come at the end of candles *)
//
// Mofidifications:
// 6.0 - Major Release Version
// - Added second MA ribbon to help filter signals to the trend direction.
// - Modified Alert filtering to include second MA Ribbon
// - Change default settings to reflect Signal to Signal BOT parameters.
// - Removed older redunant alerts.
//
// 5.0 - Development series
//
// 4.1 - Fix bug with painting Buy/Sell arrows when non-repaint shunt mode selected.
// - Added option to alert just the first Buy/Sell alert after a trend swing
// - Added Long and Short Alarms. When combined with the "first Buy/Sell" in trend option,
// It is now possible to use this indicator to interface with AutoView
// or ProfitView. I suggest using the "QQEX XZ Alert" alarm to exit Long or Short
// trade. Use only "Once per bar Close" option for Alarms. This is not a full
// fledged trading BOT though with TP/SL settings.
//
// - Changed QQE defaults to be a bit smoother (14, 8, 5) instead of (6, 3, 2.618)
// which is more suited to Forex and Crypto trading.
//
// 4.0 - Added implied GPL copyright notice.
// - Changed defaults to use HullMAs instead of EMAs.
// 3.0 - No repaint on BUY/SELL alert, however, now trades should be taken when the BUY/SELL
// Alert is displayed. The alarm is still generated on the previous candle so you can
// still get a pre-warning, this enables you time to analyse the pending alert.
// - Added option to test success of alerted trades, highlight successful and failed trade bars
// and show simple stats: success rate and number of trades (out of 5000), this will help
// tune the settings for timeframe and currency PAIR.
// 2.0 - Added code to use the medium moving average (EMA20) rising/falling for additional
// trend direction filter.
// - Remove Moving Average cross over signals and other options not used in this indicator.
// - Added code to distinguish between the crosses, now only show Thresh Hold crosses as BUY/SELL
// alerts.
// - Modidied default settings to more well known MA's and slightly different QQE settings, these
// work well at lower timeframes.
// - Added circle plots at bottom of chart to show when actual BUY/SELL alerts occur.
// 1.0 - original
//
// References:
// Some Code borrowed from:
// - "Scalp Jockey - MTF MA Cross Visual Strategizer by JayRogers"
// - "QQE MT4 by glaz"
// Inspiration from:
// - http://www.forexstrategiesresources.com/binary-options-strategies-ii/189-aurora-binary-trading/
// - http://www.forexstrategiesresources.com/metatrader-4-trading-systems-v/652-qqe-smoothed-trading/
// - http://dewinforex.com/forex-indicators/qqe-indicator-not-quite-grail-but-accurately-defines-trend-and-flat.html
// - "Binary option trading by two previous bars" by radixvinni
//
//
// -----------------------------------------------------------------------------
// Copyright 2015 Glaz,JayRogers
//
// Copyright 2016,2017,2018 JustUncleL
//
// This program is free software: you can redistribute it and/or modify
// it under the terms of the GNU General Public License as published by
// the Free Software Foundation, either version 3 of the License, or
// any later version.
//
// This program is distributed in the hope that it will be useful,
// but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
// GNU General Public License for more details.
//
// The GNU General Public License can be found here
// <http://www.gnu.org/licenses/>.
//
// -----------------------------------------------------------------------------
//
// Use Alternate Anchor TF for MAs
anchor = input(4,minval=0,maxval=100,title="Relative TimeFrame Multiplier for Second MA Ribbon (0=none, max=100)")
//
// - INPUTS START
// Fast MA - type, source, length
showAvgs = input(true,title="Show Moving Average Lines")
type1 = input(defval="EMA", title="Fast MA Type: ", options=["SMA", "EMA", "WMA", "VWMA", "SMMA", "DEMA", "TEMA", "HullMA", "ZEMA", "TMA", "SSMA"])
len1 = input(defval=16, title="Fast - Length", minval=1)
gamma1 = 0.33
// Medium Fast MA - type, source, length
type2 = input(defval="EMA", title="Medium MA Type: ", options=["SMA", "EMA", "WMA", "VWMA", "SMMA", "DEMA", "TEMA", "HullMA", "ZEMA", "TMA", "SSMA"])
len2 = input(defval=21, title="Medium - Length", minval=1)
gamma2 = 0.55
// Slow MA - type, source, length
type3 = input(defval="EMA", title="Slow MA Type: ", options=["SMA", "EMA", "WMA", "VWMA", "SMMA", "DEMA", "TEMA", "HullMA", "ZEMA", "TMA", "SSMA"])
len3 = input(defval=26, title="Slow Length", minval=1)
gamma3 = 0.77
//
// QQE rsi Length, Smoothing, fast ATR factor, source
RSILen = input(14,title='RSI Length')
SF = input(8,title='RSI Smoothing Factor')
QQEfactor = input(5.0,type=float,title='Fast QQE Factor')
threshhold = input(10, title="RSI Threshhold")
//
sQQEx = input(true,title="Show QQE Signal crosses")
sQQEz = input(false,title="Show QQE Zero crosses")
sQQEc = input(true,title="Show QQE Thresh Hold Channel Exits")
//
tradeSignal = input("XC", title="Select which QQE signal to Buy/Sell", options=["XC","XQ","XZ"])
closeSignal = input("XQ", title="Select which QQE signal to Close Order", options=["XC","XQ","XZ"])
//
xfilter = input(true, title="Filter XQ Buy/Sell Orders by Threshold" )
filter = input(false,title="Use Moving Average Filter")
dfilter = input(true, title="Use Trend Directional Filter" )
ufirst = input(false, title="Only Alert First Buy/Sell in a new Trend")
RSIsrc = input(close,title="Source")
src = RSIsrc // MA source
srcclose= RSIsrc
///////////////////////////////////////////////
//* Backtesting Period Selector | Component *//
///////////////////////////////////////////////
//* https://www.tradingview.com/script/eCC1cvxQ-Backtesting-Period-Selector-Component *//
//* https://www.tradingview.com/u/pbergden/ *//
//* Modifications made by JustUncleL*//
//>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>//
//*** START of COMMENT OUT [Alerts]
//testStartYear = input(2018, "Backtest Start Year",minval=1980)
//testStartMonth = input(6, "Backtest Start Month",minval=1,maxval=12)
//testStartDay = input(12, "Backtest Start Day",minval=1,maxval=31)
//testPeriodStart = timestamp(testStartYear,testStartMonth,testStartDay,0,0)
//testStopYear = 9999 //input(9999, "Backtest Stop Year",minval=1980)
//testStopMonth = 12 // input(12, "Backtest Stop Month",minval=1,maxval=12)
//testStopDay = 31 //input(31, "Backtest Stop Day",minval=1,maxval=31)
//testPeriodStop = timestamp(testStopYear,testStopMonth,testStopDay,0,0)
//testPeriod = time >= testPeriodStart and time <= testPeriodStop ? true : false
//*** END of COMMENT OUT [Alerts]
//<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<//
// - INPUTS END
gold = #FFD700
AQUA = #00FFFFFF
BLUE = #0000FFFF
RED = #FF0000FF
LIME = #00FF00FF
GRAY = #808080FF
// - FUNCTIONS
// - variant(type, src, len, gamma)
// Returns MA input selection variant, default to SMA if blank or typo.
// SuperSmoother filter
// © 2013 John F. Ehlers
variant_supersmoother(src,len) =>
a1 = exp(-1.414*3.14159 / len)
b1 = 2*a1*cos(1.414*3.14159 / len)
c2 = b1
c3 = (-a1)*a1
c1 = 1 - c2 - c3
v9 = 0.0
v9 := c1*(src + nz(src[1])) / 2 + c2*nz(v9[1]) + c3*nz(v9[2])
v9
variant_smoothed(src,len) =>
v5 = 0.0
v5 := na(v5[1]) ? sma(src, len) : (v5[1] * (len - 1) + src) / len
v5
variant_zerolagema(src,len) =>
ema1 = ema(src, len)
ema2 = ema(ema1, len)
v10 = ema1+(ema1-ema2)
v10
variant_doubleema(src,len) =>
v2 = ema(src, len)
v6 = 2 * v2 - ema(v2, len)
v6
variant_tripleema(src,len) =>
v2 = ema(src, len)
v7 = 3 * (v2 - ema(v2, len)) + ema(ema(v2, len), len) // Triple Exponential
v7
//calc Laguerre
variant_lag(p,g) =>
L0 = 0.0
L1 = 0.0
L2 = 0.0
L3 = 0.0
L0 := (1 - g)*p+g*nz(L0[1])
L1 := -g*L0+nz(L0[1])+g*nz(L1[1])
L2 := -g*L1+nz(L1[1])+g*nz(L2[1])
L3 := -g*L2+nz(L2[1])+g*nz(L3[1])
f = (L0 + 2*L1 + 2*L2 + L3)/6
f
// return variant, defaults to SMA
variant(type, src, len, g) =>
type=="EMA" ? ema(src,len) :
type=="WMA" ? wma(src,len):
type=="VWMA" ? vwma(src,len) :
type=="SMMA" ? variant_smoothed(src,len) :
type=="DEMA" ? variant_doubleema(src,len):
type=="TEMA" ? variant_tripleema(src,len):
type=="LAGMA" ? variant_lag(src,g) :
type=="HullMA"? wma(2 * wma(src, len / 2) - wma(src, len), round(sqrt(len))) :
type=="SSMA" ? variant_supersmoother(src,len) :
type=="ZEMA" ? variant_zerolagema(src,len) :
type=="TMA" ? sma(sma(src,len),len) :
sma(src,len)
// - /variant
// If have anchor specified, calculate the base multiplier, base on time in mins
//mult = isintraday ? anchor==0 or interval<=0 or interval>=anchor or anchor>1440? 1 : round(anchor/interval) : 1
//mult := not isintraday? 1 : mult // Only available Daily or less
// Anchor is a relative multiplier based on current TF.
mult = anchor>0 ? anchor : 1
// - FUNCTIONS END
// - Fast ATR QQE
//
Wilders_Period = RSILen * 2 - 1
//
Rsi = rsi(RSIsrc,RSILen)
RSIndex = ema(Rsi, SF)
AtrRsi = abs(RSIndex[1] - RSIndex)
MaAtrRsi = ema(AtrRsi, Wilders_Period)
DeltaFastAtrRsi = ema(MaAtrRsi,Wilders_Period) * QQEfactor
//
newshortband= RSIndex + DeltaFastAtrRsi
newlongband= RSIndex - DeltaFastAtrRsi
longband = 0.0
shortband=0.0
trend = 0
longband:=RSIndex[1] > longband[1] and RSIndex > longband[1] ? max(longband[1],newlongband) : newlongband
shortband:=RSIndex[1] < shortband[1] and RSIndex < shortband[1] ? min(shortband[1],newshortband) : newshortband
trend:=cross(RSIndex, shortband[1])? 1 : cross(longband[1], RSIndex) ? -1 : nz(trend[1],1)
FastAtrRsiTL = trend==1 ? longband : shortband
// - SERIES VARIABLES
// MA's
ma_fast = variant(type1, srcclose, len1, gamma1)
ma_medium = variant(type2, srcclose, len2, gamma2)
ma_slow = variant(type3, srcclose, len3, gamma3)
// MA's
ma_fast_alt = variant(type1, srcclose, len1*mult, gamma1)
ma_medium_alt = variant(type2, srcclose, len2*mult, gamma2)
ma_slow_alt = variant(type3, srcclose, len3*mult, gamma3)
// Get Direction From Medium Moving Average
direction = rising(ma_medium,3) ? 1 : falling(ma_medium,3) ? -1 : 0
altDirection = rising(ma_medium_alt,3) ? 1 : falling(ma_medium_alt,3) ? -1 : 0
//
// Find all the QQE Crosses
QQExlong = 0, QQExlong := nz(QQExlong[1])
QQExshort = 0, QQExshort := nz(QQExshort[1])
QQExlong := FastAtrRsiTL< RSIndex ? QQExlong+1 : 0
QQExshort := FastAtrRsiTL> RSIndex ? QQExshort+1 : 0
// Zero cross
QQEzlong = 0, QQEzlong := nz(QQEzlong[1])
QQEzshort = 0, QQEzshort := nz(QQEzshort[1])
QQEzlong := RSIndex>=50 ? QQEzlong+1 : 0
QQEzshort := RSIndex<50 ? QQEzshort+1 : 0
//
// Thresh Hold channel Crosses give the BUY/SELL alerts.
QQEclong = 0, QQEclong := nz(QQEclong[1])
QQEcshort = 0, QQEcshort := nz(QQEcshort[1])
QQEclong := RSIndex>(50+threshhold) ? QQEclong+1 : 0
QQEcshort := RSIndex<(50-threshhold) ? QQEcshort+1 : 0
//
// Check Filtering.
QQEflong = mult == 1 ? (not filter or (srcclose>ma_medium and ma_medium>ma_slow and ma_fast>ma_medium)) and (not dfilter or (direction>0 )) :
(not filter or (ma_medium>ma_medium_alt and srcclose>ma_fast and ma_fast>ma_medium)) and (not dfilter or (direction>0 and altDirection>0 and srcclose>ma_medium))
QQEfshort = mult == 1 ? (not filter or (srcclose<ma_medium and ma_medium<ma_slow and ma_fast<ma_medium)) and (not dfilter or (direction<0 )) :
(not filter or (ma_medium<ma_medium_alt and srcclose<ma_fast and ma_fast<ma_medium)) and (not dfilter or (direction<0 and altDirection<0 and srcclose<ma_medium))
QQExfilter = (not xfilter or RSIndex>(50+threshhold) or RSIndex<(50-threshhold))
//
// Get final BUY / SELL alert determination
buy_ = 0, buy_ := nz(buy_[1])
sell_ = 0, sell_ := nz(sell_[1])
// Make sure Buy/Sell are non-repaint and occur after close signal.
buy_ := tradeSignal=="XC"? (QQEclong[1]==1 and QQEflong[1] ? buy_+1 : 0) :
tradeSignal=="XQ"? (QQExlong[1]==1 and QQEflong[1] and QQExfilter[1]? buy_+1 : 0) :
tradeSignal=="XZ"? (QQEzlong[1]==1 and QQEflong[1] ? buy_+1 : 0) : 0
sell_ := tradeSignal=="XC"? (QQEcshort[1]==1 and QQEfshort[1] ? sell_+1 : 0) :
tradeSignal=="XQ"? (QQExshort[1]==1 and QQEfshort[1] and QQExfilter[1]? sell_+1 : 0) :
tradeSignal=="XZ"? (QQEzshort[1]==1 and QQEfshort[1] ? sell_+1 : 0) : 0
//
// Find the first Buy/Sell in trend swing.
Buy = 0, Buy := nz(Buy[1])
Sell = 0, Sell := nz(Sell[1])
Buy := sell_>0 ? 0 : buy_==1 or Buy>0 ? Buy+1 : Buy
Sell := buy_>0 ? 0 : sell_==1 or Sell>0 ? Sell+1 : Sell
// Select First or all buy/sell alerts.
buy = ufirst ? Buy : buy_
sell = ufirst ? Sell : sell_
closeLong = 0, closeLong := nz(closeLong[1])
closeShort = 0, closeShort := nz(closeShort[1])
closeLong := closeSignal=="XC" ? (QQEcshort==1 ? closeLong+1 : 0) :
closeSignal=="XQ" ? tradeSignal=="XQ" ? (QQExshort==1 ? closeLong+1 : 0) : ((QQExshort==1 or QQEzshort or QQEcshort) ? closeLong+1 : 0) :
closeSignal=="XZ" ? (QQEzshort==1 ? closeLong+1 : 0) : 0
closeShort := closeSignal=="XC" ? (QQEclong==1 ? closeShort+1 : 0) :
closeSignal=="XQ" ? tradeSignal=="XQ" ? (QQExlong==1 ? closeShort+1 : 0) : ((QQExlong==1 or QQEzlong or QQEclong==1) ? closeShort+1 : 0) :
closeSignal=="XZ" ? (QQEzlong==1 ? closeShort+1 : 0) : 0
tradestate = 0, tradestate := nz(tradestate[1])
tradestate := tradestate==0 ? (buy==1 ? 1 : sell==1 ? 2 : 0) : (tradestate==1 and closeLong==1) or (tradestate==2 and closeShort==1)? 0 : tradestate
isLong = change(tradestate) and tradestate==1
isShort = change(tradestate) and tradestate==2
isCloseLong = change(tradestate) and tradestate==0 and nz(tradestate[1])==1
isCloseShort = change(tradestate) and tradestate==0 and nz(tradestate[1])==2
// - SERIES VARIABLES END
// - PLOTTING
// Ma's
tcolor = direction<0?red:green
// ma1=plot(showAvgs?ma_fast:na, title="MA Fast", color=tcolor, linewidth=1, transp=0)
ma2=plot(showAvgs?ma_medium:na, title="MA Medium Fast", color=tcolor, linewidth=2, transp=0)
// ma3=plot(showAvgs?ma_slow:na, title="MA Slow", color=tcolor, linewidth=1, transp=0)
// fill(ma1,ma3,color=tcolor,transp=90)
// Ma's
altTcolor=altDirection<0?red:green
barcolor(altDirection<0? red:green)
ma4=plot(showAvgs and mult>1?ma_fast_alt:na, title="MA Fast", color=altTcolor, linewidth=1, transp=0)
ma5=plot(showAvgs and mult>1?ma_medium_alt:na, title="MA Medium Fast", color=altTcolor, linewidth=2, transp=0)
ma6=plot(showAvgs and mult>1?ma_slow_alt:na, title="MA Slow", color=altTcolor, linewidth=1, transp=0)
fill(ma4,ma6,color=altTcolor,transp=90)
// Color Changes
turned_aqua = altTcolor[1] == red and altTcolor == green
turned_blue = altTcolor[1] == green and altTcolor == red
take_profit_long = ma_slow > ma_fast_alt and ma_slow > ma_slow_alt and tcolor[1] == green and tcolor == red
take_profit_short = ma_slow < ma_fast_alt and ma_slow < ma_slow_alt and tcolor[1] == red and tcolor == green
// plotshape(turned_aqua, title="MA's Green Buy", style=shape.triangleup, location=location.belowbar, text="Long", color=green, transp=20, size=size.normal)
// plotshape(turned_blue, title="MA's Red Sell", style=shape.triangledown, location=location.abovebar, text="Short", color=red, transp=20, size=size.normal)
// plotshape(take_profit_long, title="Take Profit Long", style=shape.triangledown, location=location.abovebar, text="Take Profit Long", color=purple, transp=20, size=size.tiny)
// plotshape(take_profit_short, title="Take Profit Short", style=shape.triangleup, location=location.belowbar, text="Take Profit Short", color=purple, transp=20, size=size.tiny)
strategy.entry("Long", strategy.long, when=turned_aqua and window)
strategy.entry("short", strategy.short, when=turned_blue and window)
entered_long = strategy.position_size[1] <= 0 and strategy.position_size > 0
entered_short = strategy.position_size[1] >= 0 and strategy.position_size < 0
long_tp_count = 0
long_tp_count := entered_long ? 0 : take_profit_long ? long_tp_count[1] + 1 : long_tp_count[1]
short_tp_count = 0
short_tp_count := entered_short ? 0 : take_profit_short ? short_tp_count[1] + 1 : short_tp_count[1]
// take_off_long = long_tp_count == 0 ? tp1_perc : long_tp_count == 1 ? tp2_perc : na
// take_off_short = short_tp_count == 0 ? tp1_perc : short_tp_count == 1 ? tp2_perc : na
long_tp1_qty = na
long_tp2_qty = na
short_tp1_qty = na
short_tp2_qty = na
long_tp1_qty := entered_long ? strategy.position_size * tp1_perc : long_tp1_qty[1]
long_tp2_qty := entered_long ? strategy.position_size * tp2_perc : long_tp2_qty[1]
short_tp1_qty := entered_short ? -strategy.position_size * tp1_perc : short_tp1_qty[1]
short_tp2_qty := entered_short ? -strategy.position_size * tp2_perc : short_tp2_qty[1]
long_sl_level = sl_perc == 0 ? na : strategy.position_avg_price * (1 - sl_perc)
short_sl_level = sl_perc == 0 ? na : strategy.position_avg_price * (1 + sl_perc)
strategy.order("LTP1", strategy.short, qty=long_tp1_qty, when=strategy.position_size > 0 and take_profit_long and long_tp_count[1]==0 and not turned_blue)
strategy.order("LTP2", strategy.short, qty=long_tp2_qty, when=strategy.position_size > 0 and take_profit_long and long_tp_count[1]==1 and not turned_blue)
strategy.order("STP1", strategy.long, qty=short_tp1_qty, when=strategy.position_size < 0 and take_profit_short and short_tp_count[1]==0 and not turned_aqua)
strategy.order("STP2", strategy.long, qty=short_tp2_qty, when=strategy.position_size < 0 and take_profit_short and short_tp_count[1]==1 and not turned_aqua)
strategy.exit("L-SL", "Long", stop=long_sl_level)
strategy.exit("S-SL", "Short", stop=short_sl_level)
// SL PLOTS
// --------
plot(strategy.position_size > 0 ? long_sl_level : na, color=red, style=linebr, title="Long Stop")
plot(strategy.position_size < 0 ? short_sl_level : na, color=maroon, style=linebr, title="Short Stop")
// ALERTS (STUDY ONLY)
alertcondition(turned_aqua, title="Long", message="Ma's Turned Green")
alertcondition(turned_blue, title="Short", message="Ma's Turned Red")
alertcondition(take_profit_long, title="Take Profit Long", message="Take Profit Long")
alertcondition(take_profit_short, title="Take Profit Short", message="Take Profit Short")
alertcondition(isLong, title="QQEX Long", message="QQEX LONG") // use "Once per Bar" option
alertcondition(isShort, title="QQEX Short", message="QQEX SHORT") // use "Once per Bar" option
alertcondition(isCloseLong, title="QQEX Close Long", message="QQEX CLOSE LONG") // use "Once per Bar Close" option
alertcondition(isCloseShort, title="QQEX Close Short", message="QQEX CLOSE SHORT") // use "Once per Bar Close" option
// show only when alert condition is met and bar closed.
plotshape(isLong or isShort,title= "Cross Alert Completed", location=location.bottom, color=isShort?red:green, transp=0, style=shape.circle,size=size.auto,offset=0)
plotshape(isCloseShort[1] or isCloseLong[1],title= "Close Order", location=location.top, color=isCloseShort[1]?red:green, transp=0, style=shape.square,size=size.auto,offset=-1)
// Test Plots
// ---------
// plot(long_tp_count)
// plot(short_tp_count, color=red)
//EOF