//+------------------------------------------------------------------+ //| DRAW_CANDLES.mq5 | //| Copyright 2000-2024, MetaQuotes Ltd. | //| https://www.mql5.com | //+------------------------------------------------------------------+ #property copyright "Copyright 2000-2024, MetaQuotes Ltd." #property link "https://www.mql5.com" #property version "1.00" #property description "DRAW_CANDLES를 시연할 지표." #property description "별도의 창에 선택한 심볼의 촛대를 그립니다" #property description " " #property description "캔들스틱의 색상과 너비 및 심볼이 변경됩니다" #property description "모든 N 틱을 임의로" #property indicator_separate_window #property indicator_buffers 4 #property indicator_plots 1 //--- 막대 플롯 #property indicator_label1 "DRAW_CANDLES1" #property indicator_type1 DRAW_CANDLES #property indicator_color1 clrGreen #property indicator_style1 STYLE_SOLID #property indicator_width1 1 //--- 매개변수 입력 input int N=5; // 유형을 변경할 틱의 수 input int bars=500; // 표시할 막대의 수 input bool messages=false; // "엑스퍼트 어드바이저" 로그에 미시지 표시 //--- 지표 버퍼 double Candle1Buffer1[]; double Candle1Buffer2[]; double Candle1Buffer3[]; double Candle1Buffer4[]; //--- 심볼 이름 string symbol; //--- 색상을 저장할 배열 color colors[]={clrRed,clrBlue,clrGreen,clrPurple,clrBrown,clrIndianRed}; //+------------------------------------------------------------------+ //| 사용자 지정 지표 초기화 함수 | //+------------------------------------------------------------------+ int OnInit() { //--- 막대가 매우 작을 경우 미리 작업을 완료 하십시오 if(bars<50) { Comment("더 많은 수의 막대를 지정하십시오! 지표 작동이 종료되었습니다"); return(INIT_PARAMETERS_INCORRECT); } //--- 지표 버퍼 맵핑 SetIndexBuffer(0,Candle1Buffer1,INDICATOR_DATA); SetIndexBuffer(1,Candle1Buffer2,INDICATOR_DATA); SetIndexBuffer(2,Candle1Buffer3,INDICATOR_DATA); SetIndexBuffer(3,Candle1Buffer4,INDICATOR_DATA); //--- 빈 값 PlotIndexSetDouble(0,PLOT_EMPTY_VALUE,0); //--- 막대가 그려진 심볼의 이름 symbol=_Symbol; //--- 심볼 표시 설정 PlotIndexSetString(0,PLOT_LABEL,symbol+" Open;"+symbol+" High;"+symbol+" Low;"+symbol+" Close"); IndicatorSetString(INDICATOR_SHORTNAME,"DRAW_CANDLES("+symbol+")"); //--- return(INIT_SUCCEEDED); } //+------------------------------------------------------------------+ //| 사용자 지정 지표 반복 함수 | //+------------------------------------------------------------------+ int OnCalculate(const int rates_total, const int prev_calculated, const datetime &time[], const double &open[], const double &high[], const double &low[], const double &close[], const long &tick_volume[], const long &volume[], const int &spread[]) { static int ticks=INT_MAX-100; //--- 틱을 계산하여 선의 스타일, 색상 및 너비 변경 ticks++; //--- 충분한 수의 틱이 누적된 경우 if(ticks>=N) { //--- 마켓 워치 창에서 새 심볼을 선택 symbol=GetRandomSymbolName(); //--- 양식 변경 ChangeLineAppearance(); //--- 마켓 워치 창에서 새 심볼을 선택 int tries=0; //--- 플롯 1의 버퍼를 심볼로 5번 채웁니다 while(!CopyFromSymbolToBuffers(symbol,rates_total,0, Candle1Buffer1,Candle1Buffer2,Candle1Buffer3,Candle1Buffer4) && tries<5) { //--- CopyFromSymbolToBuffers() 기능의 호출 카운터 tries++; } //--- 틱 카운터를 0으로 재설정 ticks=0; } //--- 다음 호출을 위한 prev_calculated의 반환 값 return(rates_total); } //+------------------------------------------------------------------+ //| 지정된 캔들스틱을 채웁니다 | //+------------------------------------------------------------------+ bool CopyFromSymbolToBuffers(string name, int total, int plot_index, double &buff1[], double &buff2[], double &buff3[], double &buff4[] ) { //--- rates[] 배열에서 시가, 고가, 저가, 종가를 복사합니다 MqlRates rates[]; //--- 시도의 카운터 int attempts=0; //--- 복사된 분량 int copied=0; //--- 원하는 심볼에 시계열을 35회 입력 while(attempts<25 && (copied=CopyRates(name,_Period,0,bars,rates))<0) { Sleep(100); attempts++; if(messages) PrintFormat("%s CopyRates(%s) attempts=%d",__FUNCTION__,name,attempts); } //--- 충분한 수의 막대를 복사하지 못한 경우 if(copied!=bars) { //--- 메시지 문자열 형성 string comm=StringFormat("심볼 %s의 경우 %d 의 요청된 막대 중 %d 만 수신했습니다", name, copied, bars ); //--- 기본 차트 창의 코멘트에 메시지 표시 Comment(comm); //--- 메시지 표시 if(messages) Print(comm); return(false); } else { //--- 심볼 표시 설정 PlotIndexSetString(plot_index,PLOT_LABEL,name+" Open;"+name+" High;"+name+" Low;"+name+" Close"); } //--- 빈 값으로 버퍼 초기화 ArrayInitialize(buff1,0.0); ArrayInitialize(buff2,0.0); ArrayInitialize(buff3,0.0); ArrayInitialize(buff4,0.0); //--- 버퍼에 대한 각 틱 복사 가격 for(int i=0;i<copied;i++) { //--- 버퍼의 적절한 인덱스 계산 int buffer_index=total-copied+i; //--- 버퍼에 가격 쓰기 buff1[buffer_index]=rates[i].open; buff2[buffer_index]=rates[i].high; buff3[buffer_index]=rates[i].low; buff4[buffer_index]=rates[i].close; } return(true); } //+------------------------------------------------------------------+ //| 마켓 워치에서 임의로 심볼을 반환 | //+------------------------------------------------------------------+ string GetRandomSymbolName() { //--- 마켓 워치 창에 표시되는 심볼의 수 int symbols=SymbolsTotal(true); //--- 목록에서 심볼의 포지션 - 0부터 심볼까지의 임의의 숫자 int number=MathRand()%symbols; //--- 지정된 포지션에 있는 심볼의 이름을 반환 return SymbolName(number,true); } //+------------------------------------------------------------------+ //| 막대의 모양 변경 | //+------------------------------------------------------------------+ void ChangeLineAppearance() { //--- 막대 속성에 대한 정보 구성을 위한 문자열 string comm=""; //--- 막대 색상을 변경하기 위한 블록 int number=MathRand(); // 임의 숫자 가져오기 //--- 제수는 colors[] 배열의 크기와 같습니다 int size=ArraySize(colors); //--- 정수 나눗셈의 나머지의 새로운 색상을 선택할 인덱스를 가져오기 int color_index=number%size; //--- 색상을 PLOT_LINE_COLOR 속성으로 설정 PlotIndexSetInteger(0,PLOT_LINE_COLOR,colors[color_index]); //--- 색상 쓰기 comm=comm+"\r\n"+(string)colors[color_index]; //--- 심볼 이름 쓰기 comm="\r\n"+symbol+comm; //--- 설명을 사용하여 차트에 정보 표시 Comment(comm); } |