clusterbox ticksdensity_5978916310816397262.mq5
Сообщите нам, если считаете, что материал размещён без разрешения.
Сообщить о материале
Обращение по товару «clusterbox ticksdensity_5978916310816397262.mq5» отправится на рассмотрение. Укажите контакт для ответа и опишите причину.
О программе
Индикатор отображает гистограмму плотности тиков текущего торгового дня на графике MetaTrader 5. Он собирает данные о каждом тике (цена bid/ask, время) и группирует их по ценовым кластерам, каждый из которых соответствует определённому диапазону цены в пунктах.
Для каждого кластера рассчитывается плотность — отношение количества тиков на уровне к числу баров, в которых цена этот уровень касалась. Результат визуализируется в виде горизонтальных линий на графике, длина которых пропорциональна плотности тиков.
Данные о тиках сохраняются во временные файлы, что позволяет восстановить накопленную статистику после перезапуска терминала. Индикатор также может отображать числовые значения плотности прямо на графике и поддерживает настройку цвета, толщины линий и шрифта.
Индикатор работает только на таймфреймах меньше дневного. При использовании на D1 или выше гистограмма не отображается. При некорректных настройках индикатор прекращает работу и выводит предупреждение.
Настройки программы
| Настройка | Описание |
|---|---|
| i_pointsInBox | Количество пунктов, на которые распространяется один кластер. Определяет высоту ценового интервала для группировки тиков. |
| i_levelColor | Цвет линий гистограммы плотности тиков. |
| i_histWidthInBars | Максимальная ширина гистограммы в барах, определяющая масштаб отображения плотности. |
| i_lineWidth | Толщина линий гистограммы. Допустимые значения задаются перечислением ENUM_LINEWIDTH от наиболее тонкой до наиболее толстой. |
| i_showValues | Определяет, отображаются ли числовые значения плотности тиков в виде текста на графике. |
| i_precision | Число знаков после запятой при отображении значений плотности на графике. |
| i_fontColor | Цвет шрифта значений плотности, отображаемых на графике. |
| i_fontSize | Размер шрифта значений плотности на графике. |
Поиск по коду файла
#property description "Отображение гистограммы плотности тиков текущего дня.\nОписание доступно на сайте AdvanceTools.net в разделе \"Тиковые объемы - Кластерный анализ - Плотность тиков.\""
#property strict
#property indicator_chart_window
#property indicator_buffers 1
struct TickStruct // Структура для записи данных об одном тике
{
datetime time;
double bid;
double ask;
};
enum ENUM_LINEWIDTH // Толщина линий гистограммы
{
LINEWIDTH_NULL, // Наиболее тонкая
LINEWIDTH_ONE, // Тонкая
LINEWIDTH_TWO, // Средняя
LINEWIDTH_THREE, // Толстая
LINEWIDTH_FOUR // Наиболее толстая
};
enum ENUM_YESNO
{
YES, // Да
NO // Нет
};
#define MAX_POINTS_DAY_HEIGHT 20000 // Максимальная высота дня в пунктах - размер массива для хранения количества повторов уровней
input int i_pointsInBox = 10; // Количество пунктов в одном кластере
input color i_levelColor = clrCornflowerBlue; // Цвет гистограммы объемов
input int i_histWidthInBars = 20; // Макс. ширина гистограммы в барах
input ENUM_LINEWIDTH i_lineWidth = LINEWIDTH_THREE; // Толщина линии гистограммы
input ENUM_YESNO i_showValues = YES; // Отображать значения плотности на графике?
input int i_precision = 1; // Точность представления плотности
input color i_fontColor = clrDodgerBlue; // Цвет шрифта
input int i_fontSize = 10; // Размер шрифта
bool g_activate; // Признак успешной инициализации индикатора
int g_levelRepeat[MAX_POINTS_DAY_HEIGHT], // Массив для записи количества повторов уровня. Первый элемент - кол-во тиков на уровне g_minDayPrice,
g_levelsCnt; // Текущее количество уровней в дне
double g_density[MAX_POINTS_DAY_HEIGHT], // Массив для записи значений плотности тиков, индексы которого в точности соответствуют..
g_minDayPrice, // Минимальная цена текущего дня, на которую приходится первый элемент массива количества повторов уровня
g_point;
TickStruct g_ticks[]; // Массив для хранения тиков, поступивших после начала работы индикатора
#define PREFIX "CLSTRBXCNCTR_" // Префикс имени графических объектов, отображаемых индикатором
#define FONT_NAME "MS Sans Serif" // Имя шрифта, которым будут отображаться значения плотности
int OnInit()
{
// код доступен только после оплаты
}
bool IsTuningParametersCorrect()
{
string name = WindowExpertName();
int period = Period();
if (period == 0)
{
Alert(name, ": фатальная ошибка терминала - период 0 минут. Индикатор отключен.");
return (false);
}
g_point = Point;
if (g_point == 0)
{
Alert(name, ": фатальная ошибка терминала - величина пункта равна нулю. Индикатор отключен.");
return (false);
}
if (i_pointsInBox < 1)
{
Alert(name, ": высота кластера должна быть положительным значением. Индикатор отключен.");
return (false);
}
if (i_histWidthInBars < 5)
{
Alert(name, ": максимальная ширина гистограммы не может быть меньше 5-и баров. Индикатор отключен.");
return (false);
}
if (i_precision < 0)
{
Alert(name, ": точность представления значений плотности не может быть отрицательной величиной. Индикатор отключен.");
return (false);
}
return (true);
}
bool IsLoadTempTicks()
{
int hTicksFile = FileOpen(Symbol() + "temp.tks", FILE_BIN | FILE_READ | FILE_SHARE_READ | FILE_SHARE_WRITE);
if (hTicksFile < 1)
return true;
int recSize = (int)(FileSize(hTicksFile) / sizeof(TickStruct));
if (ArrayResize(g_ticks, recSize, 1000) < 0)
{
Alert(WindowExpertName(), ": не удалось распределить память для подкачки данных из временного файла тиков. Индикатор отключен.");
FileClose(hTicksFile);
return false;
}
int i = 0;
while (i < recSize)
{
if (FileReadStruct(hTicksFile, g_ticks[i]) == 0)
{
Alert(WindowExpertName(), ": ошибка чтения данных из временного файла. Индикатор отключен.");
return false;
}
i++;
}
FileClose(hTicksFile);
return true;
}
void OnDeinit(const int reason)
{
if (!IsSavedFile()) // Если ни один из подключенных индикаторов не сохранил данные, то их сохранит текущий индикатор
SaveTempTicks(); // Сохранение данных о тиках, накопленных за текущий период работы индикатора
DeleteAllObjects();
}
bool IsSavedFile()
{
int lastTickIndex = ArraySize(g_ticks) - 1;
if (lastTickIndex < 0) // Ни один тик не был получен. Запись данных не требуется
return true;
int hTicksFile = FileOpen(Symbol() + "temp.tks", FILE_BIN | FILE_READ | FILE_SHARE_READ | FILE_SHARE_WRITE);
if (hTicksFile < 1)
return false;
if (!FileSeek(hTicksFile, -sizeof(TickStruct), SEEK_END))
{
FileClose(hTicksFile);
return false;
}
TickStruct tick;
uint readBytes = FileReadStruct(hTicksFile, tick);
FileClose(hTicksFile);
if (readBytes == 0)
return false;
return tick.time >= g_ticks[lastTickIndex].time; // Дата/время последнего записанного в файле тика больше или равна дате/времени..
}
void SaveTempTicks()
{
int hTicksFile = FileOpen(Symbol() + "temp.tks", FILE_BIN | FILE_READ | FILE_WRITE | FILE_SHARE_READ | FILE_SHARE_WRITE);
if (hTicksFile < 1)
return;
int total = ArraySize(g_ticks), i = 0;
while (i < total)
{
if (FileWriteStruct(hTicksFile, g_ticks[i]) == 0)
{
Print("Ошибка сохранения данных во временный файл...");
return;
}
i++;
}
FileClose(hTicksFile);
}
void DeleteAllObjects()
{
for (int i = ObjectsTotal() - 1; i >= 0; i--)
if (StringSubstr(ObjectName(i), 0, StringLen(PREFIX)) == PREFIX)
ObjectDelete(ObjectName(i));
}
void ShowTrendLine(datetime time1, double price1, datetime time2, int index, string toolTip, color clr)
{
string name = PREFIX + "LINE_" + IntegerToString(time1) + IntegerToString(index);
if (ObjectFind(0, name) < 0)
{
ObjectCreate(0, name, OBJ_TREND, 0, time1, price1, time2, price1);
ObjectSetInteger(0, name, OBJPROP_COLOR, clr);
ObjectSetInteger(0, name, OBJPROP_BACK, true);
ObjectSetInteger(0, name, OBJPROP_WIDTH, (int)i_lineWidth);
ObjectSetInteger(0, name, OBJPROP_RAY, false);
ObjectSetInteger(0, name, OBJPROP_HIDDEN, true);
ObjectSetInteger(0, name, OBJPROP_SELECTABLE, Показано первые 50% кода (символов: 11855)
Открыть по тарифу
Купите тариф с пакетом открытий или войдите, если тариф уже есть. Открытый файл останется в вашем кабинете навсегда.
Разовая покупка файла
На этой странице откроется полный исходный код файла вместо ознакомительного фрагмента.
Зачем нужен email? После подтверждения оплаты файл сохранится в кабинете на этот email. Если аккаунта ещё нет, мы создадим его и пришлём ссылку для задания пароля. Если аккаунт уже есть, покупка добавится в него. Укажите адрес, к которому у вас есть доступ.
Чтобы оформить заказ, введите email и перейдите к оплате.