Discusión sobre el artículo "¡Visualice esto! La biblioteca gráfica en MQL5 como un análogo de plot en el lenguaje R"

 

Artículo publicado ¡Visualice esto! La biblioteca gráfica en MQL5 como un análogo de plot en el lenguaje R:

A la hora de investigar y estudiar patrones, la representación visual con la ayuda de gráficos juega un papel fundamental. En los lenguajes populares de programación en la comunidad científica, tales como R y Python, para la visualización se usa la función especial plot. Con su ayuda, es posible dibujar líneas, gráficos de dispersión e histogramas para visualizar patrones. En MQL5 usted puede hacer lo mismo con la ayuda de la clase CGraphics.

Al usar las funciones, puede aparecer el error "división por cero". Este problema se puede resolver de dos formas:

  • desactivar en  el archivo metaeditor.ini el control de la división por cero
    [Experts]
    FpNoZeroCheckOnDivision=1
  • o bien analizar la fórmula usada en la función y retornar para estos casos un valor válido. Encontrará un ejemplo de este procesamiento con ayuda de una macro en los archivos adjuntos 3Functions.mq5 y bat.mq5.



Autor: MetaQuotes Software Corp.

 
¡Buen trabajo! Gracias. Ya iba a arreglar el algoritmo CircleAA
Por cierto, la función CircleWu se puede simplificar y acelerar:

void CCanvas::CircleWu(const int x,const int y,const double r,const uint clr,const uint style=UINT_MAX)
  {
   if(r<=0)
      return;
//--- cálculos preliminares
   double r2=r*r;
   double quarter=round(r*M_SQRT1_2);
//--- establecer el estilo de línea
   uint prev_style=m_style;
   if(style!=UINT_MAX)
      LineStyleSet(style);
   uint mask=1<<m_style_idx;
//--- dibujar
   for(int dx=0; dx<=quarter; dx++)
     {
      double dy=sqrt(r2-dx*dx);
      double alpha1=dy-floor(dy);
      double alpha2=1-alpha1;
      if((m_style&mask)==mask)
        {
         PixelTransform4(x,y,dx,(int)(dy)+1,clr,alpha1);
         PixelTransform4(x,y,dx,(int)(dy),clr,alpha2);
         PixelTransform4(x,y,(int)dy+1,dx,clr,alpha1);
         PixelTransform4(x,y,(int)dy,dx,clr,alpha2);
        }
      mask<<=1;
      if(mask==0x1000000)
         mask=1;
     }
  
//--- establecer el estilo de línea anterior
   if(style!=UINT_MAX)
      m_style=prev_style;
  }
 
Nikolai Semko:
¡Buen trabajo! Gracias. Ya iba a arreglar el algoritmo CircleAA
Por cierto, la función CircleWu se puede simplificar y acelerar:
¡Gracias por la idea, se harán ediciones!
 

Puede cambiar las propiedades de la propia gráfica y de cada una de sus funciones en cualquier momento. Por ejemplo, vamos a añadir leyendas a los ejes del gráfico, cambiar el nombre de la curva y activar el modo de aproximación spline para ella:

#include <Graphics\Graphic.mqh>
//+------------------------------------------------------------------+
//| Función de inicio del programa de script|
//+------------------------------------------------------------------+
void OnStart()
  {
   CGraphic graphic;
   graphic.Create(0,"Graphic",0,30,30,780,380);
   double x[]={-10,-4,-1,2,3,4,5,6,7,8};
   double y[]={-5,4,-10,23,17,18,-9,13,17,4};
   CCurve *curve=graphic.CurveAdd(x,y,CURVE_LINES);
   curve.Name("Example");                 
   curve.LinesIsSmooth(true);             
   graphic.XAxis().Name("X - axis");      
   graphic.XAxis().NameSize(12);          
   graphic.YAxis().Name("Y - axis");      
   graphic.YAxis().NameSize(12);
   graphic.YAxis().ValuesWidth(15);
   graphic.CurvePlotAll();
   graphic.Update();
   DebugBreak();
  }

 У меня метод называется LinesSmooth LineIsSmooth нету. Продолжаю изучать дальше :)

 

 
Orangetree:

Puede cambiar las propiedades de la propia gráfica y de cada una de sus funciones en cualquier momento. Por ejemplo, vamos a añadir leyendas a los ejes del gráfico, cambiar el nombre de la curva y activar el modo de aproximación spline para ella:

  {
   curve.LinesIsSmooth(true);             

 У меня метод называется LinesSmooth LineIsSmooth нету. Продолжаю изучать дальше :)

 

El método fue renombrado posteriormente. Gracias, corregido en el artículo
 

¿Cómo puedo hacer que cuando se redibuja una curva en el gráfico, se actualice también la escala?

curve5.Update(resultPrices);
    
graphicfirst.Redraw(); и Update()


la propia curva se actualiza, pero la escala con los precios antiguos permanece y el gráfico se desplaza fuera de los límites del lienzo

Ya lo encontré, necesito hacer CalculateMaxMinValues() :)

 
Maxim Dmitrievsky:
¿Podríais decirme cómo redibujar correctamente un gráfico ya creado, por ejemplo, al cambiar los valores de las matrices? Redraw() y Update() no tienen ningún efecto

Buenas tardes, ¿exactamente cómo has intentado redibujar el gráfico?

Si sólo necesitas cambiar los datos de una curva concreta, aquí tienes un ejemplo que funciona:

#include <Graphics\Graphic.mqh>
//+------------------------------------------------------------------+
//| Función de inicio del programa de script|
//+------------------------------------------------------------------+
void OnStart()
  {
//--- dato 1
   double x1[]={-10,-4,-1,2,3,4,5,6,7,8};
   double y1[]={-5,4,-10,23,17,18,-9,13,17,4};
//--- datos 2
   double x2[]={-10,-10,10,10};
   double y2[]={-10,10,-10,10};
//--- gráfico
   CGraphic graph;
   graph.HistoryNameWidth(80);
   graph.Create(0,"Graph",0,30,30,830,430);
//--- Puntos
   CCurve *curve=graph.CurveAdd(x1,y1,CURVE_LINES);
   graph.CurvePlot(0);
   graph.Update();
   Sleep(1000);
   curve.Update(x2,y2);
   graph.Redraw(true);
   graph.Update();
   Sleep(1000);
  }
P.D. Hay un hilo en el foro sobre la librería Graphics, donde ya se ha planteado esta cuestión.
 
Roman Konopelko:

Buenas tardes, ¿cómo intentaba exactamente redibujar el gráfico?

Si sólo necesitas cambiar los datos de una curva concreta, aquí tienes un ejemplo que funciona:

P.D. Hay un hilo en el foro sobre la librería Graphics, en él ya se ha planteado esta cuestión.
gracias, ya lo he resuelto, estaba haciendo exactamente lo mismo, sólo que en un array... sólo hay que recalcular graph.CalculateMaxMinValues() para la gráfica también, entonces se actualiza la escala.
 
Maxim Dmitrievsky:
Gracias, ya lo he solucionado, hice exactamente lo mismo, sólo en un array. sólo tienes que recalcular graph.CalculateMaxMinValues() para el gráfico también, entonces la escala se actualiza
Si llamas al método CGraphic::Redraw(const bool rescale=false) con el parámetro true, las escalas se recalcularán automáticamente (no hace falta llamar a CalculateMaxMinValues por separado).
 
Roman Konopelko:
Si llamas al método CGraphic::Redraw(const bool rescale=false) con el parámetro true, las escalas se recalcularán automáticamente (sin necesidad de llamar a CalculateMaxMinValues por separado).

Correcto, lo tengo. gracias )
 

¿Es posible hacer dos o más escalas en el gráfico, similares a las de una regla, donde las divisiones se dan en centímetros y pulgadas, con valores que sólo se dan si el punto se utilizó para trazar el gráfico?