MQL4 Как предупредить, когда цена достигнет определенного уровня?
У меня есть этот бесплатный индикатор это имя FiboPiv_v2.mq4
,
Это инструмент, который я использую с хорошим результатом в скальпинге. Обычно я устанавливаю предупреждение вручную, но вижу, что код открыт, и поэтому я хотел бы внести изменения, но я новичок в программировании на MQL4.
Я хотел бы добавить всплывающее окно и звук, который говорит что-то вроде " AUDUSD достиг S1 ".
Код индикатора:
#property indicator_chart_window
//+------------------------------------------------------------------+
//| Custom indicator initialization function |
//+------------------------------------------------------------------+
int init()
{
//---- indicators
return(0);
}
//+------------------------------------------------------------------+
//| Custom indicator deinitialization function |
//+------------------------------------------------------------------+
int deinit()
{
//----
ObjectDelete("S1");
ObjectDelete("S2");
ObjectDelete("S3");
ObjectDelete("R1");
ObjectDelete("R2");
ObjectDelete("R3");
ObjectDelete("PIVIOT");
ObjectDelete("Support 1");
ObjectDelete("Support 2");
ObjectDelete("Support 3");
ObjectDelete("Piviot level");
ObjectDelete("Resistance 1");
ObjectDelete("Resistance 2");
ObjectDelete("Resistance 3");
Comment(" ");
//----
return(0);
}
//+------------------------------------------------------------------+
//| Custom indicator iteration function |
//+------------------------------------------------------------------+
int start()
{
double rates[1][6],yesterday_close,yesterday_high,yesterday_low;
ArrayCopyRates(rates,Symbol(),PERIOD_D1);
//----
if(DayOfWeek()==1)
{
if(TimeDayOfWeek(iTime(Symbol(),PERIOD_D1,1))==5)
{
yesterday_close= rates[1][4];
yesterday_high = rates[1][3];
yesterday_low=rates[1][2];
}
else
{
for(int d=5;d>=0;d--)
{
if(TimeDayOfWeek(iTime(Symbol(),PERIOD_D1,d))==5)
{
yesterday_close= rates[d][4];
yesterday_high = rates[d][3];
yesterday_low=rates[d][2];
}
}
}
}
else
{
yesterday_close= rates[1][4];
yesterday_high = rates[1][3];
yesterday_low=rates[1][2];
}
//---- Calculate Pivots
Comment("\nYesterday quotations:\nH ",yesterday_high,"\nL
",yesterday_low,"\nC ",yesterday_close);
double R=yesterday_high-yesterday_low;//range
double p=(yesterday_high+yesterday_low+yesterday_close)/3;// Standard Pivot
double r3 = p + (R * 1.000);
double r2 = p + (R * 0.618);
double r1 = p + (R * 0.382);
double s1 = p - (R * 0.382);
double s2 = p - (R * 0.618);
double s3 = p - (R * 1.000);
//----
drawLine(r3,"R3",Lime,0);
drawLabel("Resistance 3",r3,Lime);
drawLine(r2,"R2",Green,0);
drawLabel("Resistance 2",r2,Green);
drawLine(r1,"R1",DarkGreen,0);
drawLabel("Resistance 1",r1,DarkGreen);
drawLine(p,"PIVIOT",Blue,1);
drawLabel("Piviot level",p,Blue);
drawLine(s1,"S1",Maroon,0);
drawLabel("Support 1",s1,Maroon);
drawLine(s2,"S2",Crimson,0);
drawLabel("Support 2",s2,Crimson);
drawLine(s3,"S3",Red,0);
drawLabel("Support 3",s3,Red);
//----
return(0);
}
//+------------------------------------------------------------------+
void drawLabel(string name,double lvl,color Color)
{
if(ObjectFind(name)!=0)
{
if(Bars<10) return;
ObjectCreate(name,OBJ_TEXT,0,Time[10],lvl);
ObjectSetText(name,name,8,"Arial",EMPTY);
ObjectSet(name,OBJPROP_COLOR,Color);
}
else
{
if(Bars<10) return;
ObjectMove(name,0,Time[10],lvl);
}
}
//----
void drawLine(double lvl,string name,color Col,int type)
{
if(ObjectFind(name)!=0)
{
ObjectCreate(name,OBJ_HLINE,0,Time[0],lvl,Time[0],lvl);
if(type==1)
ObjectSet(name,OBJPROP_STYLE,STYLE_SOLID);
else
ObjectSet(name,OBJPROP_STYLE,STYLE_DOT);
ObjectSet(name,OBJPROP_COLOR,Col);
ObjectSet(name,OBJPROP_WIDTH,1);
}
else
{
ObjectDelete(name);
ObjectCreate(name,OBJ_HLINE,0,Time[0],lvl,Time[0],lvl);
if(type==1)
ObjectSet(name,OBJPROP_STYLE,STYLE_SOLID);
else
ObjectSet(name,OBJPROP_STYLE,STYLE_DOT);
ObjectSet(name,OBJPROP_COLOR,Col);
ObjectSet(name,OBJPROP_WIDTH,1);
}
}
//+--------------------------------------------------------------------+
1 ответ
Первый:
Забудь иметь Alert()
вызов внутри типа индикатора MQL4-кода. За подробностями исх. ниже + MQL4 Документация по таким и аналогичным образом запрещенным вызовам.
Следующий:
Оригинальный код был ужасно неэффективным
(подробности см. в документации по New -MQL4.56789, в 2018/Q2 по-прежнему выполняются все (в действительности, все экземпляры платформы CustomIndicator + с одновременным управлением индикаторами + внутри одного, одиночного, уязвимого для блокировки, SPOF-потока (!!))
Этакий код, исправленный по эффективности, который не " встряхивает все деревья " снизу вверх для каждого QUOTE
-прибытие, которое выполняет все необходимые обновления и показывает схему звукового сигнала:
#property indicator_chart_window
double R, r3, r2, r1, p, s1, s2, s3; // SEMI-GLOBALs for easy runPriceCHECKs()
//+------------------------------------------------------------------+
//| Custom indicator iteration function |
//+------------------------------------------------------------------+
int start()
{
static int aLastVisitedBAR = EMPTY; // INIT
if ( aLastVisitedBAR == iBars( _Symbol, PERIOD_D1 ) ) // TEST:
{ runPriceCHECKs(); // Check Price v/s PIVOT levels
return( 0 ); // but PIVOTs never change during the same day ... so JIT/RET--^
}
else aLastVisitedBAR == iBars( _Symbol, PERIOD_D1 ); // SYNC & RE-CALC:
double rates[][6], yesterday_close,
yesterday_high,
yesterday_low;
ArrayCopyRates( rates,
_Symbol,
PERIOD_D1
);
//----
if ( DayOfWeek() == 1 )
{
if ( TimeDayOfWeek( iTime( _Symbol, PERIOD_D1, 1 ) ) == 5 )
{
yesterday_close = rates[1][4];
yesterday_high = rates[1][3];
yesterday_low = rates[1][2];
}
else
{
for ( int d = 5; d >= 0; d-- )
{
if ( TimeDayOfWeek( iTime( _Symbol, PERIOD_D1, d ) ) == 5 )
{
yesterday_close = rates[d][4];
yesterday_high = rates[d][3];
yesterday_low = rates[d][2];
}
}
}
}
else
{
yesterday_close = rates[1][4];
yesterday_high = rates[1][3];
yesterday_low = rates[1][2];
}
//---- Calculate Pivots
Comment( "\nYesterday quotations:\nH ",
yesterday_high, "\nL ",
yesterday_low, "\nC ",
yesterday_close
);
R = yesterday_high - yesterday_low; // a Day range
p = ( yesterday_high + yesterday_low + yesterday_close ) /3;// a Standard Pivot
r3 = p + ( R * 1.000 ); drawLine( r3, "R3", clrLime, 0 ); drawLabel( "Resistance 3", r3, clrLime );
r2 = p + ( R * 0.618 ); drawLine( r2, "R2", clrGreen, 0 ); drawLabel( "Resistance 2", r2, clrGreen );
r1 = p + ( R * 0.382 ); drawLine( r1, "R1", clrDarkGreen, 0 ); drawLabel( "Resistance 1", r1, clrDarkGreen );
drawLine( p, "PIVOT", clrBlue, 1 ); drawLabel( "Pivot level", p, clrBlue );
s1 = p - ( R * 0.382 ); drawLine( s1, "S1", clrMaroon, 0 ); drawLabel( "Support 1", s1, clrMaroon );
s2 = p - ( R * 0.618 ); drawLine( s2, "S2", clrCrimson, 0 ); drawLabel( "Support 2", s2, clrCrimson );
s3 = p - ( R * 1.000 ); drawLine( s3, "S3", clrRed, 0 ); drawLabel( "Support 3", s3, clrRed );
//----
runPriceCHECKs(); // Check Price v/s PIVOT levels
//----
return( 0 );
}
//+------------------------------------------------------------------+
//| drawLabel( string name, double lvl, color Color ) |
//+------------------------------------------------------------------+
void drawLabel( string name, double lvl, color Color )
{
if ( Bars < 10 ) return;
if ( ObjectFind( name ) == 0 ) ObjectMove( name, 0, Time[10], lvl );
else
{ ObjectCreate( name, OBJ_TEXT, 0, Time[10], lvl );
ObjectSet( name, OBJPROP_COLOR, Color );
ObjectSetText( name, name, 8, "Arial", EMPTY );
}
}
//+------------------------------------------------------------------+
//| drawLine( double lvl, string name, color Col, int type ) |
//+------------------------------------------------------------------+
void drawLine( double lvl, string name, color Col, int type )
{
if ( ObjectFind( name ) == 0 )
ObjectDelete( name );
ObjectCreate( name, OBJ_HLINE, 0, Time[0], lvl,
Time[0], lvl );
ObjectSet( name, OBJPROP_COLOR, Col );
ObjectSet( name, OBJPROP_WIDTH, 1 );
ObjectSet( name, OBJPROP_STYLE, ( type == 1 ) ? STYLE_SOLID : STYLE_DOT );
}
//+------------------------------------------------------------------+
//| runPriceCHECKs() |
//+------------------------------------------------------------------+
void runPriceCHECKs()
{
#define DEF_PROXIMITY_TRESHOLD_R3 ( 15 * Point )
#define DEF_PROXIMITY_TRESHOLD_R2 ( 10 * Point )
#define DEF_PROXIMITY_TRESHOLD_R1 ( 5 * Point )
#define DEF_PROXIMITY_TRESHOLD_P ( 2 * Point )
#define DEF_PROXIMITY_TRESHOLD_S1 ( 5 * Point )
#define DEF_PROXIMITY_TRESHOLD_S2 ( 10 * Point )
#define DEF_PROXIMITY_TRESHOLD_S3 ( 15 * Point )
if ( MathAbs( r3 - Close ) <= DEF_PROXIMITY_TRESHOLD_R3 )
...
PlaySound( aFileNAME_WAV_R3 ); // The file must be located in terminal_directory\Sounds or its sub-directory. Only WAV files are played.
// Sleep( 250 ); // 250 [ms] AS A LAST RESORT, BETTER MAKE .WAV CUT-SHORT NOT TO LAST LONGER BY ITSELF
// PlaySound( NULL );
return;
if ( MathAbs( r2 - Close ) <= DEF_PROXIMITY_TRESHOLD_R2 )
...
return;
if ( MathAbs( r1 - Close ) <= DEF_PROXIMITY_TRESHOLD_R1 )
...
return;
if ( MathAbs( p - Close ) <= DEF_PROXIMITY_TRESHOLD_P )
...
return;
if ( MathAbs( s1 - Close ) <= DEF_PROXIMITY_TRESHOLD_S1 )
...
return;
if ( MathAbs( s2 - Close ) <= DEF_PROXIMITY_TRESHOLD_S2 )
...
return;
if ( MathAbs( s3 - Close ) <= DEF_PROXIMITY_TRESHOLD_S3 )
...
return;
// nop
}
//+------------------------------------------------------------------+
//| Custom indicator initialization function |
//+------------------------------------------------------------------+
int init()
{ return( 0 );
}
//+------------------------------------------------------------------+
//| Custom indicator deinitialization function |
//+------------------------------------------------------------------+
int deinit()
{
//----
ObjectDelete( "S1" );
ObjectDelete( "S2" );
ObjectDelete( "S3" );
ObjectDelete( "R1" );
ObjectDelete( "R2" );
ObjectDelete( "R3" );
ObjectDelete( "PIVOT" );
ObjectDelete( "Support 1" );
ObjectDelete( "Support 2" );
ObjectDelete( "Support 3" );
ObjectDelete( "Piviot level" );
ObjectDelete( "Resistance 1" );
ObjectDelete( "Resistance 2" );
ObjectDelete( "Resistance 3" );
Comment( ":o)" );
//----
return( 0 );
}
//+------------------------------------------------------------------+