Вы упускаете торговые возможности:
- Бесплатные приложения для трейдинга
- 8 000+ сигналов для копирования
- Экономические новости для анализа финансовых рынков
Регистрация
Вход
Вы принимаете политику сайта и условия использования
Если у вас нет учетной записи, зарегистрируйтесь
Вы не разобрались в проблеме совершенно. Никто ничего специально не мудрит, а использует штатный способ - на текущем графике размещается эксперт, который под свои нужны создает индикатор - ВСЁ. После этого пользователь переключает таймфрейм и получает задвоенные подокна индикаторов - одно нормальное, второе "зомби" - либо с полным дубликатом параметров первого индикатора (что не может быть в МТ5 по определению - это баг), либо с непроинициализированным именем, то есть без сработавшего OnInit.
В приложенных исходниках MQL5 инициализация и деинициализация производятся по лучшим стандартам. Потрудились бы изучить что ли тестовый пример, прежде чем писать лабуду.
Что происходит при изменении параметров приатаченного индикатора (ТФ - один из неявных параметров индикатора), доподлинно известно и постоянно - старая копия удаляется, а новая создается, и это видно даже в прилагаемых логах - там выведены все хендлы.
но у меня работает, у вас нет...наверное потому-что я не разбираюсь
Да, расчетная часть. Но может что-то изменилось и внешне - книга-то 3 года назад писалась.
Поэкспериментировал с ручным размещением индикаторов.
В Indicator_01__1 в OnTick() добавил в стоку вывод мэджика createdByEA
Если кидать вручную и задавать одинаковый мэджик, то имеем несколько дублирующих визуализаций индикатора в подокнах, но расчетная часть принтуется одна (общая),
если кинуть с разными меджиками, то будут принтоваться две разные расчетные части (логично, т.к. параметры индикаторов теперь отличаются из-за меджиков).
А что происходит при работе из эксперта я до конца не понимаю, у меня ощущение, что там все-таки несколько багов:
1. При смене ТФ у индикатора, еще до вызова его OnDeinit, теряется заданный ранее shortname (т.к. моя процедура indicatorsEnumeration из OnDeinit() эксперта выдает имя файла индикатора, хотя перед сменой ТФ она печатала заданное имя)
2. То о чём вы написали в логах - терминал не должен был создавать дубликаты. (Хотя старая расчетная часть не была удалена т.к. индикатор с графика не был удален из-за бага 1.)
Может есть смысл написать куда-то разработчикам?
но у меня работает, у вас нет...наверное потому-что я не разбираюсь
Если речь про приложенный тесткейс - то ошибка возникает не всегда, а после многократных переключений ТФ. Условия и предполагаемые причины возникновения я описал.
Если у вас свой тесткейс (связка эксперт+пользовательский индикатор), то без исходника обсуждать, что и как там работает - невозможно.
А что происходит при работе из эксперта я до конца не понимаю, у меня ощущение, что там все-таки несколько багов:
1. При смене ТФ у индикатора, еще до вызова его OnDeinit, теряется заданный ранее shortname (т.к. моя процедура indicatorsEnumeration из OnDeinit() эксперта выдает имя файла индикатора, хотя перед сменой ТФ она печатала заданное имя)
2. То о чём вы написали в логах - терминал не должен был создавать дубликаты. (Хотя старая расчетная часть не была удалена т.к. индикатор с графика не был удален из-за бага 1.)
Может есть смысл написать куда-то разработчикам?
По п.1 возможно следует иметь в виду, что эксперт не перегружается, а остается на графике, хотя для него последовательно вызываются OnDeinit и OnInit, а вот индикаторы - старый удаляется, а новый создается - причем последовательность вызовов OnDeinit у старого и OnInit в новом может быть произвольной.
По п.2 продублировал сообщение в топике про релиз, куда обычно сообщают об ошибках.
но у меня работает, у вас нет...наверное потому-что я не разбираюсь
100%!
Ну чтож, я сделал попытку достучаться до вас. Вы ни один пример у себя не запустили.
Философия об очевидных принципах программирования, вроде конструкторов и деструкторов, мне никак не поможет - эти вещи давно понятны и без вас.
Придется сделать костыль "минимального размера", лаконичный и "стильный" и, возможно, поделиться им с сообществом.
Может есть смысл написать куда-то разработчикам?
Я подтверждаю наличие проблемы с функцией ChartIndicatorDelete() и сообщил о ней в MQ.
Я подтверждаю наличие проблемы с функцией ChartIndicatorDelete() и сообщил о ней в MQ.
Публикую костыль, который у меня работает надежно! :)
Суть метода:
1. При инициализации пользовательских индикаторов в их input параметр передаем ключевое слово Expert_ID_Name, общее для всех пользовательских индикаторов, создаваемых данным советником. Это слово можно, но не обязательно, использовать для формирования shortname индикатора.
2. В OnDeinit() советника используем общую функцию MyIndicatorsDelete(const string name), где в name передаем Expert_ID_Name.
Данная функция делает следующее:
2.1 В обратном порядке перебирает все окна графика.
2.2 В обратном порядке перебирает все индикаторы на каждом из окон.
2.3 Получает структуру параметров каждого индикатора и анализирует строковые параметры на наличие в них ключевого слова name = Expert_ID_Name.
2.4 При наличии совпадения индикатор считается "своим" и предпринимается попытка его удаления с графика. Если попытка неудачна (из-за багов терминала), то взводится признак problem = true;
2.5 После перебора всех индикаторов по п.2.1-2.4 если problem = true, то весь цикл начинается сначала после паузы в 0.1 секунды.
Максимальное кол-во повторных попыток задано 100 шт., но у меня всё срабатывало без проблем максимум со второй попытки.
3. После функции удаления индикаторов с окон графика вызываем IndicatorHandleRelease(int &handle) последовательно для всех хэндлов индикаторов.
Таким образом я отвязался от shortname индикатора, т.к. он сбрасывается сразу после изменения TF и ключевое слово в нем не обнаруживается какое-то время.
Вместо этого я ищу ключевое слово непосредственно в параметрах индикатора, которые стабильны.
Поскольку ChartIndicatorDelete() по тем или иным причинам может не сработать с первого раза - предпринимаются новые попытки после короткой задержки в 100мс.
Функцию MyIndicatorsDelete(const string name) я у себя продублировал и в OnInit() советника, т.к. при нештатном выключении терминала (например при отключении света), OnDeinit() не выполнится и нужно будет "почистить" индикаторы при новом старте советника.
P.S. Перебор окон и индикаторов и их удаление нужно обязательно проводить в обратном порядке, т.к. при удалении индикатора и его окна нумерация изменяется и при прямом порядке обнаружение индикаторов ломается.