

-- ©2020 by Evgeny Shibaev, а пользуются ВСЕ !!!
-- Таблица, отображающая суммарный объем бидов и асков в стакане, их разницу (DELTA),frfytв процентах рост(падение) инструмента финансового рынка за определенное количество дней
-- Какие инструменты(тикеры) отслеживаем. Таблица пар тикер - площадка
tickers = {["SiZ0"] = "SPBFUT", ["RIZ0"] = "SPBFUT", ["BRZ0"] = "SPBFUT", ["GAZP"] = "TQBR", ["SBER"] = "TQBR", ["YNDX"] = "TQBR"}
-- GZZ0 = "SPBFUT", SRZ0 = "SPBFUT", GMKN = "TQBR", MGNT = "TQBR", SU26207RMFS9 = "TQOB"
sources = {} -- Список источников данных по количеству тикеров
rows = {} -- Список строк в таблице по количеству тикеров
screener = AllocTable() -- Указатель на таблицу
stopped = false -- Остановка скрипта
local max = math.max -- локальная ссылка на math.max
local min = math.min -- локальная ссылка на math.min
TICKER_COLUMN = 0
PRICE_SPREAD_COLUMN = 1
VW_BID_PRICE_COLUMN = 2
VW_BID_PRICE_SPREAD = 3
VW_DELTA_COLUMN = 4
VW_ASK_PRICE_SPREAD = 5
VW_ASK_PRICE_COLUMN = 6
SUM_BID_COLUMN = 7
SUM_ASK_COLUMN = 8
DELTA_COLUMN = 9
-- Функция вызывается перед вызовом main
function OnInit(path)
-- Добавляем столбцы в таблицу
AddColumn(screener, TICKER_COLUMN, "Ticker", true, QTABLE_STRING_TYPE, 15)
AddColumn(screener, PRICE_SPREAD_COLUMN, "Spread Price", true, QTABLE_DOUBLE_TYPE, 12)
AddColumn(screener, VW_BID_PRICE_COLUMN, "VW bid price", true, QTABLE_DOUBLE_TYPE, 15)
AddColumn(screener, VW_BID_PRICE_SPREAD, "VW bid spread", true, QTABLE_DOUBLE_TYPE, 15)
AddColumn(screener, VW_ASK_PRICE_COLUMN, "VW ask price", true, QTABLE_DOUBLE_TYPE, 12)
AddColumn(screener, VW_ASK_PRICE_SPREAD, "VW ask spread", true, QTABLE_DOUBLE_TYPE, 12)
AddColumn(screener, SUM_BID_COLUMN, "Sum BIDS", true, QTABLE_DOUBLE_TYPE, 12)
AddColumn(screener, SUM_ASK_COLUMN, "Sum ASKS", true, QTABLE_DOUBLE_TYPE, 12)
AddColumn(screener, DELTA_COLUMN, "DELTA", true, QTABLE_DOUBLE_TYPE, 12)
AddColumn(screener, VW_DELTA_COLUMN, "VW DELTA", true, QTABLE_DOUBLE_TYPE, 12)
CreateWindow(screener)
-- Даем название таблице
SetWindowCaption(screener, "BID-ASK Screener")
for ticker, board in pairs(tickers) do
--Для каждого тикера определяем строку в таблице и запоминаем ее в rows
rows[ticker] = InsertRow(screener, -1)
--В первом столбце каждой строки будет имя тикера
SetCell(screener, rows[ticker], 0, ticker)
end
end
--Функция вызывается при каждом изменении стакана любого тикера
function OnQuote(board, ticker)
if stopped then return end
local sec = getSecurityInfo(board, ticker)
local afterpoint = sec["scale"] + 1 -- Округляем значения на один знак после запятой больше чем знаков в цене
local avg_format = "%."..afterpoint.."f"
local level2 = getQuoteLevel2(board, ticker) --Получаем стакан
local bid_size, ask_size, best_bid_price, best_ask_price, bid_vwsum, ask_vwsum = 0, 0, 0, 0, 0, 0
-- Проход по бидам
for index, bid in ipairs(level2["bid"]) do
best_bid_price = bid["price"]
bid_size = bid_size + bid["quantity"]
bid_vwsum = bid_vwsum + (bid["quantity"] * bid["price"])
end
-- Проход по аскам
for index, ask in ipairs(level2["offer"]) do
ask_size = ask_size + ask["quantity"]
ask_vwsum = ask_vwsum + (ask["quantity"] * ask["price"])
end
best_ask_price = level2["offer"][1].price
local VW_BidPrice = bid_vwsum/bid_size
local VW_AskPrice = ask_vwsum/ask_size
local VW_BidSpread = best_bid_price - VW_BidPrice
local VW_AskSpread = VW_AskPrice - best_ask_price
local DeltaChange = (bid_size - ask_size) / (bid_size + ask_size) * 100
local SpreadChange = (VW_AskSpread - VW_BidSpread) / (VW_AskSpread + VW_BidSpread) * 100
local wh = RGB(255,255,255)
local gr = RGB(0,128,0)
local rd = RGB(128,0,0)
SetCell(screener, rows[ticker], DELTA_COLUMN, string.format("%d", bid_size - ask_size))
-- Подкрашиваем ячейку соответственно росту(падению) и величины роста(падения)
SetColor(screener, rows[ticker], DELTA_COLUMN, BCellColor(DeltaChange), FCellColor(DeltaChange), BCellColor(DeltaChange), FCellColor(DeltaChange))
SetCell(screener, rows[ticker], SUM_BID_COLUMN, string.format("%d", bid_size))
SetColor(screener, rows[ticker], SUM_BID_COLUMN, wh, gr, wh, gr)
SetCell(screener, rows[ticker], SUM_ASK_COLUMN, string.format("%d", ask_size))
SetColor(screener, rows[ticker], SUM_ASK_COLUMN, wh, rd, wh, rd)
SetCell(screener, rows[ticker], VW_BID_PRICE_SPREAD, string.format(avg_format, VW_BidSpread))
SetColor(screener, rows[ticker], VW_BID_PRICE_SPREAD, wh, gr, wh, gr)
SetCell(screener, rows[ticker], VW_ASK_PRICE_SPREAD, string.format(avg_format, VW_AskSpread))
SetColor(screener, rows[ticker], VW_ASK_PRICE_SPREAD, wh, rd, wh, rd)
SetCell(screener, rows[ticker], VW_DELTA_COLUMN, string.format(avg_format, VW_AskSpread - VW_BidSpread))
SetColor(screener, rows[ticker], VW_DELTA_COLUMN, BCellColor(SpreadChange), FCellColor(SpreadChange), BCellColor(SpreadChange), FCellColor(SpreadChange))
SetCell(screener, rows[ticker], VW_BID_PRICE_COLUMN, string.format(avg_format, VW_BidPrice))
SetColor(screener, rows[ticker], VW_BID_PRICE_COLUMN, wh, gr, wh, gr)
SetCell(screener, rows[ticker], VW_ASK_PRICE_COLUMN, string.format(avg_format, VW_AskPrice))
SetColor(screener, rows[ticker], VW_ASK_PRICE_COLUMN, wh, rd, wh, rd)
SetCell(screener, rows[ticker], PRICE_SPREAD_COLUMN, string.format(avg_format, (best_ask_price+best_bid_price)/2))
end
-- Цвет текста в ячейке. Если рост - то цвет "зеленый", падение - "красный"
function FCellColor(change) if change > 0 then return RGB(0,0,0) else return RGB(0,0,0) end end
-- Маленькая "тепловая карта". Делает фон ячейки более интенсивным, взависимости от процента изменения величины
function BCellColor(change)
bright = math.floor(255 - min(math.abs(change*5), 235),1) --10 110
if change > 0 then return RGB(bright,255,bright) else return RGB(255,bright,bright) end
end
-- Функция вызывается перед остановкой скрипта
function OnStop(signal) stopped = true end
-- Функция вызывается перед закрытием квика
function OnClose() stopped = true end;
-- Основная функция выполнения скрипта
function main()
while not stopped do sleep(1) end
endИли ссылка ScreenerBidAsk.lua
Искренне Ваш!