Update L1 labels in price loop
parent
73e54a2259
commit
f438139ad7
|
@ -19,6 +19,7 @@ from ._graphics import (
|
||||||
ContentsLabel,
|
ContentsLabel,
|
||||||
BarItems,
|
BarItems,
|
||||||
level_line,
|
level_line,
|
||||||
|
L1Labels,
|
||||||
)
|
)
|
||||||
from ._axes import YSticky
|
from ._axes import YSticky
|
||||||
from ._style import (
|
from ._style import (
|
||||||
|
@ -504,7 +505,7 @@ class ChartPlotWidget(pg.PlotWidget):
|
||||||
|
|
||||||
# TODO: something instead of stickies for overlays
|
# TODO: something instead of stickies for overlays
|
||||||
# (we need something that avoids clutter on x-axis).
|
# (we need something that avoids clutter on x-axis).
|
||||||
self._add_sticky(name)
|
self._add_sticky(name, bg_color='default_light')
|
||||||
|
|
||||||
label = ContentsLabel(chart=self, anchor_at=anchor_at)
|
label = ContentsLabel(chart=self, anchor_at=anchor_at)
|
||||||
self._labels[name] = (label, partial(label.update_from_value, name))
|
self._labels[name] = (label, partial(label.update_from_value, name))
|
||||||
|
@ -519,6 +520,7 @@ class ChartPlotWidget(pg.PlotWidget):
|
||||||
def _add_sticky(
|
def _add_sticky(
|
||||||
self,
|
self,
|
||||||
name: str,
|
name: str,
|
||||||
|
bg_color='bracket',
|
||||||
# retreive: Callable[None, np.ndarray],
|
# retreive: Callable[None, np.ndarray],
|
||||||
) -> YSticky:
|
) -> YSticky:
|
||||||
# add y-axis "last" value label
|
# add y-axis "last" value label
|
||||||
|
@ -528,6 +530,7 @@ class ChartPlotWidget(pg.PlotWidget):
|
||||||
# TODO: pass this from symbol data
|
# TODO: pass this from symbol data
|
||||||
# digits=0,
|
# digits=0,
|
||||||
opacity=1,
|
opacity=1,
|
||||||
|
bg_color=bg_color,
|
||||||
)
|
)
|
||||||
return last
|
return last
|
||||||
|
|
||||||
|
@ -801,41 +804,69 @@ async def chart_from_quotes(
|
||||||
last_bars_range, last_mx, last_mn = maxmin()
|
last_bars_range, last_mx, last_mn = maxmin()
|
||||||
|
|
||||||
chart.default_view()
|
chart.default_view()
|
||||||
|
l1 = L1Labels(chart)
|
||||||
|
|
||||||
|
last_bid = last_ask = ohlcv.array[-1]['close']
|
||||||
|
|
||||||
async for quotes in stream:
|
async for quotes in stream:
|
||||||
for sym, quote in quotes.items():
|
for sym, quote in quotes.items():
|
||||||
for tick in iterticks(quote, type='trade'):
|
for tick in quote.get('ticks', ()):
|
||||||
array = ohlcv.array
|
# for tick in iterticks(quote, type='trade'):
|
||||||
|
|
||||||
# update price sticky(s)
|
ticktype = tick.get('type')
|
||||||
last = array[-1]
|
price = tick.get('price')
|
||||||
last_price_sticky.update_from_data(*last[['index', 'close']])
|
|
||||||
|
|
||||||
# update price bar
|
if ticktype in ('trade', 'utrade'):
|
||||||
chart.update_ohlc_from_array(
|
array = ohlcv.array
|
||||||
chart.name,
|
|
||||||
array,
|
|
||||||
)
|
|
||||||
|
|
||||||
# TODO: we need a streaming minmax algorithm here to
|
# update price sticky(s)
|
||||||
brange, mx, mn = maxmin()
|
last = array[-1]
|
||||||
if brange != last_bars_range:
|
last_price_sticky.update_from_data(*last[['index', 'close']])
|
||||||
if mx > last_mx or mn < last_mn:
|
|
||||||
# avoid running this every cycle.
|
|
||||||
chart._set_yrange()
|
|
||||||
|
|
||||||
# save for next cycle
|
# update price bar
|
||||||
last_mx, last_mn = mx, mn
|
chart.update_ohlc_from_array(
|
||||||
|
chart.name,
|
||||||
|
array,
|
||||||
|
)
|
||||||
|
|
||||||
if vwap_in_history:
|
# TODO: we need a streaming minmax algorithm here to
|
||||||
# update vwap overlay line
|
brange, mx, mn = maxmin()
|
||||||
chart.update_curve_from_array('vwap', ohlcv.array)
|
if brange != last_bars_range:
|
||||||
|
if mx > last_mx or mn < last_mn:
|
||||||
|
# avoid running this every cycle.
|
||||||
|
chart._set_yrange()
|
||||||
|
|
||||||
# TODO:
|
# save for next cycle
|
||||||
# - eventually we'll want to update bid/ask labels and
|
last_mx, last_mn = mx, mn
|
||||||
# other data as subscribed by underlying UI consumers.
|
|
||||||
# - in theory we should be able to read buffer data
|
if vwap_in_history:
|
||||||
# faster then msgs arrive.. needs some tinkering and testing
|
# update vwap overlay line
|
||||||
|
chart.update_curve_from_array('vwap', ohlcv.array)
|
||||||
|
|
||||||
|
# TODO:
|
||||||
|
# - eventually we'll want to update bid/ask labels and
|
||||||
|
# other data as subscribed by underlying UI consumers.
|
||||||
|
# - in theory we should be able to read buffer data
|
||||||
|
# faster then msgs arrive.. needs some tinkering and testing
|
||||||
|
|
||||||
|
# if trade volume jumps above / below prior L1 price
|
||||||
|
# levels adjust bid / ask lines to match
|
||||||
|
if price > last_ask:
|
||||||
|
l1.ask_label.update_from_data(0, price)
|
||||||
|
last_ask = price
|
||||||
|
|
||||||
|
elif price < last_bid:
|
||||||
|
l1.bid_label.update_from_data(0, price)
|
||||||
|
last_bid = price
|
||||||
|
|
||||||
|
|
||||||
|
elif ticktype == 'ask':
|
||||||
|
l1.ask_label.update_from_data(0, price)
|
||||||
|
last_ask = price
|
||||||
|
|
||||||
|
elif ticktype == 'bid':
|
||||||
|
l1.bid_label.update_from_data(0, price)
|
||||||
|
last_bid = price
|
||||||
|
|
||||||
|
|
||||||
async def chart_from_fsp(
|
async def chart_from_fsp(
|
||||||
|
@ -931,7 +962,7 @@ async def chart_from_fsp(
|
||||||
|
|
||||||
# add moveable over-[sold/bought] lines
|
# add moveable over-[sold/bought] lines
|
||||||
level_line(chart, 30)
|
level_line(chart, 30)
|
||||||
level_line(chart, 70)
|
level_line(chart, 70, orient_v='top')
|
||||||
|
|
||||||
chart._shm = shm
|
chart._shm = shm
|
||||||
chart._set_yrange()
|
chart._set_yrange()
|
||||||
|
|
Loading…
Reference in New Issue