//+------------------------------------------------------------------+ //| ProjectName | //| Copyright 2012, CompanyName | //| http://www.companyname.net | //+------------------------------------------------------------------+ /* iCustom(NULL,0,"~StochAM",Kperiod,Dperiod,Slowing,PriceField, Source,SourcePeriod,Window,Sens,Power,Smooth,Signal,Fade, N,i); где N: 0 - стохастик 1 - сигнальная %D 2 - рез-т нормирования 3 - сглаживание затухания 4 - буфер источника волатильности // не выводится 5 - сырое нормирование // не выводится */ #property indicator_separate_window // в окне индикатора #property indicator_buffers 6 #property indicator_color1 Green // стохастик #property indicator_color2 Red // сигнальная #property indicator_maximum 100 #property indicator_minimum 0 #property indicator_level1 80 #property indicator_level2 20 // входные параметры extern int Kperiod=5; // %K extern int Dperiod=3; // %D: >0 SMA, <0 EMA double kDp; // коэфф.EMA для %D bool bDp; extern int Slowing=3; // замедление int Method=0; // метод сглаживания %D extern int PriceField=0; // 0- High/Low, 1- Close extern int Source=2; // 0- объем, 1- ATR, 2- ст.дев., 3- Close extern int SourcePeriod=5; // период источника, <0 EMA, >0 SMA double kSp; // коэфф.EMA для SourcePeriod bool bSp; extern int Window=5; // окно нормирования в барах extern double Sens=2; // порог чувствтительности в пп.или тиках (объем) double sens; // порог чувствтительности в ценах или тиках (объем) extern double Power=2; // степень для передаточной функции extern int Smooth=1; // сглаживание нормирования double kSm; // коэфф.EMA для Smooth bool bSl; extern int Signal=1; // сигнальная double kSg; // коэфф.EMA для Signal bool bSg; extern int Fade=12; // затухание сигнальной double kFd; // коэфф.EMA для Fade int History=0; // 0- все бары // массивы инд.буферов double STH[], // стохастик SGN[], // сигнальная (%D) стохастика NRM[], // рез-т нормирования NEG[], // сглаживание затухания SRC[], // буфер источника волатильности // не выводится NR0[]; // сырое нормирование // не выводится // общие (глобальные) переменные bool first=1; // флаг первого запуска //+------------------------------------------------------------------+ //| | //+------------------------------------------------------------------+ // инициализация int init() { first=1; // флаг первого запуска string _sth="Stoch("+(string)Kperiod+","+(string)Dperiod+","+(string)Slowing+") "; if(Source>0) sens=Sens*Point; // приведение порога к ценам для ценовых источников else sens=Sens; if(Sens>0) string _sn=DoubleToStr(Sens,1)+" "; // вычисление коэффициентов EMA if(Dperiod<0) {Dperiod=-Dperiod; kDp=2.0/(1+Dperiod); bDp=1;} else bDp=0; if(SourcePeriod<0) {SourcePeriod=-SourcePeriod; kSp=2.0/(1+SourcePeriod); bSp=1;} else bSp=0; if(Smooth<0) {Smooth=-Smooth; kSm=2.0/(1+Smooth); bSl=1;} else bSl=0; if(Signal<0) {Signal=-Signal; kSg=2.0/(1+Signal); bSg=1;} else bSg=0; kFd=2.0/(1+Fade); string _sgfd=" ("+(string)Signal+","+(string)Fade+")"; string _src=""; switch(Source) { case 0: _src=_src+"Volume"; break; // объем case 1: _src=_src+"ATR"; break; // ATR case 2: _src=_src+"StDev"; break; // ст.девиация case 3: _src=_src+"Close"; break; // Close case 4: _src=_src+"H/L"; // High/Low } _src=_src+"("+(string)SourcePeriod+")"; string _nrm=" ["+(string)Window+","+(string)Smooth+"]"; IndicatorShortName(_sth+_sn+_src+_nrm+_sgfd); // инд.буферы SetIndexBuffer(0,STH); SetIndexStyle(0,DRAW_LINE); SetIndexLabel(0,_sth); SetIndexBuffer(1,SGN); SetIndexStyle(1,DRAW_LINE,2); SetIndexLabel(1,"Sgn("+(string)Slowing+")"); SetIndexBuffer(2,NRM); SetIndexStyle(2,DRAW_NONE); SetIndexLabel(2,_nrm); SetIndexBuffer(3,NEG); SetIndexStyle(3,DRAW_NONE,2); SetIndexLabel(3,"Neg"+_sgfd); SetIndexBuffer(4,SRC); SetIndexStyle(4,DRAW_NONE); SetIndexLabel(4,NULL); SetIndexBuffer(5,NR0); SetIndexStyle(5,DRAW_NONE); SetIndexLabel(5,NULL); return(0); } // ф-я дополнительной инициализации int reinit() { ArrayInitialize(STH,0.0); // обнуление массива ArrayInitialize(SGN,0.0); // обнуление массива ArrayInitialize(NRM,0.0); // обнуление массива ArrayInitialize(NEG,0.0); // обнуление массива ArrayInitialize(SRC,0.0); // обнуление массива ArrayInitialize(NR0,0.0); // обнуление массива return(0); } //+------------------------------------------------------------------+ //| | //+------------------------------------------------------------------+ int start() { int ic=IndicatorCounted(); if(!first && Bars-ic-1>1) ic=reinit(); // если есть пропущенные бары не на подключении - пересчет bool ic0=ic==0; // флаг пересчета int limit=Bars-ic; // кол-во пересчетов if(ic==0) { reinit(); limit-=3; } for(int i=limit; i>=0; i--) { // цикл пересчета по ВСЕМ барам bool reset=i==limit && ic0; // сброс на первой итерации цикла пересчета if(reset) { static int BarsPrev=0; // пред. значение Bars } bool NewBar=(ic0 && i>0) || BarsPrev!=Bars; // первый тик нового бара //========================================= // источник int sh=i+SourcePeriod; switch(Source) { case 0: // объем if(bSp) SRC[i]=kSp*Volume[i]+(1-kSp)*SRC[i+1]; // ЕМА else { // SMA double ma=SRC[i+1]*SourcePeriod-Volume[sh]; SRC[i]=(ma+Volume[i])/SourcePeriod; } break; case 1: SRC[i]=iATR(NULL,0,SourcePeriod,i); break; // ATR case 2: SRC[i]=iStdDev(NULL,0,SourcePeriod,0,bSp,0,i); break; // ст.девиация case 3: // Close if(bSp) SRC[i]=kSp*Close[i]+(1-kSp)*SRC[i+1]; // ЕМА else { // SMA ma=SRC[i+1]*SourcePeriod-Close[sh]; SRC[i]=(ma+Close[i])/SourcePeriod; } break; } //========================================= // нормирование // экстремумы double max=SRC[ArrayMaximum(SRC,Window,i)]; double min=SRC[ArrayMinimum(SRC,Window,i)]; double c=SRC[i]; // шумоподавление double delta=max-min; // размах double diff=sens-delta; // разница между порогом чувств. и размахом if(diff>0) { // если разница >0 (размах меньше порога), то delta=sens; // размах = порогу, min-=diff/2; // новое значение минимума } // нормирование if(delta!=0) NR0[i]=MathPow((c-min)/delta,Power); //== // замедление if(bSl) NRM[i]=kSm*NR0[i]+(1-kSm)*NRM[i+1]; // EMA else { // SMA sh=i+Smooth; ma=NRM[i+1]*Smooth-NR0[sh]; NRM[i]=(ma+NR0[i])/Smooth; } //== // сигнальная if(reset) {static double sgnPrev=0;} if(bSg) double sgn=kSg*NRM[i]+(1-kSg)*sgnPrev; // EMA else { // SMA sh=i+Signal; ma=sgnPrev*Signal-NRM[sh]; sgn=(ma+NRM[i])/Signal; } //== // затухание сигнальной // по затуханию NEG[i]=kFd*sgn+(1-kFd)*NEG[i+1]; if(sgn>NEG[i+1]) NEG[i]=sgn; //========================================= // стохастик double sth=iStochastic(NULL,0,Kperiod,1,Slowing,0,PriceField,0,i)-50; STH[i]=NEG[i]*sth+50; // модуляция номированной волатильностью // сигнальная %D if(bDp) SGN[i]=kDp*STH[i]+(1-kDp)*SGN[i+1]; // EMA else { // SMA sh=i+Dperiod; if(sh