From e623c5875430a38c8ceede68a2d6dc54dd0e62a3 Mon Sep 17 00:00:00 2001 From: Tyler Goodlet Date: Sat, 22 May 2021 11:40:54 -0400 Subject: [PATCH 1/2] Naively throttle graphics updates to 60 FPS --- piker/ui/_chart.py | 29 +++++++++++++++++++++++++++-- 1 file changed, 27 insertions(+), 2 deletions(-) diff --git a/piker/ui/_chart.py b/piker/ui/_chart.py index 0650663c..ea1544fa 100644 --- a/piker/ui/_chart.py +++ b/piker/ui/_chart.py @@ -18,6 +18,7 @@ High level Qt chart widgets. """ +import time from typing import Tuple, Dict, Any, Optional, Callable from types import ModuleType from functools import partial @@ -934,7 +935,9 @@ async def test_bed( # txt.setPos(vb_right - w, d_coords.y()) # txt.setPlainText(f"FUCK YOU {i}") i += 1 - # rlabel.setPos(vb_right - 2*w, d_coords.y()) + + +_quote_throttle_rate = 60 # Hz async def chart_from_quotes( @@ -1011,9 +1014,17 @@ async def chart_from_quotes( tick_size = chart._lc.symbol.tick_size tick_margin = 2 * tick_size + last = time.time() async for quotes in stream: - for sym, quote in quotes.items(): + now = time.time() + period = now - last + if period <= 1/_quote_throttle_rate: + # faster then display refresh rate + # print(f'quote too fast: {1/period}') + continue + + for sym, quote in quotes.items(): for tick in quote.get('ticks', ()): # print(f"CHART: {quote['symbol']}: {tick}") @@ -1099,6 +1110,8 @@ async def chart_from_quotes( last_mx, last_mn = mx, mn + last = now + async def spawn_fsps( linked_charts: LinkedSplitCharts, @@ -1272,9 +1285,19 @@ async def run_fsp( stream = conf['stream'] + last = time.time() + # update chart graphics async for value in stream: + now = time.time() + period = now - last + # if period <= 1/30: + if period <= 1/_quote_throttle_rate: + # faster then display refresh rate + # print(f'quote too fast: {1/period}') + continue + # TODO: provide a read sync mechanism to avoid this polling. # the underlying issue is that a backfill and subsequent shm # array first/last index update could result in an empty array @@ -1299,6 +1322,8 @@ async def run_fsp( # update graphics chart.update_curve_from_array(fsp_func_name, array) + last = now + async def check_for_new_bars(feed, ohlcv, linked_charts): """Task which updates from new bars in the shared ohlcv buffer every From 9e367432fd546138ea4e8187599832ded14633e9 Mon Sep 17 00:00:00 2001 From: Tyler Goodlet Date: Tue, 25 May 2021 06:56:18 -0400 Subject: [PATCH 2/2] Minimize update to Qt reported display's refresh rate --- piker/ui/_chart.py | 24 +++++++++++++++++++----- 1 file changed, 19 insertions(+), 5 deletions(-) diff --git a/piker/ui/_chart.py b/piker/ui/_chart.py index ea1544fa..9f6e118b 100644 --- a/piker/ui/_chart.py +++ b/piker/ui/_chart.py @@ -937,7 +937,7 @@ async def test_bed( i += 1 -_quote_throttle_rate = 60 # Hz +_quote_throttle_rate: int = 60 # Hz async def chart_from_quotes( @@ -1019,7 +1019,7 @@ async def chart_from_quotes( now = time.time() period = now - last - if period <= 1/_quote_throttle_rate: + if period <= 1/_quote_throttle_rate - 0.001: # faster then display refresh rate # print(f'quote too fast: {1/period}') continue @@ -1110,7 +1110,8 @@ async def chart_from_quotes( last_mx, last_mn = mx, mn - last = now + # set time of last graphics update + last = now async def spawn_fsps( @@ -1293,7 +1294,7 @@ async def run_fsp( now = time.time() period = now - last # if period <= 1/30: - if period <= 1/_quote_throttle_rate: + if period <= 1/_quote_throttle_rate - 0.001: # faster then display refresh rate # print(f'quote too fast: {1/period}') continue @@ -1322,6 +1323,7 @@ async def run_fsp( # update graphics chart.update_curve_from_array(fsp_func_name, array) + # set time of last graphics update last = now @@ -1531,10 +1533,22 @@ async def _async_main( Provision the "main" widget with initial symbol data and root nursery. """ + chart_app = widgets['main'] # attempt to configure DPI aware font size - _font.configure_to_dpi(current_screen()) + screen = current_screen() + + # configure graphics update throttling based on display refresh rate + global _quote_throttle_rate + _quote_throttle_rate = min( + round(screen.refreshRate()), + _quote_throttle_rate, + ) + log.info(f'Set graphics update rate to {_quote_throttle_rate} Hz') + + # configure global DPI aware font size + _font.configure_to_dpi(screen) async with trio.open_nursery() as root_n: