English Русский 中文 Deutsch 日本語 Português
Desarrollo de robots comerciales usando programación visual

Desarrollo de robots comerciales usando programación visual

MetaTrader 5Trading | 7 febrero 2022, 10:14
1 524 0
Evgenii Shcherbakov
Evgenii Shcherbakov

Introducción

Como regla general, podemos reducir las estrategias comerciales a un algoritmo específico que se puede automatizar. Los robots comerciales son capaces de realizar operaciones comerciales miles de veces más rápido que un ser humano, pero no todos los tráders tienen habilidades de programación.

botbrains.app es una plataforma no-code que permite desarrollar robots comerciales. Para crear un robot comercial en el editor BotBrains, el usuario no necesita programar: solo tiene que arrastrar los bloques necesarios al esquema, indicar sus parámetros y establecer los vínculos entre ellos.

La aplicación botbrains.app dispone de documentación (docs.botbrains.app); en ella se describen todos los conceptos del editor. Este artículo describe la interfaz del editor y sus funciones clave. Además, analiza la implementación de la estrategia comercial "Cruce de medias móviles".


Capacidades del editor

En BotBrains no solo podemos desarrollar robots comerciales simples (por por ejemplo, robots de negociación basados ​​en el cruce de medias móviles), sino también implementar algoritmos comerciales complejos (por ejemplo, robots de negociación basados ​​en el trading con spread entre símbolos). En BotBrainspodemos vincular un robot comercial a un bot personal de Telegram usando bloques, enviar mensajes sobre los resultados comerciales y mandar capturas de pantalla de gráficos con un tamaño arbitrario. También podemos crear una interfaz de robot completa en el editor de BotBrains: crear botones fácilmente y asignarles acciones, añadir campos de edición para controlar los valores de las variables justo durante la ejecución del robot; hay muchos otros bloques disponibles para crear una interfaz de robot. 

A continuación, mostraremos un recuadro con las categorías de los bloques disponibles en el editor de botbrains. La lista completa de bloques disponibles se presenta al final del artículo.

Categoría Descripción
Eventos Los bloques se activan cuando ocurre un determinado evento comercial, por ejemplo, un cambio en el precio de un gráfico o en la profundidad de mercado.
Condición
El bloque de condición realiza la comprobación.
Ciclo
Los ciclos tienen muchos usos. Por ejemplo, usando un ciclo, podemos iterar por todos los símbolos disponibles y determinar el símbolo que ha realizado el mayor movimiento en la última sesión comercial.
Indicadores
Los indicadores son una de las principales herramientas de análisis técnico. BotBrains ofrece una amplia gama de indicadores, desde volúmenes simples hasta nubes Ichimoku.
Análisis gráfico
Por ejemplo, podemos obtener información sobre una vela específica, u obtener el precio máximo/mínimo para un periodo de tiempo determinado. También podemos dibujar líneas verticales y horizontales en el gráfico.
Análisis de la profundidad de mercado
Obtener información sobre el spread y los campos de la profundidad de mercado.
Transacciones
Colocación de órdenes de mercado, límite y stop. Eliminar órdenes límite y stop. Cierre de posiciones.
Variables
Cambiar los valores de las variables. Por ejemplo, podemos almacenar en una variable la cantidad de lotes con los que comerciará el robot.
Sonidos
Cuando sucede algo, puede reproducir un sonido específico, por ejemplo, el sonido "señal de compra", al cumplirse todas las condiciones para realizar una compra.
Obtener información
Obtener información sobre la cuenta, la sesión comercial, las órdenes límite/stop activas, el símbolo, la hora, las órdenes límite/stop históricas y las transacciones históricas.
Enumeraciones
Iteración de la lista de símbolos, iteración de la lista de órdenes límite y stop activas. Iteración de órdenes de límite/stop y transacciones históricas.
Telegram
Enviar mensajes y capturas de pantalla propios de gráficos en Telegram.
Interfaz
Construir una interfaz de robot comercial completa. Los elementos individuales de la interfaz se pueden cambiar usando bloques de modificación. Podemos asignar acciones a los botones de la interfaz. Usando los bloques de interfaz de "campo de edición", podemos cambiar los valores de las variables directamente durante el comercio. Todo esto nos permite crear interfaces dinámicas.
Constantes predefinidas
Básicamente, las constantes predefinidas se usan para realizar comprobaciones. Por ejemplo, hay 3 constantes predefinidas para la dirección de la posición: compra, venta y sin dirección. Podemos obtener la dirección de la posición abierta actual y compararla con una de las constantes predefinidas.
Depuración
Con el bloque de depuración, podemos mostrar la información sobre la depuración en el diario del terminal. Por ejemplo, usando el bloque de depuración, es posible comprobar si las variables contienen los valores correctos.
Otros bloques
Cierre del terminal, cese completo del robot, suspensión temporal del robot. Iniciar sesión en un archivo, notificar en el terminal, realizar comentarios en el gráfico.
Operaciones matemáticas
Suma, resta, multiplicación, división, resto de división, raíz cuadrada, exponenciación. Comparaciones: menor que, mayor que, menor o igual que, mayor o igual que.
Operadores lógicos
Hay operadores lógicos para la construcción de condiciones: AND, OR, NOT.
Teletransporte
Hay bloques para entrar y salir del teletransporte. A veces, debemos cambiar rápida y convenientemente a la ejecución de otra sección del esquema; con la ayuda de teletransportes, esto se realiza en cuestión de segundos.
Bloques de conversión a un tipo
De forma predeterminada, todos los datos del usuario se almacenan como un número. Con la ayuda de los bloques de conversión, podemos especificar explícitamente en qué formato queremos representar los datos. Hay 4 tipos: entero, fraccionario, string, fecha y hora.
Selección de una variable o constante
Selección de una variable o constante.
Introducir un valor
Introducción de un valor.

Interfaz del editor BotBrains

El editor de BotBrains tiene 3 modos: Lógica, Interfaz, Código.

Modo "Lógica":

En el modo "lógica", podemos crear el esquema lógico de un robot. En este modo, podemos usar la gran mayoría de bloques: desde el bloque "si" y los bloques para realizar transacciones hasta los bloques para enviar mensajes a Telegram y los bloques para iniciar sesión en el robot. En este modo, usted desarrollará la lógica de su robot comercial. Con bloques simples, podremos especificar lo que debe hacer nuestro robot: cuándo comprar, cuándo vender, cuándo enviar mensajes a Telegram, cuándo dejar de comerciar, etc. En total, hay más de 140 bloques disponibles en el editor de botbrains, con los que podemos implementar casi cualquier estrategia comercial.

Logic mode

Modo "Interfaz":

En el modo "Interfaz", como su nombre indica, podemos construir la interfaz de un robot comercial. En solo un par de minutos, se puede crear una interfaz de robot comercial completa. Cada elemento de la interfaz tiene ajustes completos de aspecto exterior. Usando el bloque "Modificar elemento de la interfaz", podemos cambiar directamente los parámetros de los elementos de la interfaz mientras el robot está funcionando.

interface mode

Modo "Código":

En este modo, podemos ver el código generado del robot comercial. Para generar un código de robot comercial, solo debemos presionar la tecla ~ o clicar en el botón correspondiente en la barra de herramientas de la derecha.

Code mode

Inicio de un robot comercial

El código completo de nuestro robot comercial se generará en cuestión de segundos después de presionar una tecla en el teclado. Para ejecutar un robot creado con BotBrains, deberemos asegurarnos de que todas las dependencias necesarias hayan sido establecidas:

  1. La biblioteca botbrains_lib.ex5
  2. El archivo de inclusión botbrains_lib.mqh
  3. El archivo de inclusión botbrains_constants.mqh
  4. Los archivos de sonido

Si las dependencias mencionadas no han sido instaladas, los robots creados con BotBrains no podrán ejecutarse o no funcionarán correctamente.

Podemos descargar todas las dependencias necesarias en el siguiente enlace. La instalación de las dependencias se abarca con detalle en el correspondiente artículo sobre documentación.

Ejemplo: cruce de medias móviles

Vamos a analizar la implementación de la estrategia comercial "Cruce de medias móviles". Podemos abrir el esquema terminado inmediatamente en el editor clicando en el enlace.

Abrimos el editor y creamos en nuestro robot 5 constantes:

  1. slow_ma_period periodo de la media móvil lenta (valor constante: 60)
  2. fast_ma_period - periodo de la media móvil rápida  (valor constante: 30)
  3. symbol - código del símbolo con el que se comercia  (valor constante: MGCV21 o cualquier otro símbolo disponible para el comercio)
  4. admin_id - id del usuario de Telegram a quien nuestro robot enviará mensajes con la información sobre las transacciones y las capturas de pantalla de los gráficos (valor constante: su ID de Telegram)
  5. lot - número de lotes comerciados

constants

Para determinar si dos medias móviles se cruzan, necesitamos crear 4 variables:

  1. ma_slow - valor actual de la media móvil lenta
  2. ma_fast - valor actual de la media móvil rápida
  3. ma_slow_prev - valor de la media móvil lenta en la vela anterior
  4. ma_fast_prev - valor de la media móvil rápida en la vela anterior


Así, nos bastará con comparar los valores de estas variables para determinar la intersección de las medias móviles lenta y rápida. Tenga en cuenta que no establecemos el valor inicial de las variables: el valor de dichas variables se actualizará con la llegada de un nuevo tick para el instrumento con el que comerciamos.

Vamos a hacer que cuando se inicie el robot, se muestre el mensaje "Robot iniciado" en el diario del terminal. Para conseguir esto, solo necesitaremos arrastrar dos bloques al esquema lógico del robot: el bloque de eventos "Inicio del robot" y el bloque "Mensaje en el diario", y vincular los conectores de estos bloques:

robot launch message

Por consiguiente, indicaremos que cuando el robot se inicie (bloque de eventos "Inicio del robot"), se ejecute el bloque "Mensaje en el diario".

En la configuración del bloque "Mensaje en el diario", especificamos el mensaje que deberá mostrarse cuando se inicie el robot:

journal message block settings

Cuando llega un nuevo tick para un instrumento comerciado, nuestro robot debe cambiar los valores de las variables. Para ello, arrastraremos el bloque de eventos "Nuevo tick" y 4 bloques "Establecer el valor de variable calculado" al esquema lógico del robot. Vamos a establecer los vínculos entre estos bloques:

variables update on new tick

Con la ayuda del bloque "Moving Average", podemos obtener el valor de la media móvil. Este bloque tiene los siguientes parámetros:

  1. Símbolo
  2. Marco temporal 
  3. Número de periodos
  4. Método de suavizado
  5. Precio utilizado
  6. Desplazamiento

Usando el parámetro "desplazamiento", podemos obtener el valor del indicador en una vela específica. Por ejemplo, un cambio 0 muestra el valor del indicador en la vela actual, mientras que un cambio 1 muestra el valor del indicador en la vela anterior. Por consiguiente, podemos obtener los valores de las medias móviles rápida y lenta en las velas actuales y anteriores; para esto, deberemos indicar diferentes valores para los parámetros "Número de periodos" y "Desplazamiento". 

Arrastramos el bloque del indicador "Moving Average" al cuerpo del primer bloque:


Estabecemos los parámetros del bloque "Moving Average":

Tenga en cuenta que las constantes correspondientes se usan como valores de los parámetros "Símbolo" y "Número de periodos". También podemos usar variables como valores de los parámetros de los bloques.

El trabajo con variables y constantes se describe en el correspondiente artículo de la documentación.

Por lo tanto, el valor actual de la media móvil lenta se escribirá en la variable "ma_slow" cada vez que llegue un nuevo tick para el instrumento comerciado.

Vamos a hacer lo mismo con la variable "ma_fast":

En esta etapa, estamos actualizando los valores actuales de las medias móviles, pero para determinar la intersección, deberemos conocer el valor de las medias móviles en la vela anterior. Por ello, en los últimos 2 bloques "Establecer el valor calculado de la variable", implementaremos todo por analogía, pero estableciendo el parámetro "Shift" de los bloques "Media móvil" en 1, de manera que los valores de las medias móviles de la vela anterior se escriban en las variables "ma_slow_prev" y "ma_fast_prev".

Hacemos lo mismo para la variable "ma_fast_prev".

Debemos asegurarnos de escribir los valores correctos en nuestras variables. Vamos a añadir el bloque de eventos "Temporizador" al esquema. Este bloque tiene un solo parámetro: "Intervalo (seg)". Por defecto, este parámetro es 1, lo cual significa que el bloque se llama cada segundo por defecto. Luego, añadimos el bloque "Información de depuración" al esquema 4: este bloque simplemente se encarga de enviar el valor especificado al diario del terminal. Con este bloque podemos ver qué valores se escriben en nuestras variables. En cada bloque de "Información de depuración", pondremos 3 bloques en el orden siguiente:

  1. Introducir valor - se trata de un campo de edición simple donde podemos introducir un texto arbitrario. En nuestro caso, solo tenemos que introducir los nombres de las variables para comprender a qué variables se refieren estos u otros valores.
  2. Signo "+" - con la ayuda de este bloque, podemos combinar dos líneas. 
  3. Selección de variable - usando este bloque, podremos elegir la variable cuyo valor necesitamos obtener.

Así que nuestro esquema debería tener el aspecto siguiente:

En BotBrains, todos los valores de usuario se almacenan como un número. En este caso, necesitaremos indicar explícitamente que los bloques de introducción de valores contienen texto, para que sea el propio texto el que se muestre, y no su representación numérica.

Esto se logra utilizando el bloque de conversión al tipo "Línea normal". Solo necesitamos trasladar este bloque a cada bloque de introducción de valor:

En esta etapa, podemos compilar el código del robot e incluso ejecutarlo; según el temporizador, los valores de las variables especificadas se mostrarán en el diario del terminal. Sin embargo, aparecerá la advertencia "conversión implícita de 'number' a 'string'" en el momento de la compilación:

De hecho, en nuestro esquema, estamos tratando de añadir un valor string (un bloque de introducción de valores convertido a una línea) con un valor numérico (valores de variables). Para solucionar esto, solo necesitamos convertir los valores de nuestras variables a líneas. Podemos hacerlo de dos formas:

  1. Usando el mismo bloque de conversión al tipo "Línea normal"
  2. Usando el bloque para escribir "Número fraccionario": este bloque se diferencia del bloque "Línea normal" tan solo en que podemos limitar el número de dígitos decimales

Usaremos el segundo método. Para ello, trasladaremos el bloque de conversión al tipo "Número fraccionario" a cada bloque de selección de variables:

En la configuración de cada bloque "Número fraccionario", indicaremos 2 como el único parámetro - "Dígitos decimales":

El trabajo con los tipos se describe detalladamente en el correspondiente artículo de la documentación.

Ahora, abrimos el terminal y añadimos 2 indicadores "Moving Average" al gráfico del instrumento comerciado con los mismos parámetros que se usan en nuestro robot, para que podamos comparar los valores de las variables con los valores de los indicadores en el gráfico:

Generamos el código del robot clicando en ~ o en el botón correspondiente en la barra de herramientas de la derecha:

Ejecutamos nuestro robot en el terminal y comparamos los valores que se muestran en el diario del terminal con los valores reales de los indicadores en el gráfico:

Todos los valores convergen, por lo que podemos seguir trabajando.

Solo nos queda comparar los valores de las variables al llegar un nuevo tick para el instrumento comerciado, para así determinar la intersección de las medias móviles y realizar una transacción si se cumplen todas las condiciones para ello.

Primero, vamos a definir las condiciones para realizar transacciones. Para entrar en una posición larga, se deben cumplir 3 condiciones:

  1. El valor actual de la media móvil rápida debe ser mayor que el valor actual de la media móvil lenta
  2. El valor de la media móvil rápida de la vela anterior debe ser menor que el valor de la media móvil lenta de la vela anterior
  3. La dirección de la posición actual no debe ser igual a "compra"

Es fácil olvidarse de la última condición, así que nuestro robot puede comenzar a realizar muchas transacciones en un pequeño periodo de tiempo, ya que la condición 1 y la condición 2 se pueden cumplir varias veces por segundo. Gracias a la condición número 3, el robot no realizará ninguna compra aparte de una posición larga existente.

Tenga en cuenta que en el editor de BotBrains, para todos los robots se puede indicar una frecuencia máxima y una frecuencia sospechosa de transacciones. Cuando se alcance la frecuencia máxima de transacciones, el robot cerrará urgentemente todas las posiciones abiertas y eliminará todas las órdenes realizadas; el robot también nos avisará por Telegram y/o nos notificará directamente en el terminal, según los parámetros que hayamos establecido en los ajustes de seguridad del robot. Cuando se alcance una frecuencia sospechosa de transacciones, el robot no cerrará posiciones ni eliminará órdenes, sino que simplemente nos avisará por Telegram y/o nos notificará en el terminal.

Para entrar en corto, se deberán cumplir las siguientes condiciones:

  1. El valor actual de la media móvil rápida debe ser menor que el valor actual de la media móvil lenta 
  2. El valor de la media móvil rápida en la vela anterior debe ser mayor que el valor de la media móvil lenta en la vela anterior
  3. La dirección de la posición actual no debe ser igual a "venta"

Vamos a crear la condición para entrar en una posición larga:

El bloque "Información sobre la posición" tiene 2 parámetros: 

  1. Símbolo - símbolo sobre cuya posición necesitamos obtener información
  2. Valor del bloque - es el parámetro de posición que nos interesa. Opciones disponibles: volumen de la posición, hora de apertura de la posición, precio de apertura de la posición, beneficio de la posición actual y dirección de la posición

Como parámetro "Símbolo", usaremos la constante "symbol": en esta constante almacenaremos el código del instrumento comerciado. Como parámetro "Valor del bloque" usaremos "Dirección de la posición".

De esta forma, el valor del bloque "Información sobre la posición" será igual a la dirección de la posición en el símbolo comerciado.

A este bloque le siguen dos bloques: "NO" e "IGUAL". Después viene el bloque de la constante predefinida "Dirección". Este bloque almacena todas las direcciones posibles: "Dirección de compra", "Dirección de venta" y "Sin dirección". Nosotros comprobamos que la dirección de la posición actual no sea igual a la dirección de compra.

Añadimos el bloque "Orden de mercado" al esquema y lo vinculamos al conector "Sí" del bloque de condición:

El bloque de orden de mercado tiene 3 parámetros:

  1. Símbolo - el símbolo en el que debe colocarse una orden de mercado
  2. Dirección - dirección de la orden (compra/venta)
  3. Volumen - volumen de la orden


Tenga en cuenta que estamos usando constantes como valores para muchos de los parámetros. Esto nos permite configurar fácilmente el robot: podemos simplemente cambiar el valor de una constante en un lugar y el nuevo valor se utilizará automáticamente en todos los lugares donde se use esta constante.

Si hay constantes en un robot comercial creado en el editor de BotBrains, se enumerarán en la parte superior del código generado:

/********** <ROBOT CONSTANTS> **********/

const double __slow_ma_period = user_value("60");
const double __fast_ma_period = user_value("30");
const double __symbol         = user_value("MGCV21");
const double __admin_id       = user_value("744875082");
const double __lot            = user_value("1");

/********** </ROBOT CONSTANTS> **********/

Podemos pensar en las constantes como configuraciones del robot. Por ejemplo, si decidimos comerciar con otro instrumento, simplemente deberemos cambiar el valor de la constante "symbol". O podemos cambiar el valor de la constante directamente en el editor de BotBrains y regenerar el código si no deseamos trabajar directamente con el archivo.

Entonces, en esta etapa, el robot comercial abrirá una posición larga cuando la media móvil rápida cruce la media móvil lenta de abajo hacia arriba. Vamos a añadir alertas:

  1. Mostrar un mensaje en el diario del terminal
  2. Crear una notificación en el terminal
  3. Al archivo de registros del robot, añadimos una entrada sobre la realización de la transacción.
  4. Reproducimos el sonido "Señal de compra"
  5. Enviamos un mensaje a Telegram
  6. Enviamos a Telegram una captura de pantalla del gráfico.

Tenga en cuenta que si reproducimos el sonido "Señal de compra" justo después de realizar la transacción, lo más probable es que nuestro sonido no se reproduzca, ya que MetaTrader reproduce automáticamente su propio sonido cada vez que se efectúa una transacción. Por consiguiente, deberemos reproducir el sonido no de inmediato, sino un cierto intervalo después de la transacción, por ejemplo, 1 segundo. 

Puede parecer que la implementación de los 6 puntos llevará mucho tiempo, pero, en realidad, también hay bloques especiales para todo esto. Nos llevará apenas de 20 a 30 segundos implementar los 6 puntos. Todo lo que hemos hecho antes también se puede implementar en cuestión de minutos, muchas veces resulta más rápido que escribir el código a mano.

Para que los bloques de Telegram funcionen correctamente, deberemos registrar nuestro bot en el bot de Telegram @BotFather, obtener su token de bot e indicarlo en la configuración de nuestro robot en el editor de BotBrains. También necesitaremos conocer nuestro ID de Telegram; podremos encontrarlo en el bot @getmyid_bot. Todo esto se describe con detalle en el correspondiente artículo de la documentación. Asimismo, los bloques de Telegram están disponibles solo para usuarios profesionales.

Por analogía, implementaremos la comprobación para la posición corta. Para hacerlo, simplemente seleccionaremos todos los bloques relacionados con la apertura de una posición larga, los copiaremos (CTRL + C), los pegaremos (CTRL + V) y realizaremos los cambios necesarios.

Generemos el código del robot, lo compilamos y lo ejecutamos en el terminal para comprobar el rendimiento de nuestro robot comercial.

¡Ponga a prueba los robots comerciales solo en una cuenta demo! Por defecto, en los ajustes de seguridad de todos los robots creados en el editor de BotBrains, está prohibido operar en una cuenta real. ¡Cambie al comercio en una cuenta real solo después de probar a fondo su robot comercial en una cuenta demo!

Vamos a establecer periodos aleatorios para las medias móviles y a iniciar el robot comercial en el marco temporal de un minuto. En esta etapa, es importante para nosotros probar el rendimiento de nuestro robot comercial, detectar posibles errores y corregirlos. Después de 80 minutos de trading, el robot comercial ha abierto 4 posiciones. Después de abrir cada posición, el robot ha realizado con éxito una notificación al terminal, ha reproducido los sonidos correspondientes, y ha registrado las entradas correspondientes en el archivo de logs del robot y en el diario del terminal. Además, el robot comercial ha enviado mensajes y capturas de pantalla de los gráficos directamente a mi Telegram sin ningún problema. Y para todo esto, no hemos escrito una sola línea de código. En solo un par de minutos, podemos escribir el esquema de un robot tan simple.


Podría parecer que todo está en orden. Sin embargo, si analizamos detalladamente las transacciones efectuadas por nuestro robot comercial, podemos encontrar que en cada posición, salvo la primera, nuestro robot comercial ha entrado en dos transacciones: la primera transacción para salir de la posición abierta actual y la segunda transacción para abrir la siguiente posición. Esto es fácil de detectar: ​​solo tenemos que mirar el gráfico, verificar el archivo de logs, mirar los mensajes que nos envía el robot comercial a Telegram, o simplemente escuchar cuántas veces el robot comercial ha generado una alerta de sonido después de que se realice una transacción. También podemos analizar la historia de transacciones en el terminal.

En el editor de BotBrains, en la configuración de seguridad del robot, podemos indicar la frecuencia comercial sospechosa y la frecuencia máxima. Por defecto, la frecuencia comercial máxima es de 2 transacciones cada 10 segundos. Cuando se alcance la frecuencia máxima de transacciones, el robot comercial cerrará urgentemente todas las posiciones abiertas, eliminará todas las órdenes colocadas y nos notificará sobre ello por Telegram y/o creará una notificación en el terminal.

El problema no es solo que la apertura de posiciones en dos etapas provoque el doble de transacciones de las necesarias y que entraremos en la mayoría de las posiciones al peor precio, sino que también, en algún momento, nuestro robot alcanzará la frecuencia máxima de transacciones y dejará de comerciar. Esto es exactamente lo que ha sucedido en mi caso. Preste atención a las últimas entradas en el archivo de logs:


Vamos a corregir este problema. Creamos otra variable más: full_lot:

Al iniciar el robot (bloque de eventos "Inicio del robot"), establecemos el valor de la variable full_lot como el valor de constante lot:

Luego, en los bloques de transacciones, en lugar de la constante lot, usaremos la variable full_lot:

A continuación, después de entrar en la posición, estableceremos el valor de la variable full_lot como el doble del valor de la constante lot. Después de realizar la primera transacción, el robot comenzará a comerciar con el doble de volumen. Por consiguiente, cerrará la posición existente y abrirá una nueva con una transacción:

Ahora el robot comercial entrará en todas las posiciones con una sola transacción. Vamos a comprobar esto ejecutando el robot en el terminal. Si observamos la historia de transacciones, veremos que el robot ha abierto la primera transacción con 1 lote, mientras que las transacciones posteriores las ha abierto con un volumen de 2 lotes:



Vamos a crear una interfaz para el robot comercial. Para hacer esto, iremos al modo "Interfaz" del editor y usaremos bloques especiales para construir una interfaz:

Para construir una interfaz de este tipo, bastará con usar los siguientes bloques de interfaz:

  1. Rectángulo
  2. Texto
  3. Botón

Debemos asegurarnos de que, en lugar de guiones, se asignan los valores reales de las medias móviles rápida y lenta. Para lograrlo, usaremos el bloque "Modificar elemento de la interfaz": con este bloque, podremos cambiar las propiedades del bloque con el identificador indicado.

Vamos a transferir los 4 bloques "Modificar elemento de la interfaz" al esquema lógico del robot:

Para copiar el ID de un bloque, haremos lo siguiente:

  1. Presionamos CTRL
  2. Sin soltar CTRL, clicamos dos veces en el bloque que nos interese

Copiamos el ID del primer guión:

Abrimos la configuración del primer bloque "Modificar elemento de la interfaz" e indicamos los valores de los parámetros. En primer lugar, especificamos el ID del bloque cuyas propiedades queremos cambiar. En nuestro caso, se tratará del ID copiado del primer guión. Como tipo de modificación, seleccionaremos "Texto". Como nuevo texto, indicaremos la variable ma_fast_prev:


Por analogía, establecemos los parámetros de los 3 bloques restantes para modificar los elementos de la interfaz. Así, cuando llega un nuevo tick para un instrumento con el que comerciamos, los valores correspondientes de las medias móviles se escriben en las variables ma_fast, ma_slow, ma_fast_prev y ma_slow_prev, después de lo cual, los valores de estas variables se escriben en los elementos de texto correspondientes de la interfaz.

Ahora, vamos a asignar las acciones adecuadas a los botones de la interfaz. Para ello, trasladaremos al esquema lógico del robot tres bloques: 2 bloques "Orden de mercado" y 1 bloque "Posición cerrada":

Vamos a establecer los ajustes de estos parámetros:

Copiamos el ID del primer bloque "Orden de mercado" y especificamos el ID copiado como el valor del parámetro "ID del bloque vinculado" del primer botón:

Por consiguiente, al clicar en el botón "Comprar", se llamará al bloque correspondiente. Por analogía, asignamos las acciones a los botones restantes. Generamos el código del robot y lo ejecutamos en el terminal para comprobar su rendimiento:


 

Tenga en cuenta que la interfaz que hemos construido en el editor se ha transferido por completo al terminal comercial. Los botones de la interfaz funcionan y, en lugar de guiones, podemos ver los valores reales de las medias móviles.

Al final, el código del robot comercial generado tendrá el aspecto siguiente:

//+------------------------------------------------------------------+
//|                                         moving_average_cross.mq5 |
//|                                                    botbrains.app |
//+------------------------------------------------------------------+

#include <botbrains_constants.mqh>
#include <botbrains_lib.mqh>

/********** <ROBOT CONSTANTS> **********/

const double __slow_ma_period = user_value("60");
const double __fast_ma_period = user_value("30");
const double __symbol         = user_value("MGCZ21");
const double __admin_id       = user_value("744875082");
const double __lot            = user_value("1");

/********** </ROBOT CONSTANTS> **********/

/********** <ROBOT VARIABLES> **********/

double __ma_slow      = user_value("");
double __ma_fast      = user_value("");
double __ma_slow_prev = user_value("");
double __ma_fast_prev = user_value("");
double __full_lot     = user_value("");

/********** </ROBOT VARIABLES> **********/

int OnInit(){

  //Is autotrading allowed:
  if(!TerminalInfoInteger(TERMINAL_TRADE_ALLOWED)){
    MessageBox("Autotrading is not allowed, expert wil be removed");
    ExpertRemove();
    return(-1);
  }

  //Is trading on live account allowed:
  if(AccountInfoInteger(ACCOUNT_TRADE_MODE) == ACCOUNT_TRADE_MODE_REAL){
    MessageBox("Expert is not allowed to trade on live account!");
    ExpertRemove();
    return(-1);
  }

  //Set robot name:
  set_robot_name("moving_average_cross");

  //Set license key:
  set_license_key("2L5J7K-K986ND-KMPT94-1Q");

  //Set language:
  set_lang("ru");

  //Generate robot magic number:
  generate_magic();

  //Set initial trading account balance:
  set_init_account_balance();

  //Set suspicious deals frequency params:
  set_suspicous_deals_frequency(60, 3, false, true);

  //Set maximal deals frequency params:
  set_max_deals_frequency(10, 2, false, true);

  //Set the timer with an interval of 1 second:
  EventSetTimer(1);

  //Blocks executed when the robot is launched:
  block_bYi6ikfde();
  block_bYUS6GLT0();

  //Create interface elements:
  create_rectangle("b1ELCu5iq", 0, 0, CORNER_LEFT_UPPER, 15, 15, 390, 195, C'20,20,20', BORDER_FLAT, STYLE_SOLID, C'10,191,254', 2, 0, false, false, false);
  create_button("b4rh5uKlb", 0, 0, CORNER_LEFT_UPPER, 195, 165, 150, 30, "Sell", "Ubuntu Mono", 8, C'255,255,255', C'20,20,20', C'255,51,0', false, 0, false, false, false);
  create_text("b5BGSldua", 0, 0, CORNER_LEFT_UPPER, 120, 135, "-", "Ubuntu Mono", 9, C'255,255,255', 0, ANCHOR_LEFT_UPPER, 0, false, false, false);
  create_text("b9EjNpibO", 0, 0, CORNER_LEFT_UPPER, 30, 30, "Trading robot \"MA Cross\"", "Ubuntu Mono", 14, C'255,255,255', 0, ANCHOR_LEFT_UPPER, 0, false, false, false);
  create_button("bBTrBQlkS", 0, 0, CORNER_LEFT_UPPER, 30, 165, 150, 30, "Buy", "Ubuntu Mono", 8, C'255,255,255', C'20,20,20', C'51,255,0', false, 0, false, false, false);
  create_text("bEncRhDIR", 0, 0, CORNER_LEFT_UPPER, 285, 75, "Current candle:", "Ubuntu Mono", 9, C'255,255,255', 0, ANCHOR_LEFT_UPPER, 0, false, false, false);
  create_text("bI0vadsS2", 0, 0, CORNER_LEFT_UPPER, -195, 270, "Text", "Ubuntu Mono", 9, C'255,255,255', 0, ANCHOR_LEFT_UPPER, 0, false, false, false);
  create_text("bK1cW1i6s", 0, 0, CORNER_LEFT_UPPER, 30, 135, "MA slow:", "Ubuntu Mono", 9, C'255,255,255', 0, ANCHOR_LEFT_UPPER, 0, false, false, false);
  create_text("bLcIIkYqO", 0, 0, CORNER_LEFT_UPPER, 285, 135, "-", "Ubuntu Mono", 9, C'255,255,255', 0, ANCHOR_LEFT_UPPER, 0, false, false, false);
  create_text("bSDWBsxbk", 0, 0, CORNER_LEFT_UPPER, 285, 105, "-", "Ubuntu Mono", 9, C'255,255,255', 0, ANCHOR_LEFT_UPPER, 0, false, false, false);
  create_text("bTK8r1zb1", 0, 0, CORNER_LEFT_UPPER, 30, 105, "MA fast:", "Ubuntu Mono", 9, C'255,255,255', 0, ANCHOR_LEFT_UPPER, 0, false, false, false);
  create_text("bhKcJ2pwx", 0, 0, CORNER_LEFT_UPPER, 120, 75, "Previous candle:", "Ubuntu Mono", 9, C'255,255,255', 0, ANCHOR_LEFT_UPPER, 0, false, false, false);
  create_text("bj6MtjhZF", 0, 0, CORNER_LEFT_UPPER, 120, 105, "-", "Ubuntu Mono", 9, C'255,255,255', 0, ANCHOR_LEFT_UPPER, 0, false, false, false);
  create_button("bympSPhAp", 0, 0, CORNER_LEFT_UPPER, 360, 165, 30, 30, "X", "Ubuntu Mono", 8, C'255,255,255', C'20,20,20', C'255,51,0', false, 0, false, false, false);

  ChartRedraw();

  //Robot initialization was successful:
  return(INIT_SUCCEEDED);

}

void OnDeinit(const int reason){

  Comment("");
  PlaySound(NULL);

  //Remove all graphical objects from the chart on which the robot was launched:
  remove_all_objects(0);

}

void OnTimer(){

  //Timer with 1 sec. interval (bgP4YbxaQ):
  block_bTonyumSN();
  block_bO7LNEs4m();
  block_bS1JODjZj();
  block_bM4s77Wvc();

  //Every 10 sec. reset the counter of the performed deals number (max deals frequency):
  if(get_timer_tick_index() % 10 == 0){

    deals_max_frequency_counter_reset();

  }

  //Every 60 sec. reset the counter of the performed deals number (max deals frequency):
  if(get_timer_tick_index() % 60 == 0){

    deals_suspicious_frequency_counter_reset();

  }

  timer_tick_index_increment();

}

void OnTick(void){

  //Blocks executed when a new tick is received on the symbol on the charts of which the robot was launched:
  block_bHxbWWtwW();
  block_bvIvs7SMe();
  block_boHVNlqnO();

}

void OnTrade(){

  //Check deals frequency:
  check_deals_frequency();

}

void OnChartEvent(
  const int      id,      // event identificator
  const long&    lparam,  // event parameter of type long
  const double&  dparam,  // event parameter of type double
  const string&  sparam   // event parameter of type string
){

  if(id == CHARTEVENT_OBJECT_CLICK){

    string object_name = sparam;

    if(ObjectGetInteger(0, object_name, OBJPROP_TYPE) == OBJ_BUTTON){

      if(object_name == "b4rh5uKlb"){

        block_bYGEhpZDM();

      }

      if(object_name == "bBTrBQlkS"){

        block_bCa4uSC92();

      }

      if(object_name == "bympSPhAp"){

        block_bXRrICVna();

      }

      Sleep(100);
      ObjectSetInteger(0, object_name, OBJPROP_STATE, false);
      ChartRedraw();

    }

  }

}

//Function of the block b0Wkfq6OD (set_complex_variable_value):
void block_b0Wkfq6OD(){

  vset(__ma_fast, ( moving_average(to_string(__symbol), PERIOD_CURRENT, (int)__fast_ma_period, MODE_SMA, PRICE_CLOSE, 0) ));

  block_b6LYVQGej();

}

//Function of the block b1VYatoxs (interface_element_modify):
void block_b1VYatoxs(){

  modify_text("b5BGSldua", DoubleToString(__ma_slow_prev, 2) );

}

//Function of the block b3UJfY74N (interface_element_modify):
void block_b3UJfY74N(){

  modify_text("bSDWBsxbk", DoubleToString(__ma_fast, 2) );

}

//Function of the block b3crj4ayK (log):
void block_b3crj4ayK(){

  log_to_file("Open short!");

  block_bzVyOb4tW();

}

//Function of the block b6LYVQGej (set_complex_variable_value):
void block_b6LYVQGej(){

  vset(__ma_slow_prev, ( moving_average(to_string(__symbol), PERIOD_CURRENT, (int)__slow_ma_period, MODE_SMA, PRICE_CLOSE, 1) ));

  block_bQMre45Bd();

}

//Function of the block bCa4uSC92 (place_market_order):
void block_bCa4uSC92(){

  place_market_order(to_string(__symbol), "BUY", __lot);

}

//Function of the block bHxbWWtwW (condition):
void block_bHxbWWtwW(){

  if (( __ma_fast > __ma_slow ) && ( __ma_fast_prev < __ma_slow_prev ) && ( get_position_info(to_string(__symbol), "POSITION_DIRECTION") != BUY_DIRECTION )){

    block_bUySCvh6M();

  }

}

//Function of the block bM4s77Wvc (print_debug_info):
void block_bM4s77Wvc(){

  print_debug_info(( to_string(to_double("ma_fast_prev = ")) + DoubleToString(__ma_fast_prev, 2) ));

}

//Function of the block bMgaVnT74 (pause):
void block_bMgaVnT74(){

  pause(1000);

  block_bT8xv0qGj();

}

//Function of the block bO7LNEs4m (print_debug_info):
void block_bO7LNEs4m(){

  print_debug_info(( to_string(to_double("ma_fast = ")) + DoubleToString(__ma_fast, 2) ));

}

//Function of the block bPlXoF1uA (set_complex_variable_value):
void block_bPlXoF1uA(){

  vset(__full_lot, ( __lot * to_double("2") ));

}

//Function of the block bQ4zsFoIh (log):
void block_bQ4zsFoIh(){

  log_to_file("Open long!");

  block_bMgaVnT74();

}

//Function of the block bQMre45Bd (set_complex_variable_value):
void block_bQMre45Bd(){

  vset(__ma_fast_prev, ( moving_average(to_string(__symbol), PERIOD_CURRENT, (int)__fast_ma_period, MODE_SMA, PRICE_CLOSE, 1) ));

  block_bRUr8MnXh();
  block_b1VYatoxs();
  block_b3UJfY74N();
  block_bofgi9HOT();

}

//Function of the block bRUr8MnXh (interface_element_modify):
void block_bRUr8MnXh(){

  modify_text("bj6MtjhZF", DoubleToString(__ma_fast_prev, 2) );

}

//Function of the block bS1JODjZj (print_debug_info):
void block_bS1JODjZj(){

  print_debug_info(( to_string(to_double("ma_slow_prev = ")) + DoubleToString(__ma_slow_prev, 2) ));

}

//Function of the block bT8xv0qGj (buy_signal_sound):
void block_bT8xv0qGj(){

  play_sound("buy_signal");

  block_bPlXoF1uA();

}

//Function of the block bTonyumSN (print_debug_info):
void block_bTonyumSN(){

  print_debug_info(( to_string(to_double("ma_slow = ")) + DoubleToString(__ma_slow, 2) ));

}

//Function of the block bTs8fZtAO (telegram_send_chart_screenshot):
void block_bTs8fZtAO(){

  telegram_send_chart_screenshot(to_string(__symbol), 2160, 720, (int)__admin_id);

}

//Function of the block bUySCvh6M (place_market_order):
void block_bUySCvh6M(){

  place_market_order(to_string(__symbol), "BUY", __full_lot);

  block_bfrp6ajWk();
  block_bjBTLJMym();
  block_boX0sSwri();
  block_bQ4zsFoIh();

}

//Function of the block bWkG0nSQa (telegram_send_message):
void block_bWkG0nSQa(){

  telegram_send_message("Open short!", (int)__admin_id);

}

//Function of the block bX2tY0y68 (terminal_print):
void block_bX2tY0y68(){

  terminal_print("Open short!");

}

//Function of the block bXRrICVna (close_position):
void block_bXRrICVna(){

  close_position(to_string(__symbol));

}

//Function of the block bYGEhpZDM (place_market_order):
void block_bYGEhpZDM(){

  place_market_order(to_string(__symbol), "SELL", __lot);

}

//Function of the block bYUS6GLT0 (set_complex_variable_value):
void block_bYUS6GLT0(){

  vset(__full_lot, ( __lot ));

}

//Function of the block bYi6ikfde (terminal_print):
void block_bYi6ikfde(){

  terminal_print("Robot started!");

}

//Function of the block bfrp6ajWk (terminal_print):
void block_bfrp6ajWk(){

  terminal_print("Open long!");

}

//Function of the block biLE3RJAD (sell_signal_sound):
void block_biLE3RJAD(){

  play_sound("sell_signal");

  block_bPlXoF1uA();

}

//Function of the block bjBTLJMym (telegram_send_message):
void block_bjBTLJMym(){

  telegram_send_message("Open long!", (int)__admin_id);

}

//Function of the block boHVNlqnO (set_complex_variable_value):
void block_boHVNlqnO(){

  vset(__ma_slow, ( moving_average(to_string(__symbol), PERIOD_CURRENT, (int)__slow_ma_period, MODE_SMA, PRICE_CLOSE, 0) ));

  block_b0Wkfq6OD();

}

//Function of the block boX0sSwri (telegram_send_chart_screenshot):
void block_boX0sSwri(){

  telegram_send_chart_screenshot(to_string(__symbol), 2160, 720, (int)__admin_id);

}

//Function of the block bofgi9HOT (interface_element_modify):
void block_bofgi9HOT(){

  modify_text("bLcIIkYqO", DoubleToString(__ma_slow, 2) );

}

//Function of the block bugmLdNsU (place_market_order):
void block_bugmLdNsU(){

  place_market_order(to_string(__symbol), "SELL", __full_lot);

  block_bX2tY0y68();
  block_bWkG0nSQa();
  block_bTs8fZtAO();
  block_b3crj4ayK();

}

//Function of the block bvIvs7SMe (condition):
void block_bvIvs7SMe(){

  if (( __ma_fast < __ma_slow ) && ( __ma_fast_prev > __ma_slow_prev ) && ( get_position_info(to_string(__symbol), "POSITION_DIRECTION") != SELL_DIRECTION )){

    block_bugmLdNsU();

  }

}

//Function of the block bzVyOb4tW (pause):
void block_bzVyOb4tW(){

  pause(1000);

  block_biLE3RJAD();

}

En el editor de BotBrains, un robot comercial de este tipo se puede construir en minutos, y la generación del código ocupa una fracción de segundo.

Bloques disponibles

Hay más de 140 bloques disponibles en el editor de BotBrains. A continuación, mostramos un recuadro completo con los bloques disponibles. Tenga en cuenta que, para comprender completamente los fundamentos del trabajo con el editor, es recomendable leer la documentación.

Bloques de eventos:

Bloque Descripción
Inicio del funcionamiento del robot
El bloque se activa 1 vez al iniciarse el robot.
Finalización del robot
El bloque se activa 1 vez al finalizarse el robot.
Cambio en la profundidad de mercado
El bloque se activa cada vez que cambia la profundidad de mercado para el símbolo indicado.
Nuevo tick
El bloque se activa cuando llega un nuevo tick del símbolo en cuyo gráfico se ha iniciado el robot.
Cambio del volumen abierto
El bloque se activa cada vez que cambia el volumen abierto para el símbolo especificado.
Cambio del número de órdenes límite
El bloque se activa cada vez que cambia el número de órdenes límite activas para el símbolo especificado.
Cambio del número de órdenes stop
El bloque se activa cada vez que cambia el número de órdenes stop activas para el símbolo especificado.
Temporizador
El bloque se activa 1 vez cada número especificado de segundos.
Pulsación de tecla
El bloque se llama cuando se presiona la tecla con el código especificado

Condición:

Bloque Descripción
Bloque "Si"
Creación de una bifurcación lógica en el circuito del robot. El bloque tiene 1 entrada y 2 salidas.
Ciclo:

El bloque de ciclo se usa principalmente para iterar por algunos valores. Por ejemplo, un bloque de ciclo se puede utilizar para recorrer la lista de órdenes límite activas.

Bloque
Descripción
Ciclo "Hasta que"
El bloque se activará siempre que la condición especificada sea verdadera.
Indicadores de tendencia:
Bloque
Adaptive Moving Average
Average Directional Movement Index
Average Directional Movement Index by Welles Wilder
Bollinger Bands
Double Exponential Moving Average
Envelopes
Fractal Adaptive Moving Average
Ichimoku
Moving Average
Parabolic SAR
Standard Deviation
Triple Exponential Moving Average
Variable Index Dynamic Average

Osciladores:

Bloque
Average True Range
Bears Power
Bulls Power
Chaikin Oscillator
Commodity Channel Index
DeMarker
Force Index
MACD
Momentum
Moving Average of Oscillator
RSI (Relative Strength Index)
Relative Vigor Index
Stochastic Oscillator
TRIX (Triple Exponential Moving Averages Oscillator)
Larry Williams' Percent Range
Accumulation / Distribution
Money Flow Index
On Balance Volume
Volumes

Indicadores de Bill Williams:

Bloque
Accelerator Oscillator
Alligator
Awesome Oscillator
Fractals
Gator
Market Facilitation Index

Bloques de análisis del gráfico:

Bloque Descripción
Datos de la vela
Obtenga información sobre una vela específica del gráfico.
Información sobre el gráfico
Obtener información sobre el gráfico. Por ejemplo, el número de velas del gráfico, la hora de apertura de la primera o la última vela disponible.
Precio máximo
Obtener el precio máximo en el intervalo de tiempo indicado.
Precio mínimo
Obtener el precio mínimo en el intervalo de tiempo indicado.
Precio promedio
Obtener el precio promedio para el intervalo de tiempo indicado.
Dibujar una línea horizontal
Dibujar una línea horizontal en el gráfico.
Dibujar una línea vertical
Dibujar una línea vertical en el gráfico.
Eliminar todas las líneas
Elimina todas las líneas horizontales y verticales del gráfico.

Bloques de análisis de la profundidad de mercado:

Bloque Descripción
Información sobre la cotización
Obtener información sobre cotizaciones individuales de la profundidad de mercado.
Spread
Obtener el spread del símbolo indicado en ticks.

Transacciones:

Bloque Descripción
Orden de mercado
Colocar una orden de mercado.
Orden límite
Colocar una orden límite.
Quitar una orden límite
Quitar una orden límite.
Quitar todas las órdenes límite
Quitar todas las órdenes límite para el símbolo especificado.
Orden stop
Colocar una oreden stop.
Quitar una orden stop
Quitar una orden stop.
Quitar todas las órdenes stop
Quitar todas las órdenes stop para el símbolo especificado.
Cerrar posición
Cerrar la posición del símbolo especificado.
Cerrar todas las posiciones abiertas
Cerrar todas las posiciones abiertas por el robot actual.

Variables:

Bloque Descripción
Establecer un valor de variable simple
El nuevo valor de la variable se establece usando un campo de edición. Es decir, con este bloque, podemos escribir algo específico en una variable: solo un número o algún texto.
Establecer el valor calculado de una variable
El nuevo valor de la variable viene determinado por el valor calculado. Por ejemplo, con este bloque, podemos escribir el tamaño del depósito actual o el precio actual del símbolo comerciado en una variable.
Seleccionar una variable
Seleccionar una variable. Por ejemplo, podemos usar un bloque de "seleccionar una variable" dentro de un bloque de condición para comprobar el valor de una variable.

Sonidos:

Bloque Descripción
Sonido suave
Reproducir sonido "Sonido suave"
Sirena
Reproduce sonido "Sirena"
Señal de compra
Reproducir sonido "Señal de compra"
Señal de venta
Reproducir sonido "Señal de venta"

Información:

Bloque
Información de la cuenta
Información sobre la posición
Información sobre una orden límite
Información sobre todas las órdenes límite
Información sobre una orden stop
Información sobre todas las órdenes stop
Información sobre una orden límite histórica
Información sobre una orden stop histórica
Información sobre una transacción histórica
Información sobre la sesión comercial
Símbolo sobre un símbolo
Información sobre la hora

Enumeraciones:

Los bloques de enumeración se necesitan para iterar sobre algo. Por ejemplo, usando bloques de enumeración, podemos iterar por la lista de símbolos o la lista de órdenes límite/stop activas.

Bloque Descripción
Nombre del símbolo
Obtener el código del símbolo.
Solicitar la lista de órdenes activas
Solicitar la lista de órdenes activas.
Ticket de una orden límite activa
Obtener el ticket de una orden límite activa.
Ticket de una orden stop activa
El bloque retorna el ticket de una orden stop activa.
Historia:
Bloque Descripción
Consultar datos históricos
Solicitar los datos históricos para un intervalo de tiempo específico.
Ticket de una transacción de la historia
Obtener el ticket de una transacción de la historia.
Ticket de una orden límite de la historia
Obtener el ticket de una orden límite de la historia.
Ticket de una orden stop de la historia
Obtener el ticket de una orden stop de la historia.
Telegram:
Bloque Descripción
Enviar un mensaje
Enviar a Telegram el mensaje indicado al usuario con el identificador especificado.
Enviar una captura de pantalla del gráfico
Enviar una captura de pantalla del gráfico del símbolo indicado al usuario de Telegram con el identificador especificado.
Salto de línea
Se usa para crear un salto de línea en un mensaje de Telegram.

Otro:

Bloque Descripción
Mensaje en el diario
Mostrar un mensaje en el diario del terminal.
Notificación en el terminal
Hacer una notificación en el terminal.
Comentario en el gráfico
Mostrar el comentario indicado en el gráfico del símbolo especificado.
Log en un archivo
Hacer un log en el archivo de logs del robot.
Pausa
Pausar el robot durante el número especificado de milisegundos.
Apagar el robot
Apagar el robot.
Cerrar el terminal
Cerrar el terminal.

Elementos de la interfaz:

Bloque Descripción
Rectángulo
Elemento de la interfaz "rectángulo".
Botón
Elemento de la interfaz "botón".
Texto
Elemento de la interfaz "texto".
Campo de edición
Elemento de la interfaz "campo de edición".

Modificación de los elementos de la interfaz:

Bloque Descripción
Modificar elemento de la interfaz
Cambiar una propiedad de un elemento de la interfaz.

Información sobre los elementos de la interfaz:

Bloque Descripción
Información sobre un elemento de la interfaz
El bloque retorna el valor de la propiedad de bloque indicada con el identificador especificado.

Constantes predefinidas:

Las constantes predefinidas son los posibles valores de ciertos parámetros. Por ejemplo, el bloque "dirección" contiene las constantes predefinidas de las direcciones posibles: compra, venta, sin dirección.

Bloque Descripción
Dirección
Direcciones posibles (compra, venta, sin dirección).
Método de cambio de posición
Posibles métodos de cambio de la posición (entrada al mercado, salida del mercado, reversión, cierre de una posición por otra opuesta).
Tipo de transacción
Posibles tipos de transacción (compra, venta, recarga de balance, entrada de corrección, etcétera)

Depuración:

Bloque Descripción
Información sobre la depuración
Muestra el mensaje indicado en el diario del terminal.

Operadores matemáticos:
Bloque Descripción
+
Suma
-
Resta
/
División
*
Multiplicación

Raíz cuadrada
^
Potenciación
%
Resto de la división
(
Paréntesis de apertura
)
Paréntesis de cierre
>
Mayor que
<
Menor que
>=
Mayor que o igual a
<=
Menor que o igual a

Operadores lógicos:

Bloque Descripción
Y
"Y" lógico
O "O" lógico
NO "No" lógico

Teletransportes:

Los teletransportes se usan cuando necesitamos movernos a otra sección del esquema. Los teletransportes a la entrada y salida están interconectados por un número.
Bloque
Entrar en el teletransporte
Salir del teletransporte

Selección de una variable o constante:

Bloque
Seleccionar una variable
Seleccionar una constante

Introducir un valor:

Bloque Descripción
Introducir un valor
Este bloque se puede usar para establecer ciertos valores directamente en el esquema.

Conversión a un tipo:

De forma predeterminada, todos los datos se representan como un número. Usando bloques de conversión, podemos establecer explícitamente el formato en el que se representará un valor particular.

Bloque Descripción
Línea regular
Convertir el valor a una línea regular.
Línea en formato de fecha y hora
Convertir un valor al formato de fecha y hora.
Número entero
Convertir un valor a un número entero.
Numero fraccional
Convertir un valor a un número fraccional.


Conclusión

He dedicado más de un mes de trabajo al desarrollo de este proyecto. Si usted tiene alguna idea respecto al material del autor o comentarios sobre su trabajo, podrá escribir un correo electrónico a support@botbrains.app. Su opinión se tetendrá en cuenta.


Traducción del ruso hecha por MetaQuotes Ltd.
Artículo original: https://www.mql5.com/ru/articles/9998

Websockets para MetaTrader 5 — Usando la API de Windows Websockets para MetaTrader 5 — Usando la API de Windows
En este artículo, usaremos WinHttp.dll para crear un cliente de websocket para los programas de MetaTrader 5. El cliente se implementará finalmente como una clase, y también se probará contra la API de websocket de Binary.com.
Modelo de regresión universal para la predicción de precio de mercado (Parte 2): Funciones de procesos transitorios naturales, tecnológicos y sociales Modelo de regresión universal para la predicción de precio de mercado (Parte 2): Funciones de procesos transitorios naturales, tecnológicos y sociales
Este artículo supone una continuación lógica del anterior, y se ha escrito para resaltar los hechos revelados que confirman sus conclusiones durante los siguientes diez años tras su publicación, en lo referente a las tres funciones identificadas de los procesos transitorios dinámicos que describen los patrones de cambio en los precios del mercado.
Gráficos en la biblioteca DoEasy (Parte 90): Eventos de objetos gráficos estándar. Funcionalidad básica Gráficos en la biblioteca DoEasy (Parte 90): Eventos de objetos gráficos estándar. Funcionalidad básica
En este artículo, crearemos la funcionalidad básica para el seguimiento de eventos de objetos gráficos estándar. Empezaremos con el evento de doble clic sobre un objeto gráfico.
Gráficos en la biblioteca DoEasy (Parte 89): Creación programática de objetos gráficos estándar Funcionalidad básica Gráficos en la biblioteca DoEasy (Parte 89): Creación programática de objetos gráficos estándar Funcionalidad básica
Nuestra biblioteca ahora puede monitorear la aparición de objetos gráficos estándar en el gráfico del terminal de cliente, así como la eliminación y modificación de algunos de sus parámetros. Pero para que el "conjunto" quede completo, obviamente necesitamos la capacidad de crear objetos gráficos estándar a partir de nuestros programas.