2026-03-25 09:57:33 -05:00
|
|
|
//+------------------------------------------------------------------+
|
2026-03-20 10:20:00 -05:00
|
|
|
//| ConfigTab.mqh |
|
|
|
|
|
//| Copyright 2025, Niquel Mendoza. |
|
|
|
|
|
//| https://www.mql5.com/es/users/nique_372 |
|
|
|
|
|
//+------------------------------------------------------------------+
|
|
|
|
|
#property copyright "Copyright 2025, Niquel Mendoza."
|
|
|
|
|
#property link "https://www.mql5.com/es/users/nique_372"
|
|
|
|
|
#property strict
|
|
|
|
|
|
|
|
|
|
#ifndef AIDATATASKRUNER_UI_TRAINING_CONFIGTAB_MQH
|
|
|
|
|
#define AIDATATASKRUNER_UI_TRAINING_CONFIGTAB_MQH
|
|
|
|
|
|
|
|
|
|
//+------------------------------------------------------------------+
|
|
|
|
|
//| |
|
|
|
|
|
//+------------------------------------------------------------------+
|
|
|
|
|
#include "..\\Defines.mqh"
|
2026-03-20 17:16:21 -05:00
|
|
|
//--- Json para parsear (con el exe comunicador)
|
|
|
|
|
#include <TSN\\Json\\Json.mqh>
|
2026-03-24 10:39:38 -05:00
|
|
|
//--- Expert para lanzar eas
|
|
|
|
|
#include <TSN\\ExtraCodes\\Expert.mqh>
|
|
|
|
|
//--- Def para el procoolo de comunciaon
|
|
|
|
|
#include "..\\..\\Backend\\Training\\Def.mqh"
|
2026-03-25 18:05:47 -05:00
|
|
|
//--- Dll custom para filse eslec dialog con mas alcanzse
|
|
|
|
|
#include "..\\..\\DllFilseSelctDialog\\DllFilseSelctDialog\\Main.mqh"
|
2026-03-24 10:39:38 -05:00
|
|
|
|
2026-03-20 10:20:00 -05:00
|
|
|
/*
|
|
|
|
|
[CTrainingTabConfig]
|
2026-03-21 08:06:31 -05:00
|
|
|
//--- Parte general
|
2026-03-20 10:20:00 -05:00
|
|
|
m_label_titulo="Config"
|
|
|
|
|
m_label_name_file="Config file:"
|
|
|
|
|
m_label_name_file_val_tooltip="Selected config file"
|
2026-03-21 11:41:29 -05:00
|
|
|
m_btn_name_file_browse="Browse"
|
|
|
|
|
m_btn_name_file_browse_tooltip="Select config JSON file"
|
2026-03-20 10:20:00 -05:00
|
|
|
m_btn_open="Open"
|
|
|
|
|
m_btn_open_tooltip="Open file in default editor"
|
2026-03-20 17:16:21 -05:00
|
|
|
|
2026-03-21 08:06:31 -05:00
|
|
|
//--- Parte de python
|
2026-03-20 17:16:21 -05:00
|
|
|
m_label_tit_run_py="Run python"
|
2026-03-21 11:41:29 -05:00
|
|
|
m_label_py_file="Python file:"
|
|
|
|
|
m_label_py_file_val_tooltip="Path to the Python script or executable"
|
|
|
|
|
m_btn_py_file_browse="Browse"
|
|
|
|
|
m_btn_py_file_browse_tooltip="Select a .py script or .exe executable"
|
2026-03-20 17:16:21 -05:00
|
|
|
|
2026-03-24 10:39:38 -05:00
|
|
|
// Edit timeout
|
|
|
|
|
m_edit_py_max_tiemout="Tiemout for execute py:"
|
|
|
|
|
m_edit_py_max_tiemout_tooltup="Enter the value in seconds for the maximum time the py can run"
|
|
|
|
|
|
2026-03-20 17:16:21 -05:00
|
|
|
// Boton
|
|
|
|
|
m_btn_run_py="Run"
|
|
|
|
|
m_btn_run_py_tooltip="Click here to run python exe"
|
|
|
|
|
m_btn_run_py_running="Running..."
|
|
|
|
|
|
2026-03-21 08:06:31 -05:00
|
|
|
//--- Mensajes espeficiso por funcion
|
|
|
|
|
OnClickBottom_error_select_file="No file selected"
|
2026-03-20 17:16:21 -05:00
|
|
|
OnClickBottom_no_config_selected="No config file selected"
|
|
|
|
|
OnClickBottom_python_is_runing="Python is already running"
|
2026-03-21 11:41:29 -05:00
|
|
|
OnClickBottom_python_no_py_selected="No python\exe files selected"
|
2026-03-24 10:39:38 -05:00
|
|
|
|
|
|
|
|
// Error de laucher
|
|
|
|
|
OnClickBottom_python_launch_error_file="Failed to write in args.txt for launcher for python, last error = %d"
|
|
|
|
|
OnClickBottom_python_launch_error_exe="Failed to execute launcher, Check the terminal logs"
|
2026-03-24 10:47:07 -05:00
|
|
|
OnClickBottom_python_launch_python_launch_error_chart="Failed to open chart, last error = %d"
|
2026-03-20 10:20:00 -05:00
|
|
|
*/
|
|
|
|
|
|
2026-03-20 17:16:21 -05:00
|
|
|
//---
|
|
|
|
|
#define AIDATATASKRUNNER_TRAINING_NUM_C (80)
|
2026-03-24 10:39:38 -05:00
|
|
|
#define AIDATATASKRUNNER_FILENAME_ARGS_LAUNCHER ("LauncherPy\\args.txt")
|
2026-03-28 10:58:12 -05:00
|
|
|
#define AIDATATASKRUNNER_FILENAME_BAT_PY ("LauncherPy\\py.bat")
|
2026-03-20 17:16:21 -05:00
|
|
|
|
2026-03-20 10:20:00 -05:00
|
|
|
//+------------------------------------------------------------------+
|
|
|
|
|
//| |
|
|
|
|
|
//+------------------------------------------------------------------+
|
2026-03-20 17:16:21 -05:00
|
|
|
class IRunPy : public CLoggerBase
|
|
|
|
|
{
|
|
|
|
|
public:
|
|
|
|
|
IRunPy(void) {}
|
|
|
|
|
~IRunPy(void) {}
|
|
|
|
|
|
|
|
|
|
//---
|
|
|
|
|
virtual void OnTrainingInit() {}
|
|
|
|
|
virtual void OnTrainingEnd() {}
|
|
|
|
|
virtual void OnTrainingNewResult(CJson* json) {}
|
2026-03-21 08:06:31 -05:00
|
|
|
|
|
|
|
|
//---
|
|
|
|
|
virtual __forceinline uint8_t EventsFlags() const = 0;
|
2026-03-20 17:16:21 -05:00
|
|
|
};
|
|
|
|
|
|
|
|
|
|
//---
|
|
|
|
|
#define TRAINING_RUNNER_PY_FLAG_ON_TRAINIG (1)
|
|
|
|
|
#define TRAINING_RUNNER_PY_FLAG_ON_INIT (2)
|
|
|
|
|
#define TRAINING_RUNNER_PY_FLAG_ON_DEINIT (4)
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
//+------------------------------------------------------------------+
|
|
|
|
|
//| |
|
|
|
|
|
//+------------------------------------------------------------------+
|
|
|
|
|
class CTrainingTabConfig : public CGuiBaseComponent<CLoggerBase>
|
2026-03-20 10:20:00 -05:00
|
|
|
{
|
|
|
|
|
private:
|
|
|
|
|
CTextLabel m_label_titulo;
|
|
|
|
|
CTextLabel m_label_name_file;
|
|
|
|
|
CTextLabel m_label_name_file_val;
|
2026-03-21 11:41:29 -05:00
|
|
|
CButton m_btn_name_file_browse;
|
2026-03-20 10:20:00 -05:00
|
|
|
CButton m_btn_open;
|
2026-03-25 09:57:33 -05:00
|
|
|
CButton m_btn_file_config_template;
|
2026-03-21 11:41:29 -05:00
|
|
|
|
|
|
|
|
//---
|
2026-03-20 17:16:21 -05:00
|
|
|
CTextLabel m_label_tit_run_py;
|
2026-03-26 11:23:24 -05:00
|
|
|
|
|
|
|
|
// Py file
|
2026-03-21 11:41:29 -05:00
|
|
|
CTextLabel m_label_py_file;
|
|
|
|
|
CTextLabel m_label_py_file_val;
|
|
|
|
|
CButton m_btn_py_file_browse;
|
2026-03-26 11:23:24 -05:00
|
|
|
|
|
|
|
|
// Log file
|
|
|
|
|
CTextLabel m_label_log_pyfile;
|
|
|
|
|
CTextLabel m_label_log_pyfile_val;
|
|
|
|
|
CButton m_btn_logpyfile_browse;
|
|
|
|
|
|
|
|
|
|
// Max timeout
|
2026-03-24 10:39:38 -05:00
|
|
|
CTextEdit m_edit_py_max_tiemout;
|
2026-03-26 11:23:24 -05:00
|
|
|
|
|
|
|
|
// Btn run final
|
2026-03-20 17:16:21 -05:00
|
|
|
CButton m_btn_run_py;
|
2026-03-26 11:23:24 -05:00
|
|
|
|
|
|
|
|
//---
|
2026-03-21 11:41:29 -05:00
|
|
|
string m_py_file_extension;
|
2026-03-20 17:16:21 -05:00
|
|
|
|
2026-03-20 10:20:00 -05:00
|
|
|
//---
|
2026-03-20 17:16:21 -05:00
|
|
|
bool m_py_is_run;
|
2026-03-20 10:20:00 -05:00
|
|
|
bool m_common_flag;
|
2026-03-20 17:16:21 -05:00
|
|
|
int m_extra_file_flags;
|
|
|
|
|
string m_base_terminal_files_path;
|
|
|
|
|
|
|
|
|
|
//---
|
|
|
|
|
string m_path_to_config_json;
|
|
|
|
|
string m_path_to_lock_bin;
|
2026-03-24 10:39:38 -05:00
|
|
|
string m_path_to_ea_launcher;
|
2026-03-26 11:23:24 -05:00
|
|
|
string m_path_to_log_py;
|
2026-03-28 08:35:32 -05:00
|
|
|
string m_path_py_interpete;
|
2026-03-28 10:58:12 -05:00
|
|
|
string m_python_path_env;
|
2026-03-24 10:39:38 -05:00
|
|
|
uint m_timeout_for_execute_py;
|
2026-03-20 17:16:21 -05:00
|
|
|
|
|
|
|
|
//---
|
|
|
|
|
IRunPy* m_runer_py_on_pass[];
|
|
|
|
|
int m_runer_py_on_pass_size;
|
|
|
|
|
|
|
|
|
|
IRunPy* m_runer_py_on_init[];
|
|
|
|
|
int m_runer_py_on_init_size;
|
|
|
|
|
|
|
|
|
|
IRunPy* m_runer_py_on_deinit[];
|
|
|
|
|
int m_runer_py_on_deinit_size;
|
|
|
|
|
|
|
|
|
|
//---
|
|
|
|
|
void OnTrainingFinish();
|
|
|
|
|
void OnTrainingStart();
|
|
|
|
|
|
2026-03-20 10:20:00 -05:00
|
|
|
|
|
|
|
|
public:
|
2026-03-20 17:16:21 -05:00
|
|
|
CTrainingTabConfig(void);
|
|
|
|
|
~CTrainingTabConfig(void);
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
//---
|
2026-03-21 08:06:31 -05:00
|
|
|
void AddRunnerPy(IRunPy* runer);
|
2026-03-20 10:20:00 -05:00
|
|
|
|
|
|
|
|
//---
|
2026-03-28 10:58:12 -05:00
|
|
|
void SetExtra(bool common_flag, const string& path_config_json, const string& path_lock, const string& path_ea_launcer, const string& path_py_inter, const string& py_path_env);
|
2026-03-20 10:20:00 -05:00
|
|
|
bool Create(CWndCreate* p, CWindow& main_window, int top_gap, int left_gap, int right_gap, int bottom_gap);
|
|
|
|
|
|
|
|
|
|
//---
|
|
|
|
|
bool OnClickBottom(const long lparam);
|
2026-03-24 10:39:38 -05:00
|
|
|
bool OnTextEdit(const long lparam);
|
2026-03-26 06:46:59 -05:00
|
|
|
bool OnClickDec(const long lparam);
|
|
|
|
|
bool OnClickInc(const long lparam);
|
2026-03-20 10:20:00 -05:00
|
|
|
|
|
|
|
|
//---
|
|
|
|
|
void OnLenguajeChange() override final;
|
|
|
|
|
|
|
|
|
|
//---
|
|
|
|
|
__forceinline string ConfigFilePath() const { return m_label_name_file_val.LabelText(); }
|
2026-03-20 17:16:21 -05:00
|
|
|
|
|
|
|
|
//---
|
|
|
|
|
// Se tendra que llamar a aesta funcion ojito
|
|
|
|
|
void OnFinishPy();
|
|
|
|
|
|
|
|
|
|
//---
|
|
|
|
|
void OnTimerEvent();
|
2026-03-20 10:20:00 -05:00
|
|
|
};
|
|
|
|
|
|
|
|
|
|
//+------------------------------------------------------------------+
|
|
|
|
|
//| |
|
|
|
|
|
//+------------------------------------------------------------------+
|
2026-03-20 17:16:21 -05:00
|
|
|
CTrainingTabConfig::CTrainingTabConfig()
|
|
|
|
|
: CGuiBaseComponent<CLoggerBase>("CTrainingTabConfig"), m_py_is_run(false)
|
|
|
|
|
{
|
|
|
|
|
m_runer_py_on_deinit_size = ArrayResize(m_runer_py_on_deinit, 0);
|
|
|
|
|
m_runer_py_on_init_size = ArrayResize(m_runer_py_on_init, 0);
|
|
|
|
|
m_runer_py_on_pass_size = ArrayResize(m_runer_py_on_pass, 0);
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
//+------------------------------------------------------------------+
|
|
|
|
|
CTrainingTabConfig::~CTrainingTabConfig()
|
2026-03-20 10:20:00 -05:00
|
|
|
{
|
2026-03-20 17:16:21 -05:00
|
|
|
}
|
|
|
|
|
|
|
|
|
|
//+------------------------------------------------------------------+
|
|
|
|
|
//| |
|
|
|
|
|
//+------------------------------------------------------------------+
|
2026-03-28 10:58:12 -05:00
|
|
|
void CTrainingTabConfig::SetExtra(bool common_flag, const string& path_config_json, const string& path_lock, const string& path_ea_launcer, const string& path_py_inter, const string& py_path_env)
|
2026-03-20 17:16:21 -05:00
|
|
|
{
|
|
|
|
|
//---
|
2026-03-20 10:20:00 -05:00
|
|
|
m_common_flag = common_flag;
|
2026-03-20 17:16:21 -05:00
|
|
|
m_extra_file_flags = (m_common_flag ? FILE_COMMON : 0);
|
2026-03-28 08:35:32 -05:00
|
|
|
m_path_py_interpete = path_py_inter;
|
2026-03-20 17:16:21 -05:00
|
|
|
|
|
|
|
|
//--- Estos arhcivos van tal cual no hay una carpeta base asi que se debe esopciifcar ruta completa (son relativos a Files\\) tal cual no de bsae_path
|
|
|
|
|
m_path_to_config_json = path_config_json;
|
|
|
|
|
m_path_to_lock_bin = path_lock;
|
2026-03-24 10:39:38 -05:00
|
|
|
m_path_to_ea_launcher = path_ea_launcer;
|
2026-03-28 10:58:12 -05:00
|
|
|
m_python_path_env = py_path_env;
|
2026-03-20 17:16:21 -05:00
|
|
|
|
|
|
|
|
//---
|
|
|
|
|
m_base_terminal_files_path = (m_common_flag ? TERMINAL_MT5_COMMON_PATH + "\\Files\\" : TERMINAL_MT5_DATA_PAH + "\\MQL5\\Files\\");
|
2026-03-20 10:20:00 -05:00
|
|
|
}
|
|
|
|
|
|
|
|
|
|
//+------------------------------------------------------------------+
|
|
|
|
|
//| |
|
|
|
|
|
//+------------------------------------------------------------------+
|
|
|
|
|
bool CTrainingTabConfig::Create(CWndCreate *p, CWindow &main_window, int top_gap, int left_gap, int right_gap, int bottom_gap)
|
|
|
|
|
{
|
2026-03-21 11:41:29 -05:00
|
|
|
//---
|
|
|
|
|
const int initial_x = left_gap + 5;
|
2026-03-20 10:20:00 -05:00
|
|
|
int x = left_gap + 5;
|
|
|
|
|
int y = top_gap + 10;
|
|
|
|
|
|
|
|
|
|
//--- Titulo
|
|
|
|
|
m_label_titulo.FontSize(14);
|
|
|
|
|
m_label_titulo.Font("Arial");
|
|
|
|
|
m_label_titulo.LabelColor(AIDATATASKRUNER_COLOR_TEXT_PRIMARY);
|
2026-03-21 11:41:29 -05:00
|
|
|
m_label_titulo.BackColor(AIDATATASKRUNER_COLOR_FONDO_SUBTAB_PRESSED);
|
2026-03-20 10:20:00 -05:00
|
|
|
if(!p.CreateTextLabel(m_label_titulo, m_language[GUIBASE_COMPONENT_NAME(m_label_titulo)],
|
|
|
|
|
main_window, 0, m_base_tab, m_base_tab_idx, x, y, 200))
|
2026-03-20 17:16:21 -05:00
|
|
|
{
|
|
|
|
|
GUIBASE_ERROR_CREATION(m_label_titulo);
|
|
|
|
|
return false;
|
|
|
|
|
}
|
2026-03-21 11:41:29 -05:00
|
|
|
y += m_label_titulo.YSize() + 14;
|
2026-03-20 10:20:00 -05:00
|
|
|
|
|
|
|
|
//--- Label Config file:
|
|
|
|
|
m_label_name_file.FontSize(10);
|
|
|
|
|
m_label_name_file.Font("Arial");
|
|
|
|
|
m_label_name_file.LabelColor(AIDATATASKRUNER_COLOR_TEXT_SECONDARY);
|
2026-03-21 11:41:29 -05:00
|
|
|
m_label_name_file.BackColor(AIDATATASKRUNER_COLOR_FONDO_SUBTAB_PRESSED);
|
2026-03-20 10:20:00 -05:00
|
|
|
if(!p.CreateTextLabel(m_label_name_file, m_language[GUIBASE_COMPONENT_NAME(m_label_name_file)],
|
|
|
|
|
main_window, 0, m_base_tab, m_base_tab_idx, x, y, 100, 25))
|
2026-03-20 17:16:21 -05:00
|
|
|
{
|
|
|
|
|
GUIBASE_ERROR_CREATION(m_label_name_file);
|
|
|
|
|
return false;
|
|
|
|
|
}
|
2026-03-20 10:20:00 -05:00
|
|
|
x += m_label_name_file.XSize() + 5;
|
|
|
|
|
|
|
|
|
|
//--- Label valor (ruta)
|
|
|
|
|
m_label_name_file_val.FontSize(10);
|
|
|
|
|
m_label_name_file_val.Font("Arial");
|
|
|
|
|
m_label_name_file_val.LabelColor(AIDATATASKRUNER_COLOR_TEXT_PRIMARY);
|
|
|
|
|
m_label_name_file_val.BackColor(AIDATATASKRUNER_COLOR_EDIT_BACK);
|
|
|
|
|
m_label_name_file_val.LabelXGap(5);
|
2026-03-26 06:46:59 -05:00
|
|
|
m_label_name_file_val.LabelYGap(3);
|
2026-03-20 10:20:00 -05:00
|
|
|
m_label_name_file_val.Tooltip(m_language.Tooltip(GUIBASE_COMPONENT_NAME(m_label_name_file_val)));
|
|
|
|
|
|
2026-03-20 17:16:21 -05:00
|
|
|
if(!p.CreateTextLabel(m_label_name_file_val, "",
|
2026-03-20 10:20:00 -05:00
|
|
|
main_window, 0, m_base_tab, m_base_tab_idx, x, y, 350, 25))
|
2026-03-20 17:16:21 -05:00
|
|
|
{
|
|
|
|
|
GUIBASE_ERROR_CREATION(m_label_name_file_val);
|
|
|
|
|
return false;
|
|
|
|
|
}
|
2026-03-21 11:41:29 -05:00
|
|
|
x = initial_x; // Reinit
|
|
|
|
|
y += m_label_name_file_val.YSize() + 8; // Bajamos (peude no caber la ruta)
|
2026-03-20 10:20:00 -05:00
|
|
|
|
|
|
|
|
//--- Browse
|
2026-03-21 11:41:29 -05:00
|
|
|
m_btn_name_file_browse.FontSize(10);
|
|
|
|
|
m_btn_name_file_browse.Font("Arial");
|
|
|
|
|
m_btn_name_file_browse.BackColor(AIDATATASKRUNER_COLOR_BTN_BACK);
|
|
|
|
|
m_btn_name_file_browse.LabelColor(AIDATATASKRUNER_COLOR_TEXT_SECONDARY);
|
|
|
|
|
m_btn_name_file_browse.BorderColor(AIDATATASKRUNER_COLOR_BTN_BORDER);
|
|
|
|
|
m_btn_name_file_browse.Tooltip(m_language.Tooltip(GUIBASE_COMPONENT_NAME(m_btn_name_file_browse)));
|
|
|
|
|
if(!p.CreateButton(m_btn_name_file_browse, m_language[GUIBASE_COMPONENT_NAME(m_btn_name_file_browse)],
|
2026-03-20 10:20:00 -05:00
|
|
|
main_window, 0, m_base_tab, m_base_tab_idx, x, y, 80))
|
2026-03-20 17:16:21 -05:00
|
|
|
{
|
2026-03-21 11:41:29 -05:00
|
|
|
GUIBASE_ERROR_CREATION(m_btn_name_file_browse);
|
2026-03-20 17:16:21 -05:00
|
|
|
return false;
|
|
|
|
|
}
|
2026-03-21 11:41:29 -05:00
|
|
|
x += m_btn_name_file_browse.XSize() + 5;
|
2026-03-20 10:20:00 -05:00
|
|
|
|
|
|
|
|
//--- Open
|
|
|
|
|
m_btn_open.FontSize(10);
|
|
|
|
|
m_btn_open.Font("Arial");
|
|
|
|
|
m_btn_open.BackColor(AIDATATASKRUNER_COLOR_BTN_BACK);
|
|
|
|
|
m_btn_open.LabelColor(AIDATATASKRUNER_COLOR_TEXT_SECONDARY);
|
|
|
|
|
m_btn_open.BorderColor(AIDATATASKRUNER_COLOR_BTN_BORDER);
|
|
|
|
|
m_btn_open.Tooltip(m_language.Tooltip(GUIBASE_COMPONENT_NAME(m_btn_open)));
|
|
|
|
|
if(!p.CreateButton(m_btn_open, m_language[GUIBASE_COMPONENT_NAME(m_btn_open)],
|
|
|
|
|
main_window, 0, m_base_tab, m_base_tab_idx, x, y, 80))
|
2026-03-20 17:16:21 -05:00
|
|
|
{
|
|
|
|
|
GUIBASE_ERROR_CREATION(m_btn_open);
|
|
|
|
|
return false;
|
|
|
|
|
}
|
2026-03-25 09:57:33 -05:00
|
|
|
x += m_btn_open.XSize() + 5;
|
|
|
|
|
|
|
|
|
|
//---
|
|
|
|
|
m_btn_file_config_template.FontSize(10);
|
|
|
|
|
m_btn_file_config_template.Font("Arial");
|
|
|
|
|
m_btn_file_config_template.BackColor(AIDATATASKRUNER_COLOR_BTN_BACK);
|
|
|
|
|
m_btn_file_config_template.LabelColor(AIDATATASKRUNER_COLOR_TEXT_SECONDARY);
|
|
|
|
|
m_btn_file_config_template.BorderColor(AIDATATASKRUNER_COLOR_BTN_BORDER);
|
|
|
|
|
m_btn_file_config_template.Tooltip(m_language.Tooltip(GUIBASE_COMPONENT_NAME(m_btn_file_config_template)));
|
|
|
|
|
if(!p.CreateButton(m_btn_file_config_template, "?",
|
|
|
|
|
main_window, 0, m_base_tab, m_base_tab_idx, x, y, 50))
|
|
|
|
|
{
|
|
|
|
|
GUIBASE_ERROR_CREATION(m_btn_file_config_template);
|
|
|
|
|
return false;
|
|
|
|
|
}
|
2026-03-20 17:16:21 -05:00
|
|
|
|
|
|
|
|
//--- Label titulo Run Python
|
2026-03-21 11:41:29 -05:00
|
|
|
y += m_btn_open.YSize() + 21; // separacion visual de seccion
|
|
|
|
|
x = initial_x;
|
2026-03-20 17:16:21 -05:00
|
|
|
|
|
|
|
|
m_label_tit_run_py.FontSize(14);
|
|
|
|
|
m_label_tit_run_py.Font("Arial");
|
|
|
|
|
m_label_tit_run_py.LabelColor(AIDATATASKRUNER_COLOR_TEXT_PRIMARY);
|
2026-03-21 11:41:29 -05:00
|
|
|
m_label_tit_run_py.BackColor(AIDATATASKRUNER_COLOR_FONDO_SUBTAB_PRESSED);
|
2026-03-20 17:16:21 -05:00
|
|
|
if(!p.CreateTextLabel(m_label_tit_run_py, m_language[GUIBASE_COMPONENT_NAME(m_label_tit_run_py)],
|
|
|
|
|
main_window, 0, m_base_tab, m_base_tab_idx, x, y, 200))
|
|
|
|
|
{
|
|
|
|
|
GUIBASE_ERROR_CREATION(m_label_tit_run_py);
|
|
|
|
|
return false;
|
|
|
|
|
}
|
|
|
|
|
y += m_label_tit_run_py.YSize() + 10;
|
|
|
|
|
|
2026-03-21 11:41:29 -05:00
|
|
|
//--- Label py file
|
|
|
|
|
m_label_py_file.FontSize(10);
|
|
|
|
|
m_label_py_file.Font("Arial");
|
|
|
|
|
m_label_py_file.LabelColor(AIDATATASKRUNER_COLOR_TEXT_SECONDARY);
|
|
|
|
|
m_label_py_file.BackColor(AIDATATASKRUNER_COLOR_FONDO_SUBTAB_PRESSED);
|
|
|
|
|
if(!p.CreateTextLabel(m_label_py_file, m_language[GUIBASE_COMPONENT_NAME(m_label_py_file)],
|
|
|
|
|
main_window, 0, m_base_tab, m_base_tab_idx, x, y, 100, 25))
|
|
|
|
|
{
|
|
|
|
|
GUIBASE_ERROR_CREATION(m_label_py_file);
|
|
|
|
|
return false;
|
|
|
|
|
}
|
|
|
|
|
x += m_label_py_file.XSize() + 5;
|
|
|
|
|
|
|
|
|
|
//--- Label py file val
|
|
|
|
|
m_label_py_file_val.FontSize(10);
|
|
|
|
|
m_label_py_file_val.Font("Arial");
|
|
|
|
|
m_label_py_file_val.LabelColor(AIDATATASKRUNER_COLOR_TEXT_PRIMARY);
|
|
|
|
|
m_label_py_file_val.BackColor(AIDATATASKRUNER_COLOR_EDIT_BACK);
|
|
|
|
|
m_label_py_file_val.LabelXGap(5);
|
2026-03-26 06:46:59 -05:00
|
|
|
m_label_py_file_val.LabelYGap(2);
|
2026-03-21 11:41:29 -05:00
|
|
|
m_label_py_file_val.Tooltip(m_language.Tooltip(GUIBASE_COMPONENT_NAME(m_label_py_file_val)));
|
2026-03-26 11:23:24 -05:00
|
|
|
const int x_label_py_file_val = x;
|
2026-03-21 11:41:29 -05:00
|
|
|
if(!p.CreateTextLabel(m_label_py_file_val, "",
|
2026-03-26 06:46:59 -05:00
|
|
|
main_window, 0, m_base_tab, m_base_tab_idx, x, y, 425, 25))
|
2026-03-21 11:41:29 -05:00
|
|
|
{
|
|
|
|
|
GUIBASE_ERROR_CREATION(m_label_py_file_val);
|
|
|
|
|
return false;
|
|
|
|
|
}
|
2026-03-26 11:23:24 -05:00
|
|
|
x = initial_x;
|
2026-03-21 11:41:29 -05:00
|
|
|
y += m_label_py_file_val.YSize() + 8;
|
|
|
|
|
|
|
|
|
|
//--- Browse py file
|
|
|
|
|
m_btn_py_file_browse.FontSize(10);
|
|
|
|
|
m_btn_py_file_browse.Font("Arial");
|
|
|
|
|
m_btn_py_file_browse.BackColor(AIDATATASKRUNER_COLOR_BTN_BACK);
|
|
|
|
|
m_btn_py_file_browse.LabelColor(AIDATATASKRUNER_COLOR_TEXT_SECONDARY);
|
|
|
|
|
m_btn_py_file_browse.BorderColor(AIDATATASKRUNER_COLOR_BTN_BORDER);
|
|
|
|
|
m_btn_py_file_browse.Tooltip(m_language.Tooltip(GUIBASE_COMPONENT_NAME(m_btn_py_file_browse)));
|
|
|
|
|
if(!p.CreateButton(m_btn_py_file_browse, m_language[GUIBASE_COMPONENT_NAME(m_btn_py_file_browse)],
|
|
|
|
|
main_window, 0, m_base_tab, m_base_tab_idx, x, y, 80))
|
|
|
|
|
{
|
|
|
|
|
GUIBASE_ERROR_CREATION(m_btn_py_file_browse);
|
|
|
|
|
return false;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
//---
|
|
|
|
|
y += m_btn_py_file_browse.YSize() + 10; // separacion visual de seccion
|
|
|
|
|
x = initial_x;
|
|
|
|
|
|
2026-03-26 11:23:24 -05:00
|
|
|
|
|
|
|
|
//--- Label logpy file
|
|
|
|
|
m_label_log_pyfile.FontSize(10);
|
|
|
|
|
m_label_log_pyfile.Font("Arial");
|
|
|
|
|
m_label_log_pyfile.LabelColor(AIDATATASKRUNER_COLOR_TEXT_SECONDARY);
|
|
|
|
|
m_label_log_pyfile.BackColor(AIDATATASKRUNER_COLOR_FONDO_SUBTAB_PRESSED);
|
|
|
|
|
if(!p.CreateTextLabel(m_label_log_pyfile, m_language[GUIBASE_COMPONENT_NAME(m_label_log_pyfile)],
|
|
|
|
|
main_window, 0, m_base_tab, m_base_tab_idx, x, y, 130, 25))
|
|
|
|
|
{
|
|
|
|
|
GUIBASE_ERROR_CREATION(m_label_py_file);
|
|
|
|
|
return false;
|
|
|
|
|
}
|
|
|
|
|
x = x_label_py_file_val; // mismo nivel
|
|
|
|
|
|
|
|
|
|
//--- Label logpy file val
|
|
|
|
|
m_label_log_pyfile_val.FontSize(10);
|
|
|
|
|
m_label_log_pyfile_val.Font("Arial");
|
|
|
|
|
m_label_log_pyfile_val.LabelColor(AIDATATASKRUNER_COLOR_TEXT_PRIMARY);
|
|
|
|
|
m_label_log_pyfile_val.BackColor(AIDATATASKRUNER_COLOR_EDIT_BACK);
|
|
|
|
|
m_label_log_pyfile_val.LabelXGap(5);
|
|
|
|
|
m_label_log_pyfile_val.LabelYGap(2);
|
|
|
|
|
m_label_log_pyfile_val.Tooltip(m_language.Tooltip(GUIBASE_COMPONENT_NAME(m_label_log_pyfile_val)));
|
|
|
|
|
if(!p.CreateTextLabel(m_label_log_pyfile_val, "",
|
|
|
|
|
main_window, 0, m_base_tab, m_base_tab_idx, x, y, 425, 25))
|
|
|
|
|
{
|
|
|
|
|
GUIBASE_ERROR_CREATION(m_label_log_pyfile_val);
|
|
|
|
|
return false;
|
|
|
|
|
}
|
|
|
|
|
x = initial_x;
|
|
|
|
|
y += m_label_log_pyfile_val.YSize() + 8;
|
|
|
|
|
|
|
|
|
|
//--- Browse logpy file
|
|
|
|
|
m_btn_logpyfile_browse.FontSize(10);
|
|
|
|
|
m_btn_logpyfile_browse.Font("Arial");
|
|
|
|
|
m_btn_logpyfile_browse.BackColor(AIDATATASKRUNER_COLOR_BTN_BACK);
|
|
|
|
|
m_btn_logpyfile_browse.LabelColor(AIDATATASKRUNER_COLOR_TEXT_SECONDARY);
|
|
|
|
|
m_btn_logpyfile_browse.BorderColor(AIDATATASKRUNER_COLOR_BTN_BORDER);
|
|
|
|
|
m_btn_logpyfile_browse.Tooltip(m_language.Tooltip(GUIBASE_COMPONENT_NAME(m_btn_logpyfile_browse)));
|
|
|
|
|
if(!p.CreateButton(m_btn_logpyfile_browse, m_language[GUIBASE_COMPONENT_NAME(m_btn_logpyfile_browse)],
|
|
|
|
|
main_window, 0, m_base_tab, m_base_tab_idx, x, y, 80))
|
|
|
|
|
{
|
|
|
|
|
GUIBASE_ERROR_CREATION(m_btn_logpyfile_browse);
|
|
|
|
|
return false;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
//---
|
|
|
|
|
y += m_btn_logpyfile_browse.YSize() + 10; // separacion visual de seccion
|
|
|
|
|
x = initial_x;
|
|
|
|
|
|
2026-03-24 10:39:38 -05:00
|
|
|
//---
|
|
|
|
|
const string texto = m_language[AIDATATASKRUNNERL_COMPONENT_NAME(m_edit_py_max_tiemout)];
|
|
|
|
|
m_edit_py_max_tiemout.FontSize(10);
|
|
|
|
|
m_edit_py_max_tiemout.Font("Arial");
|
|
|
|
|
m_edit_py_max_tiemout.CanvasFontSet();
|
|
|
|
|
const int width = m_edit_py_max_tiemout.m_canvas.TextWidth(texto);
|
|
|
|
|
m_edit_py_max_tiemout.LabelColor(AIDATATASKRUNER_COLOR_TEXT_SECONDARY);
|
|
|
|
|
m_edit_py_max_tiemout.BackColor(AIDATATASKRUNER_COLOR_FONDO_SUBTAB_PRESSED);
|
|
|
|
|
m_edit_py_max_tiemout.GetTextBoxPointer().BackColor(AIDATATASKRUNER_COLOR_EDIT_BACK);
|
|
|
|
|
m_edit_py_max_tiemout.GetTextBoxPointer().BorderColor(AIDATATASKRUNER_COLOR_EDIT_BORDER);
|
|
|
|
|
m_edit_py_max_tiemout.GetTextBoxPointer().DefaultTextColor(AIDATATASKRUNER_COLOR_EDIT_TEXT_NORMAL);
|
|
|
|
|
m_edit_py_max_tiemout.GetTextBoxPointer().LabelColor(AIDATATASKRUNER_COLOR_EDIT_TEXT_NORMAL);
|
|
|
|
|
m_edit_py_max_tiemout.GetTextBoxPointer().SelectedBackColor(AIDATATASKRUNER_COLOR_EDIT_TEXT_SELECTED);
|
|
|
|
|
m_edit_py_max_tiemout.GetTextBoxPointer().SelectedTextColor(AIDATATASKRUNER_COLOR_EDIT_TEXT_HIGHLIGHT);
|
|
|
|
|
m_edit_py_max_tiemout.Tooltip(m_language.Tooltip(GUIBASE_COMPONENT_NAME(m_edit_py_max_tiemout)));
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
#define AIDATATASKRUNNER_TRAINING_EDITPY_MAX_VAL (double(UINT_MAX)/1000.0)
|
2026-03-26 09:51:33 -05:00
|
|
|
#define AIDATATASKRUNNER_TRAINING_EDITPY_DEF_VAL (1800)
|
2026-03-24 10:39:38 -05:00
|
|
|
if(!p.CreateTextEdit(m_edit_py_max_tiemout, texto,
|
|
|
|
|
main_window, 0, m_base_tab, m_base_tab_idx, false, x, y,
|
|
|
|
|
width + 10 + 200, 200, AIDATATASKRUNNER_TRAINING_EDITPY_MAX_VAL
|
2026-03-26 09:51:33 -05:00
|
|
|
, 1.0, 1.0, 0, double(AIDATATASKRUNNER_TRAINING_EDITPY_DEF_VAL))) // Min value = 1.0 | Step = 1.0 | 0 = Digitos | 1800 = valor por defecto (30 minutos)
|
2026-03-24 10:39:38 -05:00
|
|
|
{
|
|
|
|
|
AIDATATASKRUNER_ERROR_CREATION(m_edit_py_max_tiemout);
|
|
|
|
|
return false;
|
|
|
|
|
}
|
2026-03-26 09:51:33 -05:00
|
|
|
m_timeout_for_execute_py = AIDATATASKRUNNER_TRAINING_EDITPY_DEF_VAL * 1000; // 30 min default
|
2026-03-24 10:39:38 -05:00
|
|
|
|
|
|
|
|
//---
|
|
|
|
|
y += m_edit_py_max_tiemout.YSize() + 12;
|
|
|
|
|
x = initial_x;
|
|
|
|
|
|
|
|
|
|
|
2026-03-20 17:16:21 -05:00
|
|
|
//--- Boton Run
|
|
|
|
|
m_btn_run_py.FontSize(10);
|
|
|
|
|
m_btn_run_py.Font("Arial");
|
|
|
|
|
m_btn_run_py.BackColor(AIDATATASKRUNER_COLOR_BTN_BACK);
|
|
|
|
|
m_btn_run_py.LabelColor(AIDATATASKRUNER_COLOR_TEXT_SECONDARY);
|
|
|
|
|
m_btn_run_py.BorderColor(AIDATATASKRUNER_COLOR_BTN_BORDER);
|
|
|
|
|
m_btn_run_py.Tooltip(m_language.Tooltip(GUIBASE_COMPONENT_NAME(m_btn_run_py)));
|
|
|
|
|
if(!p.CreateButton(m_btn_run_py, m_language[GUIBASE_COMPONENT_NAME(m_btn_run_py)],
|
|
|
|
|
main_window, 0, m_base_tab, m_base_tab_idx, x, y, 140))
|
|
|
|
|
{
|
|
|
|
|
GUIBASE_ERROR_CREATION(m_btn_run_py);
|
|
|
|
|
return false;
|
|
|
|
|
}
|
2026-03-20 10:20:00 -05:00
|
|
|
|
2026-03-26 09:51:33 -05:00
|
|
|
|
2026-03-20 17:16:21 -05:00
|
|
|
//---
|
2026-03-20 10:20:00 -05:00
|
|
|
return true;
|
|
|
|
|
}
|
|
|
|
|
|
2026-03-24 10:39:38 -05:00
|
|
|
//+------------------------------------------------------------------+
|
|
|
|
|
//| |
|
|
|
|
|
//+------------------------------------------------------------------+
|
|
|
|
|
bool CTrainingTabConfig::OnTextEdit(const long lparam)
|
|
|
|
|
{
|
|
|
|
|
if(m_edit_py_max_tiemout.Id() == lparam)
|
|
|
|
|
{
|
|
|
|
|
m_timeout_for_execute_py = uint(m_edit_py_max_tiemout.GetValue()) * 1000;
|
|
|
|
|
return true;
|
|
|
|
|
}
|
|
|
|
|
return false;
|
|
|
|
|
}
|
|
|
|
|
|
2026-03-26 06:46:59 -05:00
|
|
|
//+------------------------------------------------------------------+
|
|
|
|
|
//| |
|
|
|
|
|
//+------------------------------------------------------------------+
|
|
|
|
|
bool CTrainingTabConfig::OnClickDec(const long lparam)
|
|
|
|
|
{
|
|
|
|
|
if(m_edit_py_max_tiemout.Id() == lparam)
|
|
|
|
|
{
|
|
|
|
|
m_timeout_for_execute_py = uint(m_edit_py_max_tiemout.GetValue()) * 1000;
|
|
|
|
|
return true;
|
|
|
|
|
}
|
|
|
|
|
return false;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
//+------------------------------------------------------------------+
|
|
|
|
|
//| |
|
|
|
|
|
//+------------------------------------------------------------------+
|
|
|
|
|
bool CTrainingTabConfig::OnClickInc(const long lparam)
|
|
|
|
|
{
|
|
|
|
|
if(m_edit_py_max_tiemout.Id() == lparam)
|
|
|
|
|
{
|
|
|
|
|
m_timeout_for_execute_py = uint(m_edit_py_max_tiemout.GetValue()) * 1000;
|
|
|
|
|
return true;
|
|
|
|
|
}
|
|
|
|
|
return false;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
2026-03-20 10:20:00 -05:00
|
|
|
//+------------------------------------------------------------------+
|
|
|
|
|
//| |
|
|
|
|
|
//+------------------------------------------------------------------+
|
|
|
|
|
bool CTrainingTabConfig::OnClickBottom(const long lparam)
|
|
|
|
|
{
|
2026-03-26 11:23:24 -05:00
|
|
|
//---
|
|
|
|
|
if(m_btn_logpyfile_browse.Id() == lparam)
|
|
|
|
|
{
|
|
|
|
|
//---
|
|
|
|
|
string arr[];
|
|
|
|
|
if(FileSelectDialog(GUIBASE_MSG("flselect_logiflepy"), NULL, "Log files (*.log)|*.log", (m_common_flag ? FSD_COMMON_FOLDER : 0),
|
|
|
|
|
arr, NULL) != 1)
|
|
|
|
|
{
|
|
|
|
|
MessageBox(GUIBASE_MSG("error_select_file"), GUIBASE_MSG("error"), MB_ICONERROR | MB_OK);
|
|
|
|
|
return true;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
//--- Guardamos la ruta y la extension
|
|
|
|
|
//Print(out_file_complete_path);
|
|
|
|
|
m_label_log_pyfile_val.LabelText(arr[0]); // ruta completa aqui
|
|
|
|
|
m_label_log_pyfile_val.Update(true);
|
|
|
|
|
|
|
|
|
|
//---
|
|
|
|
|
return true;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
2026-03-20 17:16:21 -05:00
|
|
|
//---
|
2026-03-21 11:41:29 -05:00
|
|
|
if(m_btn_py_file_browse.Id() == lparam)
|
|
|
|
|
{
|
2026-03-26 06:46:59 -05:00
|
|
|
string out_file_complete_path = "";
|
2026-03-25 18:14:32 -05:00
|
|
|
if(!FileSelectDialogComplete(out_file_complete_path, 500, GUIBASE_MSG("flselect_py"),
|
2026-03-26 06:46:59 -05:00
|
|
|
"Python files (*.py)\0*.py\0Executable files (*.exe)\0*.exe\0\0", TERMINAL_MT5_DATA_PAH, // Base del temrinal NAME\\
|
|
|
|
|
OFN_FILEMUSTEXIST | OFN_PATHMUSTEXIST)) // EL FOLDER y archivo deben de sexisteir
|
2026-03-21 11:41:29 -05:00
|
|
|
{
|
|
|
|
|
//reciclamos el msg mismo que se usa en el browse deljson confgig
|
2026-03-25 18:05:47 -05:00
|
|
|
MessageBox(GUIBASE_MSG("error_select_file"), GUIBASE_MSG("error"), MB_ICONERROR | MB_OK);
|
2026-03-21 11:41:29 -05:00
|
|
|
return true;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
//--- Guardamos la ruta y la extension
|
2026-03-26 06:46:59 -05:00
|
|
|
//Print(out_file_complete_path);
|
2026-03-25 18:05:47 -05:00
|
|
|
m_label_py_file_val.LabelText(out_file_complete_path); // ruta completa aqui
|
2026-03-21 11:41:29 -05:00
|
|
|
m_label_py_file_val.Update(true);
|
|
|
|
|
|
|
|
|
|
//---
|
2026-03-25 18:05:47 -05:00
|
|
|
m_py_file_extension = FileGetExtension(out_file_complete_path); // solo da la ext no con el .
|
2026-03-21 11:41:29 -05:00
|
|
|
|
|
|
|
|
return true;
|
|
|
|
|
}
|
|
|
|
|
|
2026-03-26 11:23:24 -05:00
|
|
|
//--- Config file
|
|
|
|
|
// Browse
|
2026-03-21 11:41:29 -05:00
|
|
|
if(m_btn_name_file_browse.Id() == lparam)
|
2026-03-20 10:20:00 -05:00
|
|
|
{
|
|
|
|
|
//---
|
|
|
|
|
string arr[];
|
2026-03-25 09:57:33 -05:00
|
|
|
if(FileSelectDialog("Configuration", NULL, "JSON files (*.json)|*.json", (m_common_flag ? FSD_COMMON_FOLDER : 0) | FSD_FILE_MUST_EXIST,
|
2026-03-20 10:20:00 -05:00
|
|
|
arr, NULL) != 1)
|
|
|
|
|
{
|
2026-03-25 18:05:47 -05:00
|
|
|
MessageBox(GUIBASE_MSG("error_select_file"), GUIBASE_MSG("error"), MB_ICONERROR | MB_OK);
|
2026-03-20 10:20:00 -05:00
|
|
|
return true;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
//---
|
|
|
|
|
m_label_name_file_val.LabelText(arr[0]);
|
|
|
|
|
m_label_name_file_val.Update(true);
|
|
|
|
|
|
|
|
|
|
//---
|
|
|
|
|
return true;
|
|
|
|
|
}
|
2026-03-20 17:16:21 -05:00
|
|
|
|
2026-03-26 11:23:24 -05:00
|
|
|
// Template
|
2026-03-25 09:57:33 -05:00
|
|
|
if(m_btn_file_config_template.Id() == lparam)
|
|
|
|
|
{
|
|
|
|
|
//---
|
|
|
|
|
string arr[];
|
|
|
|
|
// para el temaplte usamos el common folder flag del panel dado que teamplestes se ubica ahi vale?¿
|
|
|
|
|
if(FileSelectDialog("Configuration", AIDATATASKRUNER_PATH_TEMPLATES, "JSON files (*.json)|*.json", AIDATATASK_RUNNER_FSD_COMON_FLAG | FSD_FILE_MUST_EXIST,
|
2026-03-27 12:33:09 -05:00
|
|
|
arr, AIDATATASKRUNER_FILENAME_TEMPLATES_PYCONFIG) != 1)
|
2026-03-25 09:57:33 -05:00
|
|
|
{
|
|
|
|
|
MessageBox(GUIBASE_MSG("error_select_file"), GUIBASE_COMMON("error"), MB_ICONERROR | MB_OK);
|
|
|
|
|
return true;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
//---
|
|
|
|
|
m_label_name_file_val.LabelText(arr[0]);
|
|
|
|
|
m_label_name_file_val.Update(true);
|
|
|
|
|
|
|
|
|
|
//---
|
|
|
|
|
return true;
|
|
|
|
|
}
|
|
|
|
|
|
2026-03-26 11:23:24 -05:00
|
|
|
// Open
|
2026-03-20 10:20:00 -05:00
|
|
|
if(m_btn_open.Id() == lparam)
|
|
|
|
|
{
|
2026-03-21 06:15:18 -05:00
|
|
|
const string full_path = m_base_terminal_files_path + m_label_name_file_val.LabelText();
|
2026-03-20 17:16:21 -05:00
|
|
|
ShellExecuteW(0, "open", full_path, NULL, NULL, SW_SHOW); // no verificamos noe s critrico
|
2026-03-20 10:20:00 -05:00
|
|
|
return true;
|
|
|
|
|
}
|
2026-03-20 17:16:21 -05:00
|
|
|
|
|
|
|
|
//---
|
|
|
|
|
if(m_btn_run_py.Id() == lparam)
|
|
|
|
|
{
|
|
|
|
|
//---
|
|
|
|
|
if(m_py_is_run)
|
|
|
|
|
{
|
2026-03-25 09:57:33 -05:00
|
|
|
MessageBox(GUIBASE_MSG("python_is_runing"), GUIBASE_COMMON("warning"), MB_ICONWARNING | MB_OK);
|
2026-03-20 17:16:21 -05:00
|
|
|
return true;
|
|
|
|
|
}
|
|
|
|
|
|
2026-03-24 10:39:38 -05:00
|
|
|
//--- Check inicialzies
|
|
|
|
|
// Configuracion seleccionada
|
2026-03-20 17:16:21 -05:00
|
|
|
const string config = m_label_name_file_val.LabelText();
|
|
|
|
|
if(config.Length() < 1)
|
|
|
|
|
{
|
2026-03-25 09:57:33 -05:00
|
|
|
MessageBox(GUIBASE_MSG("no_config_selected"), GUIBASE_COMMON("error"), MB_ICONERROR | MB_OK);
|
2026-03-20 17:16:21 -05:00
|
|
|
return true;
|
|
|
|
|
}
|
|
|
|
|
|
2026-03-24 10:39:38 -05:00
|
|
|
// Archivos py selecionado
|
2026-03-21 11:41:29 -05:00
|
|
|
const string py = m_label_py_file_val.LabelText();
|
|
|
|
|
if(py.Length() < 1)
|
|
|
|
|
{
|
2026-03-25 09:57:33 -05:00
|
|
|
MessageBox(GUIBASE_MSG("no_py_selected"), GUIBASE_COMMON("error"), MB_ICONERROR | MB_OK);
|
2026-03-21 11:41:29 -05:00
|
|
|
return true;
|
|
|
|
|
}
|
|
|
|
|
|
2026-03-24 10:39:38 -05:00
|
|
|
//--- Abrimos el archivo de comuncionacion
|
|
|
|
|
const string fn = AIDATATASKRUNER_BASE_FOLDER + AIDATATASKRUNNER_FILENAME_ARGS_LAUNCHER;
|
|
|
|
|
::ResetLastError();
|
2026-03-26 09:51:33 -05:00
|
|
|
const int fh = FileOpen(fn, FILE_WRITE | FILE_TXT | AIDATATASK_RUNNER_COMON_FLAG, 0);
|
2026-03-24 10:39:38 -05:00
|
|
|
if(fh == INVALID_HANDLE)
|
|
|
|
|
{
|
2026-03-25 09:57:33 -05:00
|
|
|
MessageBox(StringFormat(GUIBASE_MSG("python_launch_error_file"), ::GetLastError()), GUIBASE_COMMON("error"), MB_ICONERROR | MB_OK);
|
2026-03-24 10:39:38 -05:00
|
|
|
return true;
|
|
|
|
|
}
|
2026-03-20 17:16:21 -05:00
|
|
|
|
2026-03-24 10:39:38 -05:00
|
|
|
//---
|
|
|
|
|
// Escritura
|
2026-03-26 11:23:24 -05:00
|
|
|
FileWrite(fh, m_label_log_pyfile_val.LabelText());
|
2026-03-25 18:05:47 -05:00
|
|
|
FileWrite(fh, py); // Py path to execute (ya da la ruyta completa)
|
2026-03-24 10:39:38 -05:00
|
|
|
FileWrite(fh, m_py_file_extension); // Extension
|
2026-03-28 08:35:32 -05:00
|
|
|
FileWrite(fh, m_path_py_interpete); // Interprete
|
2026-03-28 10:58:12 -05:00
|
|
|
FileWrite(fh, m_python_path_env);
|
2026-03-24 10:39:38 -05:00
|
|
|
::FileClose(fh);
|
|
|
|
|
|
2026-03-26 09:51:33 -05:00
|
|
|
//---
|
|
|
|
|
/*
|
|
|
|
|
input string InpFileNameArgs = "";
|
|
|
|
|
input int InpFileCommonFlag = 0;
|
2026-03-26 10:26:25 -05:00
|
|
|
|
2026-03-26 09:51:33 -05:00
|
|
|
input string InpArgsConfigJson = "";
|
|
|
|
|
input string InpArgsResJson = "";
|
|
|
|
|
input string InpArgsLockBin = "";
|
|
|
|
|
input string InpArgsBaseTerminalPath = "";
|
|
|
|
|
// 1 hora (3600 * 1000) en ms
|
|
|
|
|
input uint InpPyTimeoutMs = 3600000;
|
|
|
|
|
*/
|
|
|
|
|
|
2026-03-24 10:39:38 -05:00
|
|
|
//--- Lanzamos el ea
|
2026-03-28 10:58:12 -05:00
|
|
|
MqlParam params[9];
|
2026-03-24 10:39:38 -05:00
|
|
|
params[0].type = TYPE_STRING;
|
|
|
|
|
params[0].string_value = "Experts\\" + m_path_to_ea_launcher;
|
|
|
|
|
params[1].type = TYPE_STRING;
|
|
|
|
|
params[1].string_value = fn; // Nombre del archivo
|
|
|
|
|
params[2].type = TYPE_INT;
|
|
|
|
|
params[2].integer_value = AIDATATASK_RUNNER_COMON_FLAG; // Bandera common o no common
|
2026-03-24 07:46:45 -05:00
|
|
|
|
2026-03-21 11:41:29 -05:00
|
|
|
//---
|
2026-03-24 10:39:38 -05:00
|
|
|
// Paramemos de args como tal
|
|
|
|
|
params[3].type = TYPE_STRING;
|
2026-03-26 09:51:33 -05:00
|
|
|
params[3].string_value = config;
|
2026-03-24 10:39:38 -05:00
|
|
|
params[4].type = TYPE_STRING;
|
2026-03-26 09:51:33 -05:00
|
|
|
params[4].string_value = m_path_to_config_json;
|
2026-03-24 10:39:38 -05:00
|
|
|
params[5].type = TYPE_STRING;
|
2026-03-26 09:51:33 -05:00
|
|
|
params[5].string_value = m_path_to_lock_bin;
|
2026-03-24 10:39:38 -05:00
|
|
|
// Basew terminal path s
|
|
|
|
|
params[6].type = TYPE_STRING;
|
|
|
|
|
params[6].string_value = m_base_terminal_files_path;
|
2026-03-21 11:41:29 -05:00
|
|
|
|
|
|
|
|
//---
|
2026-03-24 10:39:38 -05:00
|
|
|
params[7].type = TYPE_UINT;
|
|
|
|
|
params[7].integer_value = m_timeout_for_execute_py;
|
|
|
|
|
|
2026-03-28 10:58:12 -05:00
|
|
|
//---
|
|
|
|
|
params[8].type = TYPE_STRING;
|
|
|
|
|
params[8].string_value = AIDATATASKRUNER_BASE_FOLDER + AIDATATASKRUNNER_FILENAME_BAT_PY;
|
|
|
|
|
|
|
|
|
|
|
2026-03-24 10:47:07 -05:00
|
|
|
//---
|
|
|
|
|
::ResetLastError();
|
|
|
|
|
const long bot_chart_id = OpenChartAndDevoler(ChartID(), _Symbol, _Period, 1500);
|
|
|
|
|
if(bot_chart_id == -1)
|
|
|
|
|
{
|
2026-03-25 09:57:33 -05:00
|
|
|
MessageBox(StringFormat(GUIBASE_MSG("python_launch_error_chart"), ::GetLastError()), GUIBASE_COMMON("error"), MB_ICONERROR | MB_OK);
|
2026-03-24 10:47:07 -05:00
|
|
|
return true;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
//--- Check sincronizacion del grafico
|
|
|
|
|
while(ChartGetInteger(bot_chart_id, CHART_VISIBLE_BARS) < 1)
|
|
|
|
|
{
|
|
|
|
|
// Espera para la siguiente iteracion
|
|
|
|
|
Sleep(350);
|
|
|
|
|
}
|
|
|
|
|
|
2026-03-24 10:39:38 -05:00
|
|
|
|
2026-03-24 10:47:07 -05:00
|
|
|
if(!EXPERT::Run(bot_chart_id, params, EXPERT_PERMISOS_FLAG_DLL))
|
2026-03-20 17:16:21 -05:00
|
|
|
{
|
2026-03-25 09:57:33 -05:00
|
|
|
MessageBox(GUIBASE_MSG("python_launch_error_exe"), GUIBASE_COMMON("error"), MB_ICONERROR | MB_OK);
|
2026-03-26 09:51:33 -05:00
|
|
|
::ChartClose(bot_chart_id); // Cerramos
|
2026-03-20 17:16:21 -05:00
|
|
|
return true;
|
|
|
|
|
}
|
|
|
|
|
|
2026-03-24 10:39:38 -05:00
|
|
|
//--- Exito al lanzar el runner entonces comenzamos
|
2026-03-20 17:16:21 -05:00
|
|
|
OnTrainingStart();
|
|
|
|
|
|
|
|
|
|
//---
|
|
|
|
|
m_py_is_run = true;
|
|
|
|
|
|
|
|
|
|
//--- cambio de estado a running
|
|
|
|
|
m_btn_run_py.LabelText(m_language[GUIBASE_COMPONENT_NAME(m_btn_run_py) + "_running"]);
|
|
|
|
|
m_btn_run_py.Update(true);
|
|
|
|
|
return true;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
//---
|
2026-03-20 10:20:00 -05:00
|
|
|
return false;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
//+------------------------------------------------------------------+
|
|
|
|
|
//| |
|
|
|
|
|
//+------------------------------------------------------------------+
|
|
|
|
|
void CTrainingTabConfig::OnLenguajeChange(void)
|
|
|
|
|
{
|
2026-03-21 11:41:29 -05:00
|
|
|
|
|
|
|
|
|
2026-03-20 17:16:21 -05:00
|
|
|
//---
|
2026-03-20 10:20:00 -05:00
|
|
|
m_label_titulo.LabelText(m_language[GUIBASE_COMPONENT_NAME(m_label_titulo)]);
|
|
|
|
|
m_label_titulo.Update(true);
|
|
|
|
|
|
2026-03-20 17:16:21 -05:00
|
|
|
//---
|
2026-03-26 11:23:24 -05:00
|
|
|
// Label
|
2026-03-20 10:20:00 -05:00
|
|
|
m_label_name_file.LabelText(m_language[GUIBASE_COMPONENT_NAME(m_label_name_file)]);
|
|
|
|
|
m_label_name_file.Update(true);
|
|
|
|
|
|
2026-03-26 11:23:24 -05:00
|
|
|
// Val
|
2026-03-20 17:16:21 -05:00
|
|
|
m_label_name_file_val.Tooltip(m_language.Tooltip(GUIBASE_COMPONENT_NAME(m_label_name_file_val)));
|
|
|
|
|
|
2026-03-26 11:23:24 -05:00
|
|
|
// Browse
|
2026-03-21 11:41:29 -05:00
|
|
|
m_btn_name_file_browse.LabelText(m_language[GUIBASE_COMPONENT_NAME(m_btn_name_file_browse)]);
|
|
|
|
|
m_btn_name_file_browse.Tooltip(m_language.Tooltip(GUIBASE_COMPONENT_NAME(m_btn_name_file_browse)));
|
|
|
|
|
m_btn_name_file_browse.Update(true);
|
2026-03-20 10:20:00 -05:00
|
|
|
|
2026-03-26 11:23:24 -05:00
|
|
|
// Open
|
2026-03-20 10:20:00 -05:00
|
|
|
m_btn_open.LabelText(m_language[GUIBASE_COMPONENT_NAME(m_btn_open)]);
|
|
|
|
|
m_btn_open.Tooltip(m_language.Tooltip(GUIBASE_COMPONENT_NAME(m_btn_open)));
|
|
|
|
|
m_btn_open.Update(true);
|
2026-03-20 17:16:21 -05:00
|
|
|
|
2026-03-26 11:23:24 -05:00
|
|
|
// Teemplate ?
|
2026-03-25 09:57:33 -05:00
|
|
|
m_btn_file_config_template.Tooltip(m_language.Tooltip(GUIBASE_COMPONENT_NAME(m_btn_file_config_template)));
|
|
|
|
|
|
2026-03-26 11:23:24 -05:00
|
|
|
//--- Titulo run py
|
2026-03-20 17:16:21 -05:00
|
|
|
m_label_tit_run_py.LabelText(m_language[GUIBASE_COMPONENT_NAME(m_label_tit_run_py)]);
|
|
|
|
|
m_label_tit_run_py.Update(true);
|
|
|
|
|
|
2026-03-21 11:41:29 -05:00
|
|
|
//---
|
2026-03-26 11:23:24 -05:00
|
|
|
// Label
|
2026-03-21 11:41:29 -05:00
|
|
|
m_label_py_file.LabelText(m_language[GUIBASE_COMPONENT_NAME(m_label_py_file)]);
|
|
|
|
|
m_label_py_file.Update(true);
|
|
|
|
|
|
2026-03-26 11:23:24 -05:00
|
|
|
// Val
|
2026-03-21 11:41:29 -05:00
|
|
|
m_label_py_file_val.Tooltip(m_language.Tooltip(GUIBASE_COMPONENT_NAME(m_label_py_file_val)));
|
|
|
|
|
|
2026-03-26 11:23:24 -05:00
|
|
|
// Browse
|
2026-03-21 11:41:29 -05:00
|
|
|
m_btn_py_file_browse.LabelText(m_language[GUIBASE_COMPONENT_NAME(m_btn_py_file_browse)]);
|
|
|
|
|
m_btn_py_file_browse.Tooltip(m_language.Tooltip(GUIBASE_COMPONENT_NAME(m_btn_py_file_browse)));
|
|
|
|
|
m_btn_py_file_browse.Update(true);
|
|
|
|
|
|
2026-03-26 11:23:24 -05:00
|
|
|
|
|
|
|
|
//---
|
|
|
|
|
// Label
|
|
|
|
|
m_label_log_pyfile.LabelText(m_language[GUIBASE_COMPONENT_NAME(m_label_log_pyfile)]);
|
|
|
|
|
m_label_log_pyfile.Update(true);
|
|
|
|
|
|
|
|
|
|
// Val
|
|
|
|
|
m_label_log_pyfile_val.Tooltip(m_language.Tooltip(GUIBASE_COMPONENT_NAME(m_label_log_pyfile_val)));
|
|
|
|
|
|
|
|
|
|
// Browse
|
|
|
|
|
m_btn_logpyfile_browse.LabelText(m_language[GUIBASE_COMPONENT_NAME(m_btn_logpyfile_browse)]);
|
|
|
|
|
m_btn_logpyfile_browse.Tooltip(m_language.Tooltip(GUIBASE_COMPONENT_NAME(m_btn_logpyfile_browse)));
|
|
|
|
|
m_btn_logpyfile_browse.Update(true);
|
|
|
|
|
|
|
|
|
|
|
2026-03-24 10:39:38 -05:00
|
|
|
//--- Actulziamos el edit del py
|
|
|
|
|
const string key = GUIBASE_COMPONENT_NAME(m_edit_py_max_tiemout);
|
|
|
|
|
m_edit_py_max_tiemout.LabelText(m_language[key]);
|
|
|
|
|
m_edit_py_max_tiemout.Tooltip(m_language.Tooltip(key));
|
|
|
|
|
const string texto = m_edit_py_max_tiemout.LabelText();
|
|
|
|
|
m_edit_py_max_tiemout.CanvasFontSet();
|
|
|
|
|
const int width = m_edit_py_max_tiemout.m_canvas.TextWidth(texto);
|
|
|
|
|
|
|
|
|
|
// Ancho texto | Extra separacion entre texto y obj element| Ancho de elemento
|
|
|
|
|
m_edit_py_max_tiemout.XSize(width + 10 + 200);
|
|
|
|
|
m_edit_py_max_tiemout.Update(true);
|
|
|
|
|
|
2026-03-20 17:16:21 -05:00
|
|
|
//---
|
2026-03-21 08:06:31 -05:00
|
|
|
m_btn_run_py.Tooltip(m_language[GUIBASE_COMPONENT_NAME(m_btn_run_py)]); // toltip solo cambios
|
2026-03-22 22:09:32 -05:00
|
|
|
m_btn_run_py.LabelText(m_language[GUIBASE_COMPONENT_NAME(m_btn_run_py) + (m_py_is_run ? "_running" : "")]);
|
2026-03-20 17:16:21 -05:00
|
|
|
m_btn_run_py.Update(true);
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
//+------------------------------------------------------------------+
|
|
|
|
|
//| |
|
|
|
|
|
//+------------------------------------------------------------------+
|
2026-03-21 08:06:31 -05:00
|
|
|
void CTrainingTabConfig::AddRunnerPy(IRunPy *runer)
|
2026-03-20 17:16:21 -05:00
|
|
|
{
|
|
|
|
|
//---
|
2026-03-21 08:06:31 -05:00
|
|
|
const uint8_t flags = runer.EventsFlags();
|
|
|
|
|
|
|
|
|
|
//---
|
|
|
|
|
if((flags & TRAINING_RUNNER_PY_FLAG_ON_INIT) != 0)
|
2026-03-20 17:16:21 -05:00
|
|
|
{
|
|
|
|
|
m_runer_py_on_init[ArrayResize(m_runer_py_on_init, (++m_runer_py_on_init_size)) - 1] = runer;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
//---
|
|
|
|
|
if((flags & TRAINING_RUNNER_PY_FLAG_ON_TRAINIG) != 0)
|
|
|
|
|
{
|
|
|
|
|
m_runer_py_on_pass[ArrayResize(m_runer_py_on_pass, (++m_runer_py_on_pass_size)) - 1] = runer;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
//---
|
|
|
|
|
if((flags & TRAINING_RUNNER_PY_FLAG_ON_DEINIT) != 0)
|
|
|
|
|
{
|
|
|
|
|
m_runer_py_on_deinit[ArrayResize(m_runer_py_on_deinit, (++m_runer_py_on_deinit_size)) - 1] = runer;
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
//+------------------------------------------------------------------+
|
|
|
|
|
//| |
|
|
|
|
|
//+------------------------------------------------------------------+
|
|
|
|
|
void CTrainingTabConfig::OnTrainingStart()
|
|
|
|
|
{
|
|
|
|
|
//---
|
|
|
|
|
LogWarning("El entremianeto a empezado", FUNCION_ACTUAL);
|
|
|
|
|
|
|
|
|
|
//--- Eliminamos los archvos anteriorres si es que existen
|
|
|
|
|
::FileDelete(m_path_to_lock_bin, m_extra_file_flags);
|
|
|
|
|
::FileDelete(m_path_to_config_json, m_extra_file_flags);
|
|
|
|
|
|
|
|
|
|
//---
|
|
|
|
|
for(int i = 0; i < m_runer_py_on_init_size; i++)
|
|
|
|
|
{
|
|
|
|
|
m_runer_py_on_init[i].OnTrainingInit();
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
//+------------------------------------------------------------------+
|
|
|
|
|
//| |
|
|
|
|
|
//+------------------------------------------------------------------+
|
|
|
|
|
void CTrainingTabConfig::OnTrainingFinish()
|
|
|
|
|
{
|
|
|
|
|
//---
|
|
|
|
|
m_py_is_run = false;
|
|
|
|
|
|
|
|
|
|
//---
|
|
|
|
|
LogWarning("Training has finished", FUNCION_ACTUAL);
|
|
|
|
|
|
|
|
|
|
//---
|
|
|
|
|
for(int i = 0; i < m_runer_py_on_deinit_size; i++)
|
|
|
|
|
{
|
|
|
|
|
m_runer_py_on_deinit[i].OnTrainingEnd();
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
//---
|
|
|
|
|
const string run_key = GUIBASE_COMPONENT_NAME(m_btn_run_py) + (m_py_is_run ? "_running" : "");
|
2026-03-21 08:06:31 -05:00
|
|
|
m_btn_run_py.LabelText(m_language[run_key]);
|
2026-03-20 17:16:21 -05:00
|
|
|
m_btn_run_py.Update(true);
|
2026-03-20 10:20:00 -05:00
|
|
|
}
|
|
|
|
|
|
2026-03-20 17:16:21 -05:00
|
|
|
|
|
|
|
|
//+------------------------------------------------------------------+
|
|
|
|
|
//| |
|
|
|
|
|
//+------------------------------------------------------------------+
|
|
|
|
|
void CTrainingTabConfig::OnTimerEvent()
|
|
|
|
|
{
|
|
|
|
|
if(!m_py_is_run)
|
|
|
|
|
return;
|
|
|
|
|
|
|
|
|
|
static int8_t ct = 0;
|
|
|
|
|
if(ct++ > AIDATATASKRUNNER_TRAINING_NUM_C)
|
|
|
|
|
{
|
2026-03-21 08:06:31 -05:00
|
|
|
//---
|
|
|
|
|
ct = 0;
|
|
|
|
|
|
2026-03-20 17:16:21 -05:00
|
|
|
//---
|
2026-03-24 10:39:38 -05:00
|
|
|
if(::FileIsExist(m_path_to_lock_bin, m_extra_file_flags))
|
2026-03-20 17:16:21 -05:00
|
|
|
{
|
2026-03-21 08:06:31 -05:00
|
|
|
//--- Reinicio primero procemos luego
|
|
|
|
|
// Lo eliminamos denuevo para que esperemos la siguiente entrega
|
|
|
|
|
::FileDelete(m_path_to_lock_bin, m_extra_file_flags);
|
|
|
|
|
|
2026-03-26 10:26:25 -05:00
|
|
|
//---
|
|
|
|
|
LogInfo("Nuevo pase recibido de py", FUNCION_ACTUAL);
|
2026-03-21 08:06:31 -05:00
|
|
|
|
2026-03-20 17:16:21 -05:00
|
|
|
//---
|
|
|
|
|
CJson* json = new CJson();
|
|
|
|
|
|
|
|
|
|
//---
|
|
|
|
|
::ResetLastError();
|
2026-03-25 12:58:33 -05:00
|
|
|
const int fh = ::FileOpen(m_path_to_config_json, FILE_READ | FILE_BIN | m_extra_file_flags);
|
2026-03-20 17:16:21 -05:00
|
|
|
if(fh == INVALID_HANDLE)
|
|
|
|
|
{
|
|
|
|
|
LogWarning(::StringFormat("Fallo al abrir el archivo =%s, ultimo error = %d", m_path_to_config_json, ::GetLastError()), FUNCION_ACTUAL);
|
2026-03-26 09:51:33 -05:00
|
|
|
delete json; // Borramos el json
|
2026-03-20 17:16:21 -05:00
|
|
|
return;
|
|
|
|
|
}
|
|
|
|
|
|
2026-03-25 12:58:33 -05:00
|
|
|
//---
|
|
|
|
|
const ulong file_size = FileSize(fh);
|
|
|
|
|
string file_content = ::FileReadString(fh, int(file_size));
|
2026-03-26 15:56:42 -05:00
|
|
|
if(file_content.GetChar(0) == 0xFEFF) // check si el primero es boom
|
|
|
|
|
file_content.SetChar(0, ' ');
|
|
|
|
|
//Print(file_content);
|
2026-03-25 12:58:33 -05:00
|
|
|
|
|
|
|
|
//---
|
|
|
|
|
if(json.Parse(file_content))
|
2026-03-20 17:16:21 -05:00
|
|
|
{
|
|
|
|
|
//---
|
|
|
|
|
::FileClose(fh);
|
|
|
|
|
|
|
|
|
|
//---
|
2026-03-24 10:39:38 -05:00
|
|
|
if(json["finish"].IsValid())
|
2026-03-20 17:16:21 -05:00
|
|
|
{
|
2026-03-24 10:39:38 -05:00
|
|
|
const int res = int(json["finish"].ToInt());
|
2026-03-26 11:52:16 -05:00
|
|
|
if(res != AIDATATASKRUNNNER_TRAINIG_OUT_EXITO) // no es igual a exito hubo un fallo
|
2026-03-24 10:39:38 -05:00
|
|
|
{
|
|
|
|
|
const string str = AiDataTaskRunnerTrainingGetErr(res);
|
2026-03-26 12:50:40 -05:00
|
|
|
LogFatalError(StringFormat("Fallo al ejecutar el py, el EA launcher retonrno valor no igual a 0, valor de finish = %I64d, str = %s", res, str),
|
2026-03-24 10:39:38 -05:00
|
|
|
FUNCION_ACTUAL);
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
2026-03-20 17:16:21 -05:00
|
|
|
OnTrainingFinish();
|
2026-03-21 08:06:31 -05:00
|
|
|
delete json;
|
2026-03-20 17:16:21 -05:00
|
|
|
}
|
|
|
|
|
else
|
|
|
|
|
{
|
|
|
|
|
for(int i = 0; i < m_runer_py_on_pass_size; i++)
|
|
|
|
|
{
|
|
|
|
|
m_runer_py_on_pass[i].OnTrainingNewResult(json);
|
|
|
|
|
}
|
|
|
|
|
// Nota:
|
|
|
|
|
// Se garnatiza que en la otra tab haya un hook que vayue guradadno los json asi que noe s enceiso eliminar esa
|
|
|
|
|
// tab hook se encarga de eso
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
else
|
|
|
|
|
{
|
|
|
|
|
::FileClose(fh);
|
|
|
|
|
LogError(::StringFormat("Fallo al parsear json ultimo error = %s", ::EnumToString(EnumJsonError(json.GetLastError()))), FUNCION_ACTUAL);
|
|
|
|
|
delete json;
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
2026-03-20 10:20:00 -05:00
|
|
|
//---
|
|
|
|
|
#endif // AIDATATASKRUNER_UI_TRAINING_CONFIGTAB_MQH
|
2026-03-24 10:39:38 -05:00
|
|
|
|
|
|
|
|
|
|
|
|
|
//+------------------------------------------------------------------+
|