Форум » Консультации по программированию » Я новичок. » Ответить

Я новичок.

Anatoliy: Пишу пользовательский индикатор на основе пересечение уровни 20 и 80. Если главная линия Stochastic пересекла уровень 80 (сверху - вниз), то выводит стрелка Sell на ценовых графиках, а если главная линия Stochastic пересекла уровень 20 (снизу - верх), то стрелка Buy на ценовых графиках. #property strict #property indicator_chart_window #property indicator_buffers 2 //--- plot Buy #property indicator_type1 DRAW_ARROW #property indicator_color1 clrGreen #property indicator_style1 STYLE_SOLID #property indicator_width1 1 //--- plot Sell #property indicator_type2 DRAW_ARROW #property indicator_color2 clrRed #property indicator_style2 STYLE_SOLID #property indicator_width2 1 //--- input parameters //--- indicator buffers double BuyBuffer[]; double SellBuffer[]; //жжжжжжжжжжжжжжжжжжжжжжжжжжжжжжжжжжжжжжжжжжжжжжжжжжжжжжжжжжжжжжжжжжжж //+------------------------------------------------------------------+ //| Функция инициализации пользовательского индикатора | //+------------------------------------------------------------------+ int init() { //--- SetIndexBuffer(0,BuyBuffer); SetIndexArrow(0,233); SetIndexStyle(0,DRAW_ARROW); //--- SetIndexBuffer(1,SellBuffer); SetIndexArrow(1,234); SetIndexStyle(1,DRAW_ARROW); //--- SetIndexEmptyValue(0,80.0); SetIndexEmptyValue(1,20.0); //--- return(0); } //жжжжжжжжжжжжжжжжжжжжжжжжжжжжжжжжжжжжжжжжжжжжжжжжжжжжжжжжжжжжжжжжжжжж //+------------------------------------------------------------------+ //| Функция пользовательского индикатора итерации | //+------------------------------------------------------------------+ int start() { //--- int i, Counted_bars; double mainStoc_1 = iStochastic(NULL,0,5,3,3,MODE_SMA,0,MODE_MAIN,1); // бар 1 double mainStoc_2 = iStochastic(NULL,0,5,3,3,MODE_SMA,0,MODE_MAIN,2); // бар 2 Counted_bars=IndicatorCounted(); // Количество просчитанных баров i=Bars-Counted_bars-1; for(i=0;i>=0;i--) { if (mainStoc_2 > 80.0 && mainStoc_1 < 80.0) SellBuffer = Low-5*Point; else SellBuffer = 0.0; if (mainStoc_2 < 20.0 && mainStoc_1 > 20.0) BuyBuffer = High+5*Point; else BuyBuffer = 0.0; } //--- return(0); } И в результатах индикатор вообще не работает. Как его исправит?

Ответов - 300, стр: 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 All

Anatoliy: В MQL5 есть минус, т.е. нельзя скрипт присоединить на ценовом графике. Игорь, подскажи мне, где статьи описаны, например, рисует фон на ценовом графике. Я хочу попробовать написать пользовательский индикатор на основе пересечение 2MA, а фон будет рисоваться начала пересечения 2MA, максимум, минимум и конец пересечения 2MA в виде прямоугольника.

Scriptong: Anatoliy пишет: В MQL5 есть минус, т.е. нельзя скрипт присоединить на ценовом графике. Возможно, не совсем понял. Если же в прямом смысле, то в МТ5 можно присоединить скрипт к ценовому графику. Если же речь идет о программном присоединении скрипта к графику, то это также не было доступно и в MQL4 - нет такой функции. Для этого используются недокументированные возможности платформ. В МТ5 можно программно присоединить скрипт косвенно - путем загрузки шаблона. Есть такая функция - ChartApplyTemplate. Перед ее использованием заготавливаете шаблон, в котором уже есть скрипт. Причем, если не хочется изменять текущие настройки графика, то можно и вовсе красиво сделать: 1. Сохранить текущие настройки при помощи ChartSaveTemplate. 2. Внести изменения в сохраненный шаблон, добавив туда скрипт. 3. Загрузить шаблон. Anatoliy пишет: Игорь, подскажи мне, где статьи описаны, например, рисует фон на ценовом графике. Я хочу попробовать написать пользовательский индикатор на основе пересечение 2MA, а фон будет рисоваться начала пересечения 2MA, максимум, минимум и конец пересечения 2MA в виде прямоугольника. Можно взять пример из документации: MQL5 и MQL4. Хотя, по-моему, оба примера одинаковы

Anatoliy: Добрый суток, Игорь. Как создать объект прямоугольник (OBJ_RECTANGLE) с учётом двумя скользящей средней? В справочнике, в форуме с трудом ломаю голову, а как создать OBJ_LABEL для меня уже легко, потому что в учебнике хорошо написано, а вот прямоугольник . Например, зелёный треугольник начинает рисовать когда быстрая МА пересекает медленная МА снизу вверх, а красный треугольник зеркально. Вот, я изобразил рисунок OBJ_RECTANGLE


Scriptong: Прямоугольник создается достаточно простой функцией (она есть во многих моих индикаторах): void ShowRectangle(string name, int windowIndex, datetime time1, double price1, datetime time2, double price2, color clr, string descr, bool back = true) { if (ObjectFind(name) < 0) { ObjectCreate(name, OBJ_RECTANGLE, windowIndex, time1, price1, time2, price2); ObjectSet(name, OBJPROP_COLOR, clr); ObjectSet(name, OBJPROP_BACK, back); ObjectSetText(name, descr); return; } ObjectMove(name, 0, time1, price1); ObjectMove(name, 1, time2, price2); } или на новый лад вот так: void ShowRectangle(string name, int windowIndex, datetime time1, double price1, datetime time2, double price2, color clr, string descr, bool back = true) { if (ObjectFind(name) < 0) { ObjectCreate(0, name, OBJ_RECTANGLE, windowIndex, time1, price1, time2, price2); ObjectSetInteger(0, name, OBJPROP_COLOR, (int)clr); ObjectSetInteger(0, name, OBJPROP_BACK, (int)back); ObjectSetString(0, name, OBJPROP_TEXT, descr); return; } ObjectMove(name, 0, time1, price1); ObjectMove(name, 1, time2, price2); } Как только зарегистрировали пересечение, вызываете функцию, передавая ей нужный цвет прямоугольника. При этом нужно учесть, что последнее пересечение находится в активной фазе, а значит последний прямоугольник нужно не создавать заново, а просто обновлять. Чтобы обновить прямоугольник, нужно вызвать указанную функцию с тем же именем объекта. В результате получаем алгоритм, который в качестве имени объектов должен использовать время пересечения средних. Это позволяет различать прямоугольники между собой, а также не создавать несколько прямоугольников на одно и тоже пересечение.

Anatoliy: Для себя заготовил индикатор с двумя скользящей средней и питаюсь добавит OBJ_RECTANGLE. Я выбрал 1-й вариант Scriptong пишет: void ShowRectangle(string name, int windowIndex, datetime time1, double price1, datetime time2, double price2, color clr, string descr, bool back = true) { if (ObjectFind(name) < 0) { ObjectCreate(name, OBJ_RECTANGLE, windowIndex, time1, price1, time2, price2); ObjectSet(name, OBJPROP_COLOR, clr); ObjectSet(name, OBJPROP_BACK, back); ObjectSetText(name, descr); return; } ObjectMove(name, 0, time1, price1); ObjectMove(name, 1, time2, price2); } Вот текстовой файл ShowRectangle Игорь, посмотрите, это код не правильно, что надо изменит или/и добавит?

Scriptong: Anatoliy пишет: Игорь, посмотрите, это код не правильно, что надо изменит или/и добавит? 1. Вы используете один и тот же прямоугольник. То есть с каждым новым пересечением он перемещается, вместо того, чтобы остаться на месте пересечения. 2. Неправильное написание условия пересечения средних. 3. Время начала и окончания прямоугольника (time1 и time2) одно и то же. В итоге прямоугольник вырождается в вертикальную линию, которую на графике можно и не заметить. Решение Для каждого нового пересечения необходимо изменять имя объекта. Соответственно, для этого нужно запоминать время последнего пересечения, а при формировании прямоугольника указывать разные время начала и окончания объекта: #define PREFIX "CRSMA_" ... datetime lastCrossTime = 0; double lastHigh, lastLow; ... while (i >= 0) { ... if(Buffer_fast_MA_1[i + 1] > Buffer_average_MA_2[i + 1] && Buffer_fast_MA_1[i + 2] < Buffer_average_MA_2[i + 2]) { lastCrossTime = Time[i + 1]; lastHigh = High[ i ]; lastLow = Low[ i ]; ShowRectangle(PREFIX + IntegerToString(lastCrossTime), 0, lastCrossMA, lastHigh, Time[ i ], lastLow, clrLime); } if(Buffer_fast_MA_1[i + 1] < Buffer_average_MA_2[i + 1] && Buffer_fast_MA_1[i + 2] > Buffer_average_MA_2[i + 2]) { lastCrossTime = Time[i + 1]; lastHigh = High[ i ]; lastLow = Low[ i ]; ShowRectangle(PREFIX + IntegerToString(lastCrossTime), 0, lastCrossMA, lastHigh, Time[ i ], lastLow, clrLime); } } Этот код формирует только начальные прямоугольники на пересечениях средних. Нужно еще добавить слежение за развитием ситуации, когда не выполняется ни одно из условий пересечения, чтобы прямоугольники занимали пространство между пересечениями. В этом Вам помогут данные, уже записанные в переменных lastCrossTime, lastHigh и lastLow. Это уже проще. P. S. Представляйте код в файлах формата mq4, а не docx.

Anatoliy: Вот, я вложил исходный файл ObjRectangle_2MA, но он ни чего не изображает, а зато компилятор не ругается.

Scriptong: Anatoliy пишет: но он ни чего не изображает, а зато компилятор не ругается. Еще как ругается Только не компилятор, а интерпретатор: array out of range in 'ObjRectangle_2MA v.1.mq4' (64,29) Первый индекс бара, которым оперирует индикатор в цикле, равен Bars - 1 (значение переменной цикла i). Далее же в коде мы обращаемся к барам (i + 1) и (i + 2), то есть это должны быть бары с индексами Bars и Bars + 1. Но таких баров не существует, т. к. всего на графике количество баров равно Bars, т. е. последний бар имеет индекс Bars - 1. Для этого в цикл нужно передавать значение i, которое является корректным для любых действий в цикле далее: i = MathMin(Bars-Counted_bars-1, Bars - 3); В итоге индикатор будет отображать пересечения средних, помеченных тонкими вертикальными линиями. Чтобы их увидеть, нужно присмотреться - они есть. Эти линии - начало формирования прямоугольников. Если бы Вы последовали моему предыдущему совету в точности (установили бы lastCrossTime = Time[i + 1], а не Time[ i ]), то увидели бы именно прямоугольники. Ну а чтобы прямоугольники указывали всю область пересечения, нужно еще доработать код (см. советы в моем предыдущем сообщении). Для этого в нем уже почти все предусмотрено. P. S. ну и не забудьте, что прямоугольники Вы хотели видеть закрашенными. Для этого последний параметр при вызове функций ShowRectangle должен быть true, а не false.

Anatoliy: Scriptong пишет: Еще как ругается Только не компилятор, а интерпретатор: Т.е. нажать клавиш не F7, а на F5!!! Все что нужно я исправил ObjRectangle_2MA, но кое-что доработать. Scriptong пишет: Ну а чтобы прямоугольники указывали всю область пересечения, нужно еще доработать код (см. советы в моем предыдущем сообщении). Для этого в нем уже почти все предусмотрено. Советы в твоем предыдущем сообщении есть еще одна переменная lastCrossMA? По моему, надо добавит еще один цикл для подсчет от пересечения до пересечения

Scriptong: Anatoliy пишет: Т.е. нажать клавиш не F7, а на F5!!! Я имел в виду, что нужно смотреть содержимое вкладки "Эксперт" окна "Терминал" после запуска индикатора. Это уже работает интерпретатор. Anatoliy пишет: По моему, надо добавит еще один цикл для подсчет от пересечения до пересечения Нет, не нужно. Я же писал: Нужно еще добавить слежение за развитием ситуации, когда не выполняется ни одно из условий пересечения, чтобы прямоугольники занимали пространство между пересечениями. То есть дело всего в одном условии, которое выполняется в тех случах, когда не выполняются условия пересечения.

Anatoliy: Вот скринщот после изменения GBPUSDH1, NZDUSDH1, Я продолжаю дорабатывать, ещё нужно найти высоту прямоугольника в отрезке (от пересечения до пересечения 2МА), т.е. найти в отрезке самый максимальный бар и самый минимальный бар. Копался, били варианты той-иной не дали результаты. Как найти в отрезке максимальный бар и самый минимальный бар? С помощью функцию ArrayMaximum() и ArrayMinimum()???

Scriptong: Anatoliy пишет: Вот скринщот после изменения GBPUSDH1, NZDUSDH1, Вы рисуете несколько прямоугольников на интервале пересечения. Нужно же просто модифицировать один последний. Его начальное время формирования мы уже записали в lastCrossTime. Это его уникальный идентификатор. Anatoliy пишет: Как найти в отрезке максимальный бар и самый минимальный бар? Для этого уже предусмотрены переменные lastHigh и lastLow. Их нужно лишь обновлять на каждом баре.

Anatoliy: У меня не получается, вот скрин EURUSDM1, сюда я добавил iHighest() и iLowest() получилось такой вид. Как правильно чтоб прямоугольники били???

Scriptong: Anatoliy пишет: У меня не получается, вот скрин EURUSDM1, сюда я добавил iHighest() и iLowest() получилось такой вид. Как правильно чтоб прямоугольники били??? По всей видимости, прямоугольники Вы не обновляете, создавая новые. Покажите код, пожалуйста.

Anatoliy: ObjRectangle_2MA



полная версия страницы