Librerías: Easy Canvas - página 12

 
Nikolai Semko:

¿Esto se aplica al modo normal o al probador?

Modo normal, Nikolai.

 
Nikolai Semko:

Gracias.

¿Esta función no es adecuada?

Desgraciadamente no. Mueve el objeto bitmap en sí, necesito una función que mueva los puntos x del contenido. Sé que internamente la memoria consiste en un array x, y pero no existe memmove o algo así en mql. No se como mover la memoria rápidamente.

 
Владислав Качило :

Modo normal, Nikolai.

Suelo seguir el siguiente esquema:

  1. Hago todo el dibujo, ligado a barras o tiempo, en una función, por ejemplo void Draw()
  2. en OnChartEvent añado la línea
    if (id == CHARTEVENT_CHART_CHANGE ) Draw (); 
    siguiendo el evento de cambio de gráfico (una nueva barra es también un evento de cambio de gráfico)
  3. en OnCalculate para el modo test añado una línea para redibujar por ejemplo cuando se produce una nueva barra, porque OnChartEvent no funciona:
    .
     if(rate_total-prev_calculated == 1) if (Canvas.tester) {ChartChanged (); Draw ();}

Si no funciona en MT4, entonces algo va mal con el evento CHARTEVENT_CHART_CHANGE. Ahora no puedo comprobarlo, aún no hay cotizaciones.

 
Nikolai Semko:

Suelo hacer lo siguiente:

  1. Hago todo el dibujo, ligado a barras o tiempo, en una función, por ejemplo void Draw()
  2. añado una línea a OnChartEvent para seguir el evento de cambio de gráfico (una nueva barra es también un evento de cambio de gráfico).
  3. en OnCalculate para el modo test añado una línea para redibujar por ejemplo cuando se produce una nueva barra, porque OnChartEvent no funciona:

Si no funciona en MT4, entonces algo va mal con el evento CHARTEVENT_CHART_CHANGE. Ahora no puedo comprobarlo, aún no hay cotizaciones.

Nicolás, para que no pierdas el tiempo, escribí más arriba una solución que resolvió mi problema, a saber, como bien notaste, el siguiente código insertado en OnCalcucate():

if(rates_total - prev_calculated == 1)ChartChanged();

 
Mighty7:

Desgraciadamente no. Mueve el objeto bitmap en sí, necesito una función que mueva los puntos x del contenido. Sé que internamente la memoria consiste en un array x, y pero no existe memmove o algo así en mql. No se como mover la memoria rápidamente.

No lo he entendido, ¿necesitas mover el área rectangular dentro de todo el lienzo?

 
Vladyslav Katsylo:

Nicolás, para que no pierdas el tiempo escribí más arriba una solución que resolvió mi problema, a saber, como bien notaste, el siguiente código insertado en OnCalcucate():

En modo normal no test no deberías hacer esto, porque la función ChartChanged() se ejecutaría dos veces seguidas, lo cual no es razonable. Después de todo, se ejecuta cuando se produce el evento CHARTEVENT_CHART_CHANGE dentro del fichero iCanvas.mqh.
Es correcto redibujar el lienzo ligado a barras o tiempo en OnChartEvent cuando se produce el evento de cambio de ventana ( CHARTEVENT_CHART_CHANGE) sin utilizar ChartChanged().

 
Vladyslav Katsylo:

Nicolás, para que no pierdas el tiempo, escribí más arriba una solución que resolvió mi problema, a saber, como bien notaste, el siguiente código insertado en OnCalcucate():

Debes tener en cuenta lo siguiente:

  • ChartChanged() se ejecuta cada vez que se produce el evento CHARTEVENT_CHART_CHANGE en OnChartEvent dentro de la clase iCanvas
  • El OnChartEvent dentro de la clase iCanvas se ejecuta primero , y luego se ejecuta el OnChartEvent de su código.

Tu problema se debía a que OnCalculate se ejecuta aparentemente antes que OnChartEvent y por tanto ChartChanged() no se ha procesado todavía.
Por eso es razonable implementar el manejador de redibujado exactamente en OnChartEvent y no en OnCalculate
. Especialmente debería hacerse porque el usuario puede cambiar el tamaño de la ventana en cualquier momento. El evento CHARTEVENT_CHART_CHANGE es responsable de todo esto

 
Nikolai Semko:

No lo he entendido, ¿hay que mover el área rectangular dentro de todo el lienzo?

Sí. Ejemplo: Dibujo un círculo en el centro del lienzo a pantalla completa y quiero mover el círculo hacia la izquierda, pero no quiero borrar toda el área y volver a pintar el círculo con cada movimiento, sino simplemente desplazar la memoria hacia la izquierda.

El CCanvas es simplemente un Array x/y de puntos.

   uint              m_pixels[];               // matriz de píxeles
//+------------------------------------------------------------------+
//| Obtener el color del píxel|
//+------------------------------------------------------------------+
uint CCanvas::PixelGet(const int x,const int y) const
  {
//--- comprueba las coordenadas
   if(x>=0 && x<m_width && y>=0 && y<m_height)
      return(m_pixels[y*m_width+x]);
//--- error
   return(0);
  }

Me refiero a una función que mueva los m_pixels a la izquierda, derecha, arriba, abajo.

 
Mighty7:

Sí. Ejemplo: Dibujo un círculo en el centro del lienzo a pantalla completa y quiero desplazar el círculo hacia la izquierda, pero no quiero borrar toda el área y volver a pintar el círculo con cada movimiento, sino simplemente desplazar la memoria hacia la izquierda.

El CCanvas es simplemente un Array x/y de puntos.

Me refiero a una función que mueva los m_pixels a la izquierda, derecha, arriba, abajo.

Sí, es un deseo razonable.
Tanto más que no es difícil implementarlo.
Lo pensé, pero llegué a la conclusión de que si hay necesidad de mover la parte rectangular del lienzo común, hay una manera más fácil de implementarlo:

  • Crear un nuevo lienzo más pequeño. En este caso, usted no tiene que preocuparse de llenar el fondo de la parte que se va a mover.

Sí, un deseo bien fundado.
Además, no es difícil ponerlo en práctica.
Pensé en ello, pero llegué a la conclusión de que si hay una necesidad de mover la parte rectangular del lienzo común, entonces hay una manera más fácil de implementarlo:
  • Crear un nuevo lienzo más pequeño. En este caso, usted no tiene que preocuparse de llenar el fondo de la parte móvil.
 
Nikolai Semko:

Sí, un deseo bastante razonable.
Tanto más que no es difícil ponerlo en práctica.
Lo pensé, pero llegué a la conclusión de que si hay necesidad de mover la parte rectangular del lienzo general, hay una manera más fácil de ponerlo en práctica:

  • Crear un nuevo lienzo más pequeño. En este caso, usted no tiene que preocuparse de llenar el fondo de la parte que se va a mover.

Sí, un deseo bien fundado.
Además, no es difícil ponerlo en práctica.
Pensé en ello, pero llegué a la conclusión de que si hay una necesidad de mover la parte rectangular del lienzo común, entonces hay una manera más fácil de implementarlo:
  • Crear un nuevo lienzo más pequeño. En este caso, usted no tiene que preocuparse de llenar el fondo de la parte móvil.

Eso no funciona porque mi lienzo es la pantalla completa. Es como un gráfico de ticks pero cuesta demasiado tiempo borrar todo el fondo y construcht y pintar todo nuevo así que necesito mover el contenido a la izquierda (ej. 8 pixels) y dibujar solo los nuevos 8 pixels (8 px en dirección x y altura completa) con nuevos datos. He intentado mover el Canvas 8 px a la izquierda con MoveCanvas y esto funciona pero no puedo redimensionarlo de forma que de la izquierda se quiten 8 px de ancho y a la derecha se añadan 8 px. Espero que lo entiendas...