ㅇ과거 FX를 위해 메타트레이더 4를 이용하였고, 시스템 트레이딩을 위해 EA를 개발하여 테스트하고, 실전에 사용한 바 있는데, 이 때 자체 개발한 EA들을 공개하고자 한다.

 

ㅇ 일목균형표를 활용한 EA 만들기의 로직은 일목균형표를 진입신호로 Range Trading Strategy 툴로 매매하는 것이며, 주로 5분봉 차트를 타겟으로 한다.

ㅇ 외생변수 등 설정사항은 아래와 같다.

//********************************************************************
//| 일반외생변수 및 기타 내생변수 설정                               |
//********************************************************************
//***********************************************
// 일반 매매관련 기본 변수 설정
extern bool ECN = TRUE;                                    // ECN Broker의 경우 Ordermodify

extern double Slippage = 3.0;                              // 슬리피지 허용 변수
extern double StopOutBalance = 500;                        // 강제청산 기준 잔고
extern double MaxSpread=4.0;                               // 최고 허용 스프레드 한도
extern double TargetProfit = 60;                           // Close All Target Profit
extern double HedgeProfit = 20;                            // Close All Initial+Hedge Target Profit

datetime  PreviousBarTime1;                                // NewBar 처리를 위한 변수
datetime  PreviousBarTime2;                                // NewBar 처리를 위한 변수 
int mypoint;                                               // 4,5 Digit Broker 처리 변수
int execution=-1;                                          // 주문시 RoundTrip 속도 측정 변수
double ask00, bid00, maxLot;                               // MarketInfo 정보를 받는 변수(Double)  
double minlot,LotStep,sympoint, stopout,reqmargin,equity;  // MarketInfo 정보를 받는 변수(Double)  
int spread, mydigit,stoplevel,freeze, leverage;            // MarketInfo 정보를 받는 변수(Integer)  
string servername,StartDay,mytime;                         // MarketInfo 정보를 받는 변수(String) 

//***********************************************
// MagicNumber와 Step설정을 위한 변수 설정

extern bool AutoMagic = TRUE;                    // 통화별 자동 매직넘버 부여
extern bool AutoStep = FALSE;                    // 통화별 자동 스텝 부여

extern int MaxStep = 50;                         // 자동 스텝 부여시 Max값
extern int MinStep = 25;                         // 자동 스텝 부여시 Min값

extern double buystep=25;                        // 통화별 자동 스텝 미부여시 초기값
extern double sellstep=50;                       // 통화별 자동 스텝 미부여시 초기값
extern int buydivider = 50;                      // 통화별 자동 스텝 부여시 나누는 수(Buy)
extern int selldivider = 50;                     // 통화별 자동 스텝 부여시 나누는 수(Sell)

extern int HL_Days = 76;                         // Range 설정 기준일수
extern int TimeFrame = 1440;                     // TF : PERIOD_M1(1), PERIOD_M5(5), PERIOD_M15(15), PERIOD_M30(30), PERIOD_H1(60), PERIOD_H4(240), PERIOD_D1(1440), 0(Timeframe used on the chart.)

//********************************************************************
//| 매수/매도 관련 변수 설정                                         |
//********************************************************************
int ShortTerm = 9;
int MidTerm = 26;
int LongTerm = 52;
int LastTerm = 2;
int Huhang = 26;
int Seonhang = 26;

//********************************************************************
//| 1st Entry 관련 변수설정                                          |
//********************************************************************
// 1st Entry 매매를 위한 변수 설정

extern double lotsbuy=0.1;                         // 1st Buy 랏수
extern double lotssell=0.1;                        // 1st Sell 랏수

bool InitEntry = TRUE;                             // 1st Entry 여부 설정

extern int InitOrders = 1;                         // 최대 1st Order 개수

extern int  StopLoss=0;                            // 1st Entry SL, SL > 0경우 작동
extern int  TakeProfit=0;                          // 1st Entry TP

extern double  TrailingStop = 0;                   // 트레일링 설정시 > 0
extern double  BreakEven = 0;                      // Break Even 설정시 > 0
extern double  BreakPoint = 0;                     // Break Even 설정시 손절치(본전 + 손절치)

extern string InitComment = "gguri_RT_Ilmok_V0.2";     // 1st Entry 매매비고 

int Magicbuy  = 101;                               // 매수 매직넘버(오토시 의미없음)
int Magicsell = 111;                               // 매도 매직넘버(오토시 의미없음)

int ticketbuy,ticketsell;                          // 1st Entry Ticket 


//********************************************************************
//| 2nd Entry Order 관련 변수설정                                         |
//********************************************************************
// 2st Entry 매매를 위한 변수 설정

extern double AddMultiply=1.0;                          // 2nd Entry 랏 승수

extern bool AddEntry = TRUE;                            // 2nd Entry Enbled or Disable

extern int Addbuy = 50;                                 // 최대 2nd Entry Buy 개수
extern int Addsell = 50;                                // 최대 2nd Entry Sell 개수
extern int MaxPosition = 35;                            // 최대 Buy/Sell Order 차이 

extern int  AddTP = 60;                                  // 2nd Entry TP
extern int  AddSL = 0;                                  // 2nd Entry SL

extern string AddInitComment = "2nd_gguri_RT_Ilmok_V0.2";// 2nd Entry 매매비고

int AddTicketbuy,AddTicketsell;                         // 2nd Entry Ticket 

//********************************************************************
//| 3rd Entry Order 관련 변수설정                                          |
//********************************************************************
// 3rd Entry 매매를 위한 변수 설정

extern double Hg1Multiply=1.5;                           // 3rd-1 Entry 랏 승수
extern double Hg2Multiply=2.0;                           // 3rd-2 Entry 랏 승수
extern double Hg3Multiply=2.5;                           // 3rd-3 Entry 랏 승수
extern double Hg4Multiply=3.0;                           // 3rd-4 Entry 랏 승수

extern bool HgEntry = TRUE;                              // True이면 역으로, False이면 Additional

extern int  Hg1buy = 1;                                  // 최대 3rd Entry Buy 개수
extern int  Hg1sell = 1;                                 // 최대 3rd Entry Sell 개수
extern int  Hg2buy = 1;                                  // 최대 3rd Entry Buy 개수
extern int  Hg2sell = 1;                                 // 최대 3rd Entry Sell 개수
extern int  Hg3buy = 1;                                  // 최대 3rd Entry Buy 개수
extern int  Hg3sell = 1;                                 // 최대 3rd Entry Sell 개수
extern int  Hg4buy = 1;                                  // 최대 3rd Entry Buy 개수
extern int  Hg4sell = 1;                                 // 최대 3rd Entry Sell 개수

extern int Hg1Max = 10;                                  // 최대 Buy/Sell Order 차이 
extern int Hg2Max = 20;                                  // 최대 Buy/Sell Order 차이 
extern int Hg3Max = 30;                                  // 최대 Buy/Sell Order 차이 
extern int Hg4Max = 40;                                  // 최대 Buy/Sell Order 차이 

extern int  HgTP = 30;                                   // 3rd Entry TP
extern int  HgSL = 0;                                    // 3rd Entry SL

extern double HgTrailingStop = 10;                       // 3rd Entry 트레일링 설정시 > 0

extern string HGInitComment = "3rd_gguri_RT_Ilmok_V0.2"; // Hedge Entry 매매비고

int HgTicketbuy,HgTicketsell;                            // 3rd Entry Ticket  
int Hg1MagicBuy,Hg1MagicSell,Hg2MagicBuy,Hg2MagicSell;   // 3rd Magic Number
int Hg3MagicBuy,Hg3MagicSell,Hg4MagicBuy,Hg4MagicSell;   // 3rd Magic Number

ㅇ 전체적인 EA의 소스는 아래와 같다. 

 

//********************************************************************
//|                                 gguri_RT_Ilmok_V0.2                     |
//|                                 Copyright @ 2012                        |
//********************************************************************
//********************************************************************
//| 일목균형표를 진입신호로 Range Trading Strategy 툴로 매매   |
//********************************************************************
//********************************************************************
//| Version History 및 Library 불러오기                                   |
//********************************************************************
/*

V0.2 
- Hedge조건에서 Buy Condition / Sell Condition 충족 조건 추가

*/

//***********************************************
// Error Code 처리를 위한 Library Import
#import "stdlib.ex4"
   string ErrorDescription(int a0);
//*********************************************************************************************

//********************************************************************
//| 일반외생변수 및 기타 내생변수 설정                               |
//********************************************************************

//***********************************************
// 일반 매매관련 기본 변수 설정
extern bool ECN = TRUE;                                    // ECN Broker의 경우 Ordermodify

extern double Slippage = 3.0;                              // 슬리피지 허용 변수
extern double StopOutBalance = 500;                        // 강제청산 기준 잔고
extern double MaxSpread=4.0;                               // 최고 허용 스프레드 한도
extern double TargetProfit = 60;                           // Close All Target Profit
extern double HedgeProfit = 20;                            // Close All Initial+Hedge Target Profit

datetime  PreviousBarTime1;                                // NewBar 처리를 위한 변수
datetime  PreviousBarTime2;                                // NewBar 처리를 위한 변수 
int mypoint;                                               // 4,5 Digit Broker 처리 변수
int execution=-1;                                          // 주문시 RoundTrip 속도 측정 변수
double ask00, bid00, maxLot;                               // MarketInfo 정보를 받는 변수(Double)  
double minlot,LotStep,sympoint, stopout,reqmargin,equity;  // MarketInfo 정보를 받는 변수(Double)  
int spread, mydigit,stoplevel,freeze, leverage;            // MarketInfo 정보를 받는 변수(Integer)  
string servername,StartDay,mytime;                         // MarketInfo 정보를 받는 변수(String) 

//***********************************************
// MagicNumber와 Step설정을 위한 변수 설정

extern bool AutoMagic = TRUE;                    // 통화별 자동 매직넘버 부여
extern bool AutoStep = FALSE;                    // 통화별 자동 스텝 부여

extern int MaxStep = 50;                         // 자동 스텝 부여시 Max값
extern int MinStep = 25;                         // 자동 스텝 부여시 Min값

extern double buystep=25;                        // 통화별 자동 스텝 미부여시 초기값
extern double sellstep=50;                       // 통화별 자동 스텝 미부여시 초기값
extern int buydivider = 50;                      // 통화별 자동 스텝 부여시 나누는 수(Buy)
extern int selldivider = 50;                     // 통화별 자동 스텝 부여시 나누는 수(Sell)

extern int HL_Days = 76;                         // Range 설정 기준일수
extern int TimeFrame = 1440;                     // TF : PERIOD_M1(1), PERIOD_M5(5), PERIOD_M15(15), PERIOD_M30(30), PERIOD_H1(60), PERIOD_H4(240), PERIOD_D1(1440), 0(Timeframe used on the chart.)

//*********************************************************************************************


//********************************************************************
//| 매수/매도 관련 변수 설정                                         |
//********************************************************************

int ShortTerm = 9;
int MidTerm = 26;
int LongTerm = 52;
int LastTerm = 2;
int Huhang = 26;
int Seonhang = 26;

//********************************************************************
//| 1st Entry 관련 변수설정                                          |
//********************************************************************

//***********************************************
// 1st Entry 매매를 위한 변수 설정

extern double lotsbuy=0.1;                         // 1st Buy 랏수
extern double lotssell=0.1;                        // 1st Sell 랏수

bool InitEntry = TRUE;                             // 1st Entry 여부 설정

extern int InitOrders = 1;                         // 최대 1st Order 개수

extern int  StopLoss=0;                            // 1st Entry SL, SL > 0경우 작동
extern int  TakeProfit=0;                          // 1st Entry TP

extern double  TrailingStop = 0;                   // 트레일링 설정시 > 0
extern double  BreakEven = 0;                      // Break Even 설정시 > 0
extern double  BreakPoint = 0;                     // Break Even 설정시 손절치(본전 + 손절치)

extern string InitComment = "gguri_RT_Ilmok_V0.2";     // 1st Entry 매매비고 

int Magicbuy  = 101;                               // 매수 매직넘버(오토시 의미없음)
int Magicsell = 111;                               // 매도 매직넘버(오토시 의미없음)

int ticketbuy,ticketsell;                          // 1st Entry Ticket 


//********************************************************************
//| 2nd Entry Order 관련 변수설정                                    |
//********************************************************************

//***********************************************
// 2st Entry 매매를 위한 변수 설정

extern double AddMultiply=1.0;                          // 2nd Entry 랏 승수

extern bool AddEntry = TRUE;                            // 2nd Entry Enbled or Disable

extern int Addbuy = 50;                                 // 최대 2nd Entry Buy 개수
extern int Addsell = 50;                                // 최대 2nd Entry Sell 개수
extern int MaxPosition = 35;                            // 최대 Buy/Sell Order 차이 

extern int  AddTP = 60;                                  // 2nd Entry TP
extern int  AddSL = 0;                                  // 2nd Entry SL

extern string AddInitComment = "2nd_gguri_RT_Ilmok_V0.2";// 2nd Entry 매매비고

int AddTicketbuy,AddTicketsell;                         // 2nd Entry Ticket 


//********************************************************************
//| 3rd Entry Order 관련 변수설정                                    |
//********************************************************************

//***********************************************
// 3rd Entry 매매를 위한 변수 설정

extern double Hg1Multiply=1.5;                           // 3rd-1 Entry 랏 승수
extern double Hg2Multiply=2.0;                           // 3rd-2 Entry 랏 승수
extern double Hg3Multiply=2.5;                           // 3rd-3 Entry 랏 승수
extern double Hg4Multiply=3.0;                           // 3rd-4 Entry 랏 승수

extern bool HgEntry = TRUE;                              // True이면 역으로, False이면 Additional

extern int  Hg1buy = 1;                                  // 최대 3rd Entry Buy 개수
extern int  Hg1sell = 1;                                 // 최대 3rd Entry Sell 개수
extern int  Hg2buy = 1;                                  // 최대 3rd Entry Buy 개수
extern int  Hg2sell = 1;                                 // 최대 3rd Entry Sell 개수
extern int  Hg3buy = 1;                                  // 최대 3rd Entry Buy 개수
extern int  Hg3sell = 1;                                 // 최대 3rd Entry Sell 개수
extern int  Hg4buy = 1;                                  // 최대 3rd Entry Buy 개수
extern int  Hg4sell = 1;                                 // 최대 3rd Entry Sell 개수

extern int Hg1Max = 10;                                  // 최대 Buy/Sell Order 차이 
extern int Hg2Max = 20;                                  // 최대 Buy/Sell Order 차이 
extern int Hg3Max = 30;                                  // 최대 Buy/Sell Order 차이 
extern int Hg4Max = 40;                                  // 최대 Buy/Sell Order 차이 

extern int  HgTP = 30;                                   // 3rd Entry TP
extern int  HgSL = 0;                                    // 3rd Entry SL

extern double HgTrailingStop = 10;                       // 3rd Entry 트레일링 설정시 > 0

extern string HGInitComment = "3rd_gguri_RT_Ilmok_V0.2"; // Hedge Entry 매매비고

int HgTicketbuy,HgTicketsell;                            // 3rd Entry Ticket  
int Hg1MagicBuy,Hg1MagicSell,Hg2MagicBuy,Hg2MagicSell;   // 3rd Magic Number
int Hg3MagicBuy,Hg3MagicSell,Hg4MagicBuy,Hg4MagicSell;   // 3rd Magic Number


//********************************************************************
//| Initialization                                                   |
//********************************************************************

int init()
 {
  StartDay   = TimeToStr(TimeCurrent(),TIME_DATE);
  
  return(0);
 }

//********************************************************************
//| Deinitialization                                                 |
//********************************************************************

int deinit()
  {
   return(0);
  }

//********************************************************************
//| EA Start                                                         |
//********************************************************************

int start() {  // EA 시작

//***********************************************
// 통화별 매직넘버 설정 함수 가져오기

    getmagicbuy();
    getmagicsell();

//***********************************************
// AutoStep설정시 자동계산 Step설정 함수 가져오기

    getbuystep();
    getsellstep();

  if (sellstep > MaxStep || buystep > MaxStep ) {
   if (sellstep >= buystep) {
     buystep = NormalizeDouble((buystep/sellstep)*MaxStep,2);
     sellstep = MaxStep;
     }
     else  
   if (sellstep < buystep) {
     sellstep = NormalizeDouble((sellstep/buystep)*MaxStep,2);
     buystep = MaxStep;
   }
  }
  
  if (sellstep < MinStep || buystep < MinStep) {
   if (sellstep >= buystep) {
    sellstep = NormalizeDouble((sellstep/buystep)*MinStep,2);
    buystep = MinStep;
    }
    else  
   if (sellstep < buystep) {
    buystep = NormalizeDouble((buystep/sellstep)*MinStep,2);
    sellstep = MinStep;
    }
 } 

//***********************************************
// StopOut Balance도달시 강제청산함수 가져오기

    StopOutClose();

//***********************************************
// 통화별 2nd/3rd Entry 매직넘버 설정

    Hg1MagicSell = Magicsell+1;
    Hg1MagicBuy = Magicbuy+1;
    Hg2MagicSell = Magicsell+2;
    Hg2MagicBuy = Magicbuy+2;
    Hg3MagicSell = Magicsell+3;
    Hg3MagicBuy = Magicbuy+3;
    Hg4MagicSell = Magicsell+4;
    Hg4MagicBuy = Magicbuy+4;


//***********************************************
// MarketInfo 정보를 받는 변수 설정

    ask00      = MarketInfo(Symbol(),MODE_ASK);
    bid00      = MarketInfo(Symbol(),MODE_BID);
    mydigit    = MarketInfo(Symbol(), MODE_DIGITS);
    spread     = MarketInfo(Symbol(),MODE_SPREAD);
    sympoint   = MarketInfo(Symbol(),MODE_POINT);
    stoplevel  = MarketInfo(Symbol(), MODE_STOPLEVEL);
    freeze     = MarketInfo(Symbol(), MODE_FREEZELEVEL);
    minlot     = MarketInfo(Symbol(), MODE_MINLOT);
    LotStep    = MarketInfo(Symbol(), MODE_LOTSTEP);

    if (minlot<0.1){
        maxLot=MarketInfo(Symbol(),MODE_MAXLOT);}
    if (minlot>=0.1){
        maxLot=((AccountBalance()/2)/1000);}
    
    servername = AccountServer();
    reqmargin  = MarketInfo(Symbol(), MODE_MARGINREQUIRED);
    stopout    = AccountStopoutLevel();
    leverage   = AccountLeverage();
    mytime     = TimeToStr(TimeCurrent(),TIME_SECONDS);
    equity     = AccountEquity();

//***********************************************
// Trailing 및 BreakEven 설정

    if(TrailingStop > 0) MoveTrailingStop(Magicbuy, Magicsell, TrailingStop);
    if(HgTrailingStop > 0) MoveTrailingStop(Hg1MagicBuy, Hg1MagicSell, HgTrailingStop);
    if(HgTrailingStop > 0) MoveTrailingStop(Hg2MagicBuy, Hg2MagicSell, HgTrailingStop);
    if(HgTrailingStop > 0) MoveTrailingStop(Hg3MagicBuy, Hg3MagicSell, HgTrailingStop);
    if(HgTrailingStop > 0) MoveTrailingStop(Hg4MagicBuy, Hg4MagicSell, HgTrailingStop);
    
    if(BreakEven>0) MoveBreakEven(Magicbuy, Magicsell, BreakEven, BreakPoint);


//***********************************************
// New Bar 설정(One Order / One Bar)

    if(!NewBar()) return(0);

//***********************************************
// Max Spread Limitation 설정

    if(spread > MaxSpread*PointValue()) { 
       InitEntry = FALSE;
       AddEntry = FALSE;
       HgEntry = FALSE;
     }   

//***********************************************
// Order 개수 차이 변수 설정
    
  int buyover = TotalOrders(Magicbuy)-TotalOrders(Magicsell);   
  int sellover = TotalOrders(Magicsell)-TotalOrders(Magicbuy);          

//********************************************************************
//| Close Orders for 1st Orders (CloseOrders)                        |
//********************************************************************
// Target Profit도달시 청산함수

 RefreshRates();
 double TP_buy, TP_sell;

 double InitBuyPrice = FindLastBuyPrice(Magicbuy);
 double InitSellPrice = FindLastSellPrice(Magicsell);

  TP_buy = (TotalOrders(Magicbuy)*TargetProfit*PointValue()*Point)+InitBuyPrice;
  TP_sell = InitSellPrice-(TotalOrders(Magicsell)*TargetProfit*PointValue()*Point);
  
  if(Profit(Magicbuy)>0){
      if(bid00>=TP_buy) BuyClose(Magicbuy);
      }      
  else
  if(Profit(Magicsell)>0){
      if(ask00<=TP_sell) SellClose(Magicsell);
  }


//********************************************************************
//| 2nd Entry 주문입력 함수                                          |
//********************************************************************
// 2nd Entry 변수 설정

 RefreshRates();
 
 bool AddBuyEntry= FALSE;
 bool AddSellEntry= FALSE; 
 
 double buylots = Orderlots(Magicbuy);
 double selllots = Orderlots(Magicsell);
 
 double buystepadjust = buystep*PointValue()*Point;
 double sellstepadjust = sellstep*PointValue()*Point;
 
 double Addlotbuy=NormalizeDouble(AddMultiply*lotsbuy,2);            // 2nd Buy 랏수
 double Addlotsell=NormalizeDouble(AddMultiply*lotssell,2);          // 2nd Sell 랏수
 
//***********************************************
// 2nd Buy Order 
 
  if ( AddEntry && (buylots+Addlotbuy) 
  if ( AddBuyEntry )  {     
       if(TotalOrders(Magicbuy)>=InitOrders) {
           AddTicketbuy = OpenOrders(Symbol(),OP_BUY, Addlotbuy, Slippage, AddSL , AddTP, Magicbuy,1);
           }
   }

//***********************************************
// 2nd Sell Order

  if ( AddEntry && (selllots+Addlotsell)=InitSellPrice+sellstepadjust) ) AddSellEntry = TRUE; 

  if ( AddSellEntry )  {     
       if(TotalOrders(Magicsell)>=InitOrders) {
           AddTicketsell = OpenOrders(Symbol(),OP_SELL, Addlotsell, Slippage, AddSL, AddTP, Magicsell,1);
           }
   }


//********************************************************************
//| 1st Entry Buy/Sell 조건 설정                                     |
//********************************************************************

//********************************************************************
// Buy 조건

/*
매수조건 : 전환선 구름 상단돌파
 - 기준선 상승이나 Flat : 기준선(0) >= 기준선(1) , 기준선(1) >= 기준선(2)
 - 전환선 상승 : 전환선(0) > 전환선(1) , 전환선(1) > 전환선(2)
 - 전환선의 기준선 상향 : 전환선(0) >= 기준선(0), 전환선(1) >= 기준선(1) 
 - 현재종가가 전환선 상향(정배열) : 종가(0) >= 전환선(0)
 - 이전종가가 전환선 상향(정배열) : 종가(1) > 전환선(1)
 - 후행스팬이 후행주가 상향 : 후행스팬(26) >= 종가(26) 
 - 전환선 구름 상단돌파 : 전환선(0) > MathMax( 선행스팬1(0), 선행스팬2(0) ) && 전환선(1) <= MathMax( 선행스팬1(1), 선행스팬2(1) ) 
//---------------------------------------------------------------------------------------------------------------------------------

KiJun0 >= KiJun1 && KiJun1 >= KiJun2 
JunHwan0 > JunHwan1 && JunHwan1 > JunHwan2
JunHwan0 >= KiJun0 && JunHwan1 >= KiJun1
BPrice0 > JunHwan0 && BPrice1 > JunHwan1 
HuHang > LastPrice26 
JunHwan0 > MathMax(SunHangA0 , SunHangB0) && JunHwan1 <= MathMax(SunHangA1 , SunHangB1) 
*/


//=========================================================================
//------------------------------------------------
// 지표설정
//------------------------------------------------

double JunHwan0 = iIchimoku(Symbol(), 0, ShortTerm, MidTerm, LongTerm, MODE_TENKANSEN, 0);
double JunHwan1 = iIchimoku(Symbol(), 0, ShortTerm, MidTerm, LongTerm, MODE_TENKANSEN, 1);
double JunHwan2 = iIchimoku(Symbol(), 0, ShortTerm, MidTerm, LongTerm, MODE_TENKANSEN, 2);
double KiJun0 = iIchimoku(Symbol(), 0, ShortTerm, MidTerm, LongTerm, MODE_KIJUNSEN, 0);
double KiJun1 = iIchimoku(Symbol(), 0, ShortTerm, MidTerm, LongTerm, MODE_KIJUNSEN, 1);
double KiJun2 = iIchimoku(Symbol(), 0, ShortTerm, MidTerm, LongTerm, MODE_KIJUNSEN, 2);
double BPrice0 = iClose(Symbol(), 0, 0);
double BPrice1 = iClose(Symbol(), 0, 1);
double LPrice1 = iLow(Symbol(), 0, 1);
double HPrice1 = iHigh(Symbol(), 0, 1);

double HuHang0 = iIchimoku(Symbol(), 0, ShortTerm, MidTerm, LongTerm, MODE_CHINKOUSPAN, Huhang);
double HuHang1 = iIchimoku(Symbol(), 0, ShortTerm, MidTerm, LongTerm, MODE_CHINKOUSPAN, Huhang+1);

double SunHangA0 = iIchimoku(Symbol(), 0, ShortTerm, MidTerm, LongTerm, MODE_SENKOUSPANA, 0);
double SunHangB0 = iIchimoku(Symbol(), 0, ShortTerm, MidTerm, LongTerm, MODE_SENKOUSPANB, 0);
double SunHangA1 = iIchimoku(Symbol(), 0, ShortTerm, MidTerm, LongTerm, MODE_SENKOUSPANA, 1);
double SunHangB1 = iIchimoku(Symbol(), 0, ShortTerm, MidTerm, LongTerm, MODE_SENKOUSPANB, 1);
double LastPrice26 = iClose(Symbol(), 0, Huhang);
double LastPrice27 = iClose(Symbol(), 0, Huhang+1);

//=========================================================================

bool  buycon1 = FALSE;
bool  buycon2 = FALSE;
bool  buycon3 = FALSE;
bool  buycon4 = FALSE;
bool  buycon5 = FALSE;
bool  buycon6 = FALSE;

bool  BuyCon  = FALSE;

if ( KiJun0 >= KiJun1 && KiJun1 >= KiJun2 ) buycon1=TRUE;

if ( JunHwan0 > JunHwan1 && JunHwan1 > JunHwan2 ) buycon2=TRUE;

if ( JunHwan0 >= KiJun0 && JunHwan1 >= KiJun1 ) buycon3=TRUE;

if ( BPrice0 > JunHwan0 && BPrice1 > JunHwan1 ) buycon4=TRUE;

if ( HuHang0 > LastPrice26 ) buycon5=TRUE;

if ( JunHwan0 > MathMax(SunHangA0 , SunHangB0) && JunHwan1 <= MathMax(SunHangA1 , SunHangB1) ) buycon6=TRUE;

if( buycon1 && buycon2 && buycon3 && buycon4 && buycon5 && buycon6 ) BuyCon=TRUE;

//==========================================================================================================================================================================================================


//********************************************************************
// Sell 조건

/*
매도조건 : 전환선 구름 하단돌파

 - 기준선 하락이나 Flat : 기준선(0) <= 기준선(1) , 기준선(1) <= 기준선(2)
 - 전환선 하락 : 전환선(0) < 전환선(1), 전환선(1) < 전환선(2)
 - 전환선의 기준선 하향 : 전환선(0) <= 기준선(0) , 전환선(1) <= 기준선(2)
 - 현재종가가 전환선 하향(역배열) : 종가(0) < 전환선(0)
 - 이전종가가 전환선 하향(역배열) : 종가(1) < 전환선(1)
 - 후행스팬이 후행주가 하향 : 후행스팬(26) < 종가(26) 
 - 전환선 구름 하단돌파 : 전환선(0) < MathMin( 선행스팬1(0), 선행스팬2(0) ) && 전환선(1) >= MathMin( 선행스팬1(1), 선행스팬2(1) ) 
//---------------------------------------------------------------------------------------------------------------------------------

KiJun0 <= KiJun1 && KiJun1 <= KiJun2 
JunHwan0 < JunHwan1 && JunHwan1 < JunHwan2
JunHwan0 <= KiJun0 && JunHwan1 <= KiJun1 
BPrice0 < JunHwan0 && BPrice1 < JunHwan1 
HuHang < LastPrice26 
JunHwan0 < MathMin(SunHangA0 , SunHangB0) && JunHwan1 >= MathMin(SunHangA1 , SunHangB1)
*/


//=========================================================================

bool  sellcon1 = FALSE;
bool  sellcon2 = FALSE;
bool  sellcon3 = FALSE;
bool  sellcon4 = FALSE;
bool  sellcon5 = FALSE;
bool  sellcon6 = FALSE;

bool  SellCon  = FALSE;

if ( KiJun0 <= KiJun1 && KiJun1 <= KiJun2 ) sellcon1=TRUE;

if ( JunHwan0 < JunHwan1 && JunHwan1 < JunHwan2 ) sellcon2=TRUE;

if ( JunHwan0 <= KiJun0 && JunHwan1 <= KiJun1 ) sellcon3=TRUE;

if ( BPrice0 < JunHwan0 && BPrice1 < JunHwan1 ) sellcon4=TRUE;  

if ( HuHang0 < LastPrice26 ) sellcon5=TRUE; 

if ( JunHwan0 < MathMin(SunHangA0 , SunHangB0) && JunHwan1 >= MathMin(SunHangA1 , SunHangB1) ) sellcon6=TRUE;

if( sellcon1 && sellcon2 && sellcon3 && sellcon4 && sellcon5 && sellcon6 ) SellCon=TRUE;

//==========================================================================================================================================================================================================


//********************************************************************
//| 1st Entry Buy/Sell Order                                         |
//********************************************************************

//********************************************************************
// Buy Order (1st Entry)

 if( InitEntry && TotalOrders(Magicbuy) < InitOrders )  {   // 3
   if( BuyCon )  {    // 4
 
       RefreshRates(); 
       ticketbuy = OpenOrders(Symbol(),OP_BUY, lotsbuy, Slippage, StopLoss, TakeProfit, Magicbuy,0);

       }   // 4
  }  // 3

  else

//********************************************************************
// Sell Order (1st Entry)                                      

 if( InitEntry && TotalOrders(Magicsell) < InitOrders )   {  // 5
   if( SellCon )  {    // 6

       RefreshRates(); 
       ticketsell = OpenOrders(Symbol(),OP_SELL, lotssell, Slippage, StopLoss, TakeProfit, Magicsell,0);

       }   // 6
   }   // 5


//********************************************************************
//| 3rd Entry 주문입력 함수                                          |
//********************************************************************
// 3rd Entry 변수 설정

 RefreshRates();

 double Hg1lotbuy  = NormalizeDouble(lotsbuy*Hg1Multiply,2);    // 3rd-1 Buy 랏수
 double Hg1lotsell = NormalizeDouble(lotssell*Hg1Multiply,2);   // 3rd-1 Sell 랏수
 double Hg2lotbuy  = NormalizeDouble(lotsbuy*Hg2Multiply,2);    // 3rd-2 Buy 랏수
 double Hg2lotsell = NormalizeDouble(lotssell*Hg2Multiply,2);   // 3rd-2 Sell 랏수
 double Hg3lotbuy  = NormalizeDouble(lotsbuy*Hg3Multiply,2);    // 3rd-3 Buy 랏수
 double Hg3lotsell = NormalizeDouble(lotssell*Hg3Multiply,2);   // 3rd-3 Sell 랏수
 double Hg4lotbuy  = NormalizeDouble(lotsbuy*Hg4Multiply,2);    // 3rd-4 Buy 랏수
 double Hg4lotsell = NormalizeDouble(lotssell*Hg4Multiply,2);   // 3rd-4 Sell 랏수

//***********************************************
// 3rd-1 Buy Order / Sell Order(Hedge)
 
  if ( (buylots+Hg1lotbuy)Hg1Max && buyover    if(ask00<=InitBuyPrice-buystepadjust) {  // 1
       if(TotalOrders(Magicbuy)>=InitOrders) {  // 2
         if(!HgEntry && TotalOrders(Hg1MagicBuy)           HgTicketbuy = OpenOrders(Symbol(),OP_BUY,Hg1lotbuy,Slippage,HgSL,HgTP,Hg1MagicBuy,2);
           }  // 3
          else 
         if(HgEntry && TotalOrders(Hg1MagicSell)           HgTicketsell = OpenOrders(Symbol(),OP_SELL,Hg1lotsell,Slippage,HgSL,HgTP,Hg1MagicSell,2);         
           }  // 4
        }   // 2
      }   // 1  
   }  // 0


//***********************************************
// 3rd-1 Sell Order / Buy Order(Hedge)

  if ( (selllots+Hg1lotsell)Hg1Max && sellover    if(bid00>=InitSellPrice+sellstepadjust) {  // 1
       if(TotalOrders(Magicsell)>=InitOrders) {  // 2
         if(!HgEntry && TotalOrders(Hg1MagicSell)           HgTicketsell = OpenOrders(Symbol(),OP_SELL,Hg1lotsell,Slippage,HgSL,HgTP,Hg1MagicSell,2);
           } // 3
       else    
         if(HgEntry && TotalOrders(Hg1MagicBuy)           HgTicketbuy = OpenOrders(Symbol(),OP_BUY,Hg1lotbuy,Slippage,HgSL,HgTP,Hg1MagicBuy,2);
           }  // 4
        }   // 2 
     }  // 1   
  }  // 0

//***********************************************
// 3rd-2 Buy Order / Sell Order(Hedge)
 
  if ( (buylots+Hg2lotbuy)Hg2Max && buyover    if(ask00<=InitBuyPrice-buystepadjust) {  // 1
       if(TotalOrders(Magicbuy)>=InitOrders) {  // 2
         if(!HgEntry && TotalOrders(Hg2MagicBuy)           HgTicketbuy = OpenOrders(Symbol(),OP_BUY,Hg2lotbuy,Slippage,HgSL,HgTP,Hg2MagicBuy,2);
           }  // 3
         else    
         if(HgEntry && TotalOrders(Hg2MagicSell)           HgTicketsell = OpenOrders(Symbol(),OP_SELL,Hg2lotsell,Slippage,HgSL,HgTP,Hg2MagicSell,2);
           }  // 4
        }     // 2 
     }  // 1
  }  // 0

//***********************************************
// 3rd-2 Sell Order / Buy Order(Hedge)

  if ( (selllots+Hg2lotsell)Hg2Max && sellover    if(bid00>=InitSellPrice+sellstepadjust) {  // 1
      if(TotalOrders(Magicsell)>=InitOrders) {  // 2
        if(!HgEntry && TotalOrders(Hg2MagicSell)           HgTicketsell = OpenOrders(Symbol(),OP_SELL,Hg2lotsell,Slippage,HgSL,HgTP,Hg2MagicSell,2);
           }  // 3
         else 
         if(HgEntry && TotalOrders(Hg2MagicBuy)           HgTicketbuy = OpenOrders(Symbol(),OP_BUY,Hg2lotbuy,Slippage,HgSL,HgTP,Hg2MagicBuy,2);
           }  // 4
         }  // 2
      }  // 1 
  }  // 0


//***********************************************
// 3rd-3 Buy Order / Sell Order(Hedge)
 
  if ( (buylots+Hg3lotbuy)Hg3Max && buyover    if(ask00<=InitBuyPrice-buystepadjust) {  // 1
       if(TotalOrders(Magicbuy)>=InitOrders) {  // 2
         if(!HgEntry && TotalOrders(Hg3MagicBuy)           HgTicketbuy = OpenOrders(Symbol(),OP_BUY,Hg3lotbuy,Slippage,HgSL,HgTP,Hg3MagicBuy,2);
           }  // 3
          else 
          if(HgEntry && TotalOrders(Hg3MagicSell)           HgTicketsell = OpenOrders(Symbol(),OP_SELL,Hg3lotsell,Slippage,HgSL,HgTP,Hg3MagicSell,2);
           }  // 4
         }  // 2
      }  // 1
   }  // 0

//***********************************************
// 3rd-3 Sell Order  / Buy Order(Hedge)

  if ( (selllots+Hg3lotsell)Hg3Max && sellover    if(bid00>=InitSellPrice+sellstepadjust) {  // 1
       if(TotalOrders(Magicsell)>=InitOrders) {  // 2
         if(!HgEntry && TotalOrders(Hg3MagicSell)           HgTicketsell = OpenOrders(Symbol(),OP_SELL,Hg3lotsell,Slippage,HgSL,HgTP,Hg3MagicSell,2);
            }  // 3
          else 
          if(HgEntry && TotalOrders(Hg3MagicBuy)           HgTicketbuy = OpenOrders(Symbol(),OP_BUY,Hg3lotbuy,Slippage,HgSL,HgTP,Hg3MagicBuy,2);
           }             // 4                 
         }  // 2
      }   // 1
  }   // 0


//***********************************************
// 3rd-4 Buy Order  / Sell Order(Hedge)
 
  if ( (buylots+Hg4lotbuy)Hg4Max )  {   // 0  
    if(ask00<=InitBuyPrice-buystepadjust) {  // 1
       if(TotalOrders(Magicbuy)>=InitOrders) {  // 2
         if(!HgEntry && TotalOrders(Hg4MagicBuy)           HgTicketbuy = OpenOrders(Symbol(),OP_BUY,Hg4lotbuy,Slippage,HgSL,HgTP,Hg4MagicBuy,2);
           }  // 3
          else 
          if(HgEntry && TotalOrders(Hg4MagicSell)           HgTicketsell = OpenOrders(Symbol(),OP_SELL,Hg4lotsell,Slippage,HgSL,HgTP,Hg4MagicSell,2);
           }  // 4
        }  // 2
     }      // 1                    
 }   // 0


//***********************************************
// 3rd-4 Sell Order  / Buy Order(Hedge)

  if ( (selllots+Hg4lotsell)Hg4Max )  {    // 4 
    if(bid00>=InitSellPrice+sellstepadjust) {  // 3
       if(TotalOrders(Magicsell)>=InitOrders) {  // 2
        if(!HgEntry && TotalOrders(Hg4MagicSell)           HgTicketsell = OpenOrders(Symbol(),OP_SELL,Hg4lotsell,Slippage,HgSL,HgTP,Hg4MagicSell,2);
           }  // 1
          else 
        if(HgEntry && TotalOrders(Hg4MagicBuy)           HgTicketbuy = OpenOrders(Symbol(),OP_BUY,Hg4lotbuy,Slippage,HgSL,HgTP,Hg4MagicBuy,2);
           }  // 0
        }  // 2
     }     // 3  
 }       // 4

//***********************************************
// 주문없는 경우 변수 초기화

  if(TotalOrders(Magicbuy)==0) {
      TP_buy=0;
  }
  
  if(TotalOrders(Magicsell)==0) {
      TP_sell=0;
  }


//********************************************************************
//| Hedge 일괄 청산 함수(Initial + Additional Entry + Hedge Entry)   |
//********************************************************************

 bool TargetCloseAll = false;

 if( Profit(Magicbuy)+Profit(Magicsell)+Profit(Hg1MagicBuy)+Profit(Hg1MagicSell)+Profit(Hg2MagicBuy)+Profit(Hg2MagicSell)+Profit(Hg3MagicBuy)+Profit(Hg3MagicSell)+Profit(Hg4MagicBuy) + Profit(Hg4MagicSell)>TargetProfit) TargetCloseAll = true;
    else TargetCloseAll = false;
  
 if(TargetCloseAll) {   // 22

 int totl = OrdersTotal();

 for(int a=totl-1; a >= 0 ; a--)  {  // 23

 OrderSelect(a, SELECT_BY_POS, MODE_TRADES);
 int typ = OrderType();
 bool results = false;
 RefreshRates();

 if(OrderMagicNumber()==Magicbuy || OrderMagicNumber()==Hg1MagicBuy || OrderMagicNumber()==Magicsell || OrderMagicNumber()==Hg1MagicSell || OrderMagicNumber()==Hg2MagicBuy || OrderMagicNumber()==Hg2MagicSell   
  || OrderMagicNumber()==Hg3MagicBuy || OrderMagicNumber()==Hg3MagicSell || OrderMagicNumber()==Hg4MagicBuy || OrderMagicNumber()==Hg4MagicSell)  {  // 24

  execution = GetTickCount(); 
  switch(typ) {   //switch

  case OP_BUY : results = OrderClose(OrderTicket(),OrderLots(),MarketInfo(OrderSymbol(),MODE_BID),Slippage,Red);
  break;

  case OP_SELL : results = OrderClose(OrderTicket(),OrderLots(),MarketInfo(OrderSymbol(),MODE_ASK),Slippage, Blue);
              } //switch

  execution = GetTickCount()-execution; 

  if(results == false) {  // 25
  Print("Order ", OrderTicket(), " failed to close. Error:", GetLastError() );
                     }   // 25
       }   // 24
  
  }    // 23

}   // 22


//********************************************************************
//| 화면표시정보                                                     |
//********************************************************************

//***********************************************
// 화면표시 변수 설정

  string ScreenStr;

  int hborders = HBuyOrders(Magicbuy)+HBuyOrders(Hg1MagicBuy)+HBuyOrders(Hg2MagicBuy)+HBuyOrders(Hg3MagicBuy)+HBuyOrders(Hg4MagicBuy);
  int hsorders = HSellOrders(Magicsell)+HSellOrders(Hg1MagicSell)+HSellOrders(Hg2MagicSell)+HSellOrders(Hg3MagicSell)+HSellOrders(Hg4MagicSell);
  int horders = hborders+hsorders;
  double hbprofit = HBProfit(Magicbuy)+HBProfit(Hg1MagicBuy)+HBProfit(Hg2MagicBuy)+HBProfit(Hg3MagicBuy)+HBProfit(Hg4MagicBuy);
  double hsprofit = HSProfit(Magicsell)+HSProfit(Hg1MagicSell)+HSProfit(Hg2MagicSell)+HSProfit(Hg3MagicSell)+HSProfit(Hg4MagicSell);
  double hprofit = hbprofit+hsprofit;

  int SellOrd = TotalOrders(Magicsell)+TotalOrders(Hg1MagicSell)+TotalOrders(Hg2MagicSell)+TotalOrders(Hg3MagicSell)+TotalOrders(Hg4MagicSell) ;
  int BuyOrd = TotalOrders(Magicbuy)+TotalOrders(Hg1MagicBuy)+TotalOrders(Hg2MagicBuy)+TotalOrders(Hg3MagicBuy)+TotalOrders(Hg4MagicBuy);
  double ProfitBuy = Profit(Magicbuy)+Profit(Hg1MagicBuy)+Profit(Hg2MagicBuy)+Profit(Hg3MagicBuy)+Profit(Hg4MagicBuy);
  double ProfitSell = Profit(Magicsell)+Profit(Hg1MagicSell)+Profit(Hg2MagicSell)+Profit(Hg3MagicSell)+Profit(Hg4MagicSell);

  string buysteps = DoubleToStr(buystepadjust, mydigit);
  string sellsteps = DoubleToStr(sellstepadjust, mydigit);   

  string SHMax01 = DoubleToStr(iHigh(Symbol(),TimeFrame,iHighest(Symbol(),TimeFrame,MODE_HIGH,HL_Days,1)),mydigit);    
  string SLMin01 = DoubleToStr(iLow(Symbol(),TimeFrame,iLowest(Symbol(),TimeFrame,MODE_LOW,HL_Days,1)),mydigit);
  string SHLAvg01 = DoubleToStr(NormalizeDouble((iHigh(Symbol(),TimeFrame,iHighest(Symbol(),TimeFrame,MODE_HIGH,HL_Days,1)) + iLow(Symbol(),TimeFrame,iLowest(Symbol(),TimeFrame,MODE_LOW,HL_Days,1)))/2.0, Digits),mydigit);
  string SBPrice01 = DoubleToStr(iClose(Symbol(), 1, 1),mydigit);
  string SUpRange = DoubleToStr((iHigh(Symbol(),TimeFrame,iHighest(Symbol(),TimeFrame,MODE_HIGH,HL_Days,1))-iClose(Symbol(), 1, 1)), mydigit);
  string SDownRange = DoubleToStr((iClose(Symbol(), 1, 1)-iLow(Symbol(),TimeFrame,iLowest(Symbol(),TimeFrame,MODE_LOW,HL_Days,1))), mydigit);


//***********************************************
// 화면표시정보

  ScreenStr = StringConcatenate("Server : ",servername," Start Date_",StartDay," , My Time : ",mytime," 평가잔액 = ",equity," Leverage_",leverage,":1, 1Lot당 증거금_$",reqmargin," Target Profit_$",TargetProfit," Execution : ",execution,"ms")+"\n";
  ScreenStr = ScreenStr + StringConcatenate("MaxLot_",maxLot," MinLot_",minlot," Lot Step_",LotStep," StopLevel_",stoplevel," , Freeze Level_",freeze," , StopOut_",stopout,"%, Spread_",spread,", Max Spread_",MaxSpread*PointValue()," buy divider_",buydivider," sell divider_",selldivider)+"\n";
  ScreenStr = ScreenStr + StringConcatenate("기준일수 : ",HL_Days," 통화 : ",Symbol(),"_최고 : ",SHMax01,"_최저 : ",SLMin01," 중간값 : ",SHLAvg01," 현재가 : ",SBPrice01," 상단갭 : ",SUpRange," 하단갭 : ",SDownRange)+"\n";
  ScreenStr = ScreenStr + StringConcatenate("Init Buy Price : ",FindLastBuyPrice(Magicbuy)," Init Sell Price : ",FindLastSellPrice(Magicsell)," BuyStep : ",buysteps," SellStep ",sellsteps)+"\n";
  ScreenStr = ScreenStr + StringConcatenate("매수조건_",BuyCon," 매도조건_",SellCon," 2nd Buy_",AddBuyEntry," 2nd Sell_", AddSellEntry)+"\n";
  ScreenStr = ScreenStr + StringConcatenate("New Profits : ",ProfitBuy+ProfitSell,", New Orders : ",BuyOrd+SellOrd,"건 = Buy ",BuyOrd,"건 / Sell",SellOrd,"건") + "\n";
  ScreenStr = ScreenStr +"=============================================================================="  + "\n";
  ScreenStr = ScreenStr + StringConcatenate("Total Profits : $",hprofit,", Buy : $",hbprofit,", Sell : $",hsprofit,", Total Orders : ",horders,"건 = Total Buy ",hborders,"건 / Total Sell",hsorders,"건")+ "\n";
  Comment(ScreenStr);
 
    for(int ii=0; ii<2; ii+=2){
      ObjectDelete("rect"+ii);
      ObjectCreate("rect"+ii,OBJ_HLINE, 0, 0,TP_sell);
      ObjectSet("rect"+ii, OBJPROP_COLOR, Red);
      ObjectSet("rect"+ii, OBJPROP_WIDTH, 1);
      ObjectSet("rect"+ii, OBJPROP_RAY, False);
   }    
   for(int rr=0; rr<2; rr+=2){
      ObjectDelete("rect1"+rr);
      ObjectCreate("rect1"+rr,OBJ_HLINE, 0, 0,TP_buy);      
      ObjectSet("rect1"+rr, OBJPROP_COLOR, Blue);
      ObjectSet("rect1"+rr, OBJPROP_WIDTH, 1);
      ObjectSet("rect1"+rr, OBJPROP_RAY, False);     
   }
 
  return(0);

}  // EA 종료


//********************************************************************
//| Allow One Action Per Bar                                         |
//********************************************************************
// ***** 현재 바에서 하나만 주문처리시 사용  ****

bool NewBar() {
   static datetime lastbar = 0;
   
   if(lastbar!=Time[0]) {
      lastbar=Time[0];
      return (true);
   }
   return(false);
}


//********************************************************************
//| 통화별 매직넘버 설정 함수                                        |
//********************************************************************

int getmagicbuy() { //buy

if( AutoMagic == TRUE ) {

      if(Symbol() == "AUDUSDm" || Symbol() == "AUDUSD") Magicbuy = 3234805;
      if(Symbol() == "EURGBPm" || Symbol() == "EURGBP") Magicbuy = 5234805;
      if(Symbol() == "EURUSDm" || Symbol() == "EURUSD") Magicbuy = 1234805;
      if(Symbol() == "GBPUSDm" || Symbol() == "GBPUSD") Magicbuy = 2234805;
      if(Symbol() == "USDCADm" || Symbol() == "USDCAD") Magicbuy = 7234805;
      if(Symbol() == "USDCHFm" || Symbol() == "USDCHF") Magicbuy = 6234805;
      if(Symbol() == "USDJPYm" || Symbol() == "USDJPY") Magicbuy = 4234805;

   }

return(Magicbuy);

}

int getmagicsell() { //sell

if( AutoMagic == TRUE )  {

      if(Symbol() == "AUDUSDm" || Symbol() == "AUDUSD") Magicsell = 3234806;
      if(Symbol() == "EURGBPm" || Symbol() == "EURGBP") Magicsell = 5234806;
      if(Symbol() == "EURUSDm" || Symbol() == "EURUSD") Magicsell = 1234806;
      if(Symbol() == "GBPUSDm" || Symbol() == "GBPUSD") Magicsell = 2234806;
      if(Symbol() == "USDCADm" || Symbol() == "USDCAD") Magicsell = 7234806;
      if(Symbol() == "USDCHFm" || Symbol() == "USDCHF") Magicsell = 6234806;
      if(Symbol() == "USDJPYm" || Symbol() == "USDJPY") Magicsell = 4234806;

   }

return(Magicsell);

}


//********************************************************************
//| 통화별 Buy/ Sell Step 설정함수                                   |
//********************************************************************

double getsellstep()  {

 if( AutoStep == TRUE ) {

  double  HMax01 = iHigh(Symbol(),TimeFrame,iHighest(Symbol(),TimeFrame,MODE_HIGH,HL_Days,1)) ;  // 기준기간내 최고가
  double  LMin01 = iLow(Symbol(),TimeFrame,iLowest(Symbol(),TimeFrame,MODE_LOW,HL_Days,1)) ;     // 기준기간내 최저가
  double  BPrice01 = iClose(Symbol(), 1, 1);                                                     // 1분봉 기준 현재 종가

  double UpRange = NormalizeDouble( (HMax01-BPrice01), mydigit) ;                                // 최고가 - 현재가 차이 계산
  sellstep = NormalizeDouble(UpRange / (selldivider*PointValue()*Point),0);                      // Sell Step 계산
  }
  return(sellstep);
}

double getbuystep()  {

 if( AutoStep == TRUE ) {

  double  HMax01 = iHigh(Symbol(),TimeFrame,iHighest(Symbol(),TimeFrame,MODE_HIGH,HL_Days,1)) ;  // 기준기간내 최고가
  double  LMin01 = iLow(Symbol(),TimeFrame,iLowest(Symbol(),TimeFrame,MODE_LOW,HL_Days,1))   ;   // 기준기간내 최저가
  double  BPrice01 = iClose(Symbol(), 1, 1);                                                     // 1분봉 기준 현재 종가

  double DownRange = NormalizeDouble( (BPrice01-LMin01), mydigit) ;                              // 현재가-최저가 차이 계산
  buystep = NormalizeDouble(DownRange / (buydivider*PointValue()*Point),0);                      // Buy Step 계산
  }
  return(buystep);
}


//********************************************************************
//| Open Buy Position Close Function                                 |
//********************************************************************
// ***** 조건충족시 매직넘버별 Buy Position Close 함수  ****

void BuyClose(int Magic)
{    // 함수 시작  
 
  int total = OrdersTotal();
  for(int i=total-1;i>=0;i--)
  {   // Loop 시작
    OrderSelect(i, SELECT_BY_POS);
    bool result = false;
   
    if (OrderMagicNumber() == Magic) {
    RefreshRates();
    execution = GetTickCount(); 
    result = OrderClose( OrderTicket(), OrderLots(), bid00, Slippage, Blue );
    execution = GetTickCount()-execution; 
    
    if(result == false)
    {  // 에러 처리
      Alert("Order " , OrderTicket() , " failed to close. Error:" , GetLastError() );
      Sleep(3000);
    }   // 에러 처리 종료
    
   } 

  }    // Loop 종료

}     // 함수 종료


//********************************************************************
//| Open Sell Position Close Function                                |
//********************************************************************
// ***** 조건충족시 매직넘버별 Sell Position Close 함수  ****

void SellClose(int Magic)
{    // 함수 시작  
 
  int total = OrdersTotal();
  for(int i=total-1;i>=0;i--)
  {   // Loop 시작
    OrderSelect(i, SELECT_BY_POS);
    bool result = false;
   
    if (OrderMagicNumber() == Magic) {
    RefreshRates();
    execution = GetTickCount(); 
    result = OrderClose( OrderTicket(), OrderLots(), ask00, Slippage, Red );
    execution = GetTickCount()-execution; 
    
    if(result == false)
    {  // 에러 처리
      Alert("Order " , OrderTicket() , " failed to close. Error:" , GetLastError() );
      Sleep(3000);
    }   // 에러 처리 종료
    
   } 

  }    // Loop 종료

}     // 함수 종료


//********************************************************************
//| 주문 함수 (OpenOrders)                                           |
//********************************************************************

int OpenOrders( string SymbolName, int CmdType, double Lots, int Slippages, double StopLosses, double TakeProfit, int magic, int EntryType)  {   // 함수 시작

  static string OrderTypeToString[6] = {"OP_BUY", "OP_SELL", "OP_BUYLIMIT", "OP_SELLLIMIT", "OP_BUYSTOP", "OP_SELLSTOP"};

  int Ticket = -1;
  int ErrorCodes;

  int Slips = 0;
  double Vol = 0;
  string Comments;
  string ETComments;
  color CLRs;
  
  RefreshRates();
  
  double stopbuy = NormalizeDouble(ask00-(StopLosses*PointValue()*Point),Digits);
  double stopsell = NormalizeDouble(bid00+(StopLosses*PointValue()*Point),Digits);
  double tpbuy = NormalizeDouble(ask00+(TakeProfit*PointValue()*Point),Digits);
  double tpsell = NormalizeDouble(bid00-(TakeProfit*PointValue()*Point),Digits);

// EntryType = 0 : Init Entry, 1 : Additional Entry, 2 ; Hedge Entry

  switch(EntryType) {   //switch

  case 0 : ETComments = InitComment;
  break;

  case 1 : ETComments = AddInitComment;
  break;

  case 2 : ETComments = HGInitComment;
   } //switch
      
  if (StopLosses == 0) {
      stopbuy = 0;    
      stopsell = 0;
      }
      
  if (TakeProfit == 0) {
      tpbuy = 0;
      tpsell = 0;
      }    
         
  if (StopLosses == 0 && TakeProfit == 0) ECN = FALSE;
      
  if (CmdType == OP_BUY) {   // Buy 시작
      Comments = ETComments+"샀어";
      CLRs = Red;

  if (ECN == true) {  // ECN 시작

    execution = GetTickCount(); 
    Ticket = OrderSend(SymbolName, CmdType, Lots, ask00, Slippages, 0, 0,Comments,magic,0,CLRs);  

    if(Ticket == -1) {  // check for errors
    ErrorCodes = GetLastError();
    Print("아씨!, Error: " + ErrorDescription(ErrorCodes));
    return(-1);
    }  // check for errors

    OrderSelect(Ticket, SELECT_BY_TICKET);

    if (!OrderSelect(Ticket, SELECT_BY_TICKET)) {  // check for errors
    ErrorCodes = GetLastError();
    Print("아씨!, Error: " + ErrorDescription(ErrorCodes));
    return(-1);
    }  // check for errors

    OrderModify(Ticket,OrderOpenPrice(),stopbuy,tpbuy,0,CLRs);
    execution = GetTickCount()-execution; 
    return(0);
    }    // ECN 종료
  else
    {   // No ECN 

    execution = GetTickCount(); 
    Ticket = OrderSend(SymbolName, CmdType, Lots, ask00, Slippages, stopbuy, tpbuy,Comments,magic,0,CLRs);  

    if(Ticket == -1) {  // check for errors
    ErrorCodes = GetLastError();
    Print("아씨!, Error: " + ErrorDescription(ErrorCodes));
    return(-1);
      }  // check for errors
    execution = GetTickCount()-execution; 

    return(0);
    }  // No ECN 종료
  }  // Buy 종료

  else

  if (CmdType == OP_SELL) {    // Sell 시작
      Comments = ETComments+"팔았어";
      CLRs = Blue;

     if (ECN == true) {  // ECN 시작

       execution = GetTickCount(); 
       Ticket = OrderSend(SymbolName, CmdType, Lots, bid00, Slippages, 0, 0,Comments,magic,0,CLRs);

       if(Ticket == -1) {   // check for errors
       ErrorCodes = GetLastError();
       Print("아씨!, Error: " + ErrorDescription(ErrorCodes));
       return(-1);
       }     // check for errors

       OrderSelect(Ticket, SELECT_BY_TICKET);

       if (!OrderSelect(Ticket, SELECT_BY_TICKET)) {    // check for errors
       ErrorCodes = GetLastError();
       Print("아씨!, Error: " + ErrorDescription(ErrorCodes));
       return(-1);
       }     // check for errors

       OrderModify(Ticket,OrderOpenPrice(),stopsell, tpsell,0,CLRs);
       execution = GetTickCount()-execution; 
       return(0);

       }   // ECN 종료
      else
       {  // No ECN 

       execution = GetTickCount(); 
       Ticket = OrderSend(SymbolName, CmdType, Lots, bid00, Slippages, stopsell, tpsell,Comments,magic,0,CLRs);

       if(Ticket == -1) {     // check for errors
       ErrorCodes = GetLastError();
       Print("아씨!, Error: " + ErrorDescription(ErrorCodes));
       return(-1);
       }  // check for errors

       execution = GetTickCount()-execution; 
       return(0);

       }  // No ECN 종료
     }  // Sell 종료


  OrderSelect(OrdersTotal() - 1, SELECT_BY_POS, MODE_TRADES);
                     
    if (OrderSymbol() == SymbolName)  
    {
      Slips = OrderSlipPage(OrderOpenPrice());
      Ticket = OrderTicket();
      Vol = OrderLots();
    }
    
  Print(Ticket, " = OrderSend( ", Comments,", ", SymbolName, ", ", OrderTypeToString[CmdType], ", ", Lots, ", ", DoubleToStr(OrderOpenPrice(), MarketInfo(SymbolName, MODE_DIGITS)),", Execution : ",execution,"ms",
        ", ", Slippages, ", ", StopLosses, ", ", TakeProfit, ") - ", ErrorDescription(ErrorCodes), ", SlipPage = ", Slips, ", Lots = ", Vol);
        
  return(Ticket);
}  // 함수 종료


//********************************************************************
//| Slippage 계산 함수                                               |
//********************************************************************

int OrderSlipPage( double OriginalPrice )  {
  double Tmp;
  int Res;
  
  if (OrderCloseTime() == 0)
  {
    if (OrderType() == OP_BUY)
      Tmp = OriginalPrice - OrderOpenPrice();
    else if (OrderType() == OP_SELL)
      Tmp = OrderOpenPrice() - OriginalPrice;
  }
  else
  {
    if (OrderType() == OP_BUY)
      Tmp = OrderClosePrice() - OriginalPrice;
    else if (OrderType() == OP_SELL)
      Tmp = OriginalPrice - OrderClosePrice();
  }
  
  if (Tmp > 0)
    Res = Tmp / MarketInfo(OrderSymbol(), MODE_POINT) + 0.1;
  else
    Res = Tmp / MarketInfo(OrderSymbol(), MODE_POINT) - 0.1;
  
  return(Res);
}


//********************************************************************
//| 통화별 Point조정 설정                                            |
//********************************************************************
// 5 digit broker adjustment

int PointValue()  {

  if(MarketInfo(Symbol(), MODE_DIGITS)==3 || MarketInfo(Symbol(), MODE_DIGITS)==5)
  {
         mypoint = 10;

  }       
  else
  { 
         mypoint = 1;

  } 
   return(mypoint);
}

//********************************************************************
//| Stop Out조건발생시 전체 일괄 청산 함수                           |
//********************************************************************

void StopOutClose() {  // 0
 
  bool CloseAllOrders = false;

  if(AccountFreeMargin() < StopOutBalance || AccountBalance() < StopOutBalance) CloseAllOrders = true;
    else CloseAllOrders = false;
  
    if(CloseAllOrders) {  // 15

      int totalord = OrdersTotal();

      for(int jk=totalord-1;jk >= 0;jk--)  {  // 16

         OrderSelect(jk, SELECT_BY_POS, MODE_TRADES);
         int types = OrderType();
         bool resultall = false;
         RefreshRates();

     switch(types) {   //switch

             case OP_BUY : resultall = OrderClose(OrderTicket(),OrderLots(),MarketInfo(OrderSymbol(),MODE_BID),5,Red);
             break;

             case OP_SELL : resultall = OrderClose(OrderTicket(),OrderLots(),MarketInfo(OrderSymbol(),MODE_ASK),5, Blue);
             }    //switch

     if(resultall == false) {  // 17
     Print("Order ", OrderTicket(), " failed to close. Error:", GetLastError() );
                         }  // 17

       }  // 16
   }   // 15
}  // 0


//********************************************************************
//| Order Lot Calculate Function(주문 Lot계산 함수)                  |
//********************************************************************

 double Orderlots(int Magic)   {  // 0
 double Lots=0;
 for (int k=0; k < OrdersTotal(); k++)
  {  // 1
  if (OrderSelect(k, SELECT_BY_POS, MODE_TRADES))
    {  // 2
   if (OrderSymbol()==Symbol() && OrderMagicNumber()==Magic)
       {  // 3
       Lots = Lots + OrderLots();
       }  // 3
    }   // 2
  }   // 1
  return(Lots);
}  // 0


//********************************************************************
//| Profit Calculate Function(수익 계산 함수)                        |
//********************************************************************

 double Profit(int Magic)   {  // 0
 double Prof=0;
 for (int k=0; k < OrdersTotal(); k++)
  {  // 1
  if (OrderSelect(k, SELECT_BY_POS, MODE_TRADES))
    {  // 2
   if (OrderSymbol()==Symbol() && OrderMagicNumber()==Magic)
       {  // 3
       Prof = Prof + OrderProfit();
       }  // 3
    }   // 2
  }   // 1
  return(Prof);
}  // 0


//********************************************************************
//| Total order Calculate Function(총오더수 계산 함수)               |
//********************************************************************

int TotalOrders(int MAGIC)  {  // 0
 int cnt=0;
 for (int i=0; i < OrdersTotal(); i++)
  {  // 1
   if (OrderSelect(i, SELECT_BY_POS, MODE_TRADES))
    {  // 2
    if (OrderMagicNumber()==MAGIC && (OrderType()==OP_BUY || OrderType()==OP_SELL))
      {  // 3
      cnt++;
      }  // 3
    }  // 2
  }   // 1
  return(cnt);
}  // 0


//********************************************************************
//| 총매수수익 계산 함수(과거치 포함)                                |
//********************************************************************

 double HBProfit(int Magic)   {  // 0
 double Prof=0;
 for (int k=0; k < OrdersHistoryTotal(); k++)
  {  // 1
  if (OrderSelect(k, SELECT_BY_POS, MODE_HISTORY))
    {  // 2
   if (OrderSymbol()==Symbol() && OrderMagicNumber()==Magic && OrderType()==OP_BUY)
       {  // 3
       Prof = Prof + OrderProfit();
       }  // 3
    }   // 2
  }   // 1
  return(Prof);
}  // 0


//********************************************************************
//| 총매도수익 계산 함수(과거치 포함)                                |
//********************************************************************

 double HSProfit(int Magic)  {  // 0
 double Prof=0;
 for (int k=0; k < OrdersHistoryTotal(); k++)
  {  // 1
  if (OrderSelect(k, SELECT_BY_POS, MODE_HISTORY))
    {  // 2
   if (OrderSymbol()==Symbol() && OrderMagicNumber()==Magic && OrderType()==OP_SELL)
       {  // 3
       Prof = Prof + OrderProfit();
       }  // 3
    }   // 2
  }   // 1
  return(Prof);
}  // 0


//********************************************************************
//| 총Buy오더수 계산 함수(과거치 포함)                               |
//********************************************************************

int HBuyOrders(int MAGIC) {  // 0
 int cnt=0;
 for (int i=0; i < OrdersHistoryTotal(); i++)
  {  // 1
   if (OrderSelect(i, SELECT_BY_POS, MODE_HISTORY))
    {  // 2
    if (OrderMagicNumber()==MAGIC && OrderType()==OP_BUY)
      {  // 3
      cnt++;
      }  // 3
    }  // 2
  }   // 1
  return(cnt);
}  // 0


//********************************************************************
//| 총Sell오더수 계산 함수(과거치 포함)                              |
//********************************************************************

int HSellOrders(int MAGIC)  {  // 0
 int cnt=0;
 for (int i=0; i < OrdersHistoryTotal(); i++)
  {  // 1
   if (OrderSelect(i, SELECT_BY_POS, MODE_HISTORY))
    {  // 2
    if (OrderMagicNumber()==MAGIC && OrderType()==OP_SELL)
      {  // 3
      cnt++;
      }  // 3
    }  // 2
  }   // 1
  return(cnt);
}  // 0

//********************************************************************
//| Trailing Stop                                                    |
//********************************************************************

void MoveTrailingStop(int magicbuy, int magicsell, double trailing)  { 
   int ct,totl=OrdersTotal();

   RefreshRates();
    
   for(ct=0;ct<totl;ct++)
   {
      OrderSelect(ct,SELECT_BY_POS,MODE_TRADES);

      if(OrderType()==OP_BUY && OrderSymbol()==Symbol() && OrderMagicNumber()==magicbuy)
         {
            if( trailing > 0 && Bid > NormalizeDouble(OrderOpenPrice()+trailing*PointValue()*Point,Digits) )  
            {                 
               if((NormalizeDouble(OrderStopLoss(),Digits) < NormalizeDouble(Bid-PointValue()*trailing*Point,Digits))||(OrderStopLoss()==0))
               {
                  OrderModify(OrderTicket(),OrderOpenPrice(),NormalizeDouble(Bid-PointValue()*trailing*Point,Digits),OrderTakeProfit(),0,Blue);
                  return(0);
               }
            }
         }
      if(OrderType()==OP_SELL && OrderSymbol()==Symbol() && OrderMagicNumber()==magicsell)
         {
            if( trailing > 0 && Ask < NormalizeDouble(OrderOpenPrice()-trailing*PointValue()*Point,Digits) )  
            {                 
               if((NormalizeDouble(OrderStopLoss(),Digits) > (NormalizeDouble(Ask+(PointValue()*trailing*Point),Digits)))||(OrderStopLoss()==0))
               {
                  OrderModify(OrderTicket(),OrderOpenPrice(),NormalizeDouble(Ask+(PointValue()*trailing*Point),Digits),OrderTakeProfit(),0,Red);
                  return(0);

            }
         }
      }
   }
}


//********************************************************************
//| Break Even Strategy                                              |
//********************************************************************

void MoveBreakEven(int magicbuy, int magicsell, double breakeven, double breakpoint)  {
   int cnt,total=OrdersTotal();

   RefreshRates();

   for(cnt=0;cnt<total;cnt++)
   {
      OrderSelect(cnt,SELECT_BY_POS,MODE_TRADES);

      if( OrderType()<=OP_SELL && OrderSymbol()==Symbol() && (OrderMagicNumber()==magicbuy || OrderMagicNumber()==magicsell) )
      {
         if(OrderType()==OP_BUY)
         {
            if(breakeven>0)
            {
               if(NormalizeDouble((Bid-OrderOpenPrice()),Digits) > breakeven*PointValue()*Point)
               {
                  if(NormalizeDouble((OrderStopLoss()-OrderOpenPrice()),Digits) < 0)
                  {
                     OrderModify(OrderTicket(),OrderOpenPrice(),NormalizeDouble(OrderOpenPrice()+breakpoint*PointValue()*Point,Digits),OrderTakeProfit(),0,Blue);
                     return(0);
                  }
               }
            }
         }
         else
         {
            if(breakeven>0)
            {
               if(NormalizeDouble((OrderOpenPrice()-Ask),Digits) > breakeven*PointValue()*Point)
               {
                  if(NormalizeDouble((OrderOpenPrice()-OrderStopLoss()),Digits) < 0)
                  {
                     OrderModify(OrderTicket(),OrderOpenPrice(),NormalizeDouble(OrderOpenPrice()-breakpoint*PointValue()*Point,Digits),OrderTakeProfit(),0,Red);
                     return(0);
                  }
               }
            }
         }
      }
   }
}

 


//********************************************************************
//| Find Last Buy Price Function                                     |
//********************************************************************

double FindLastBuyPrice(int Magics) {

   double ord_open_price;
   int ord_ticket;
   double buffers = 0;
   int ticket_compair = -1;

   for (int cnt = 0; cnt < OrdersTotal(); cnt++) {
      OrderSelect(cnt, SELECT_BY_POS, MODE_TRADES);
      if (OrderSymbol() != Symbol() || OrderMagicNumber() != Magics) continue;

      if (OrderSymbol() == Symbol() && OrderMagicNumber() == Magics) {

         ord_ticket = OrderTicket();
         if (ord_ticket > ticket_compair) {
            ord_open_price = OrderOpenPrice();
            buffers = ord_open_price;
            ticket_compair = ord_ticket;
         }
      }
   }
   return (ord_open_price);
}


//********************************************************************
//| Find Last Sell Price Function                                    |
//********************************************************************

double FindLastSellPrice(int Magics) {

   double ord_open_price;
   int ord_ticket;
   double buffers = 0;
   int ticket_compair = -1;

   for (int cnt = 0; cnt < OrdersTotal(); cnt++) {

      OrderSelect(cnt, SELECT_BY_POS, MODE_TRADES);
      if (OrderSymbol() != Symbol() || OrderMagicNumber() != Magics) continue;

      if (OrderSymbol() == Symbol() && OrderMagicNumber() == Magics && OrderType() == OP_SELL) {

         ord_ticket = OrderTicket();
         if (ord_ticket > ticket_compair) {
            ord_open_price = OrderOpenPrice();
            buffers = ord_open_price;
            ticket_compair = ord_ticket;
         }
      }
   }
   return (ord_open_price);
}

 

'IT관련' 카테고리의 다른 글

일목균형표에 대한 요약  (0) 2023.03.07
메타트레이더 EA - Winner M15  (0) 2019.09.22
메타트레이더 EA - Winner H4  (0) 2019.09.21
메타트레이더 EA - RT IlmokCloud  (0) 2019.09.20
메타트레이더 EA - Named Pipe Sub  (0) 2019.09.19

+ Recent posts