Files
r_e_c_u_r/display_centre.py
Tim Caldwell 9bdb02a3e9 inital commit
(rough sketch of idea at this point)
2017-08-17 23:41:36 +12:00

313 lines
12 KiB
Python

import logging
import sys
import traceback
import time
import math
from asciimatics.effects import RandomNoise
from asciimatics.event import KeyboardEvent
from asciimatics.exceptions import ResizeScreenError, NextScene
from asciimatics.scene import Scene
from asciimatics.screen import Screen
from asciimatics.widgets import Frame, Layout, Divider, Button, ListBox, Widget, MultiColumnListBox, PopUpDialog, Text, \
Label
import data_centre
import video_centre
VIDEO_DISPLAY_TEXT = 'NOW [{}] {} NEXT [{}] {}'
VIDEO_DISPLAY_BANNER_LIST = ['[','-','-','-','-','-','-','-','-','-','-',']']
VIDEO_DISPLAY_BANNER_TEXT = '{} {} {}'
logger = logging.getLogger('myapp')
hdlr = logging.FileHandler('C:/Users/Tim/PycharmProjects/videoLooper/myapp.log')
formatter = logging.Formatter('%(asctime)s %(levelname)s %(message)s')
hdlr.setFormatter(formatter)
logger.addHandler(hdlr)
logger.setLevel(logging.INFO)
class Display(Frame):
def __init__(self, switch, screen,driver, on_load=None):
super(Display, self).__init__(screen,
screen.height,
screen.width,
on_load=on_load,
title="r_e_c_u_r"
)
self._last_frame = 0
self.popup_message = None
self.video_driver = driver
self.my_frame_update_count = 40
layout_top = Layout([1,1,1])
self.add_layout(layout_top)
self.browser_button = Button("BROWSER", self.do_nothing())
self.browser_button.disabled = True
#self.browser_button.is_tab_stop = False
if switch[0]:
self.browser_button.custom_colour = "focus_button"
self.looper_button = Button("LOOPER", self.do_nothing())
self.looper_button.disabled = True
#self.looper_button.is_tab_stop = False
if switch[1]:
self.looper_button.custom_colour = "focus_button"
self.settings_button = Button("SETTINGS", self.do_nothing())
self.settings_button.disabled = True
#self.advance_button.is_tab_stop = False
if switch[2]:
self.settings_button.custom_colour = "focus_button"
layout_top.add_widget(Divider(), 0)
layout_top.add_widget(Divider(), 1)
layout_top.add_widget(Divider(), 2)
layout_top.add_widget(self.browser_button, 0)
layout_top.add_widget(self.looper_button, 1)
layout_top.add_widget(self.settings_button, 2)
layout_body = Layout([100], fill_frame=False)
self.add_layout(layout_body)
layout_body.add_widget(Divider())
video_display_text, video_banner_text = self.get_text_for_video_display()
self.player_info_label = Label(video_display_text)
self.player_info_banner = Label(video_banner_text)
layout_body.add_widget(self.player_info_banner)
layout_body.add_widget(self.player_info_label)
layout_body.add_widget(Divider())
self.fix()
def do_nothing(self):
return
def get_text_for_video_display(self):
now_bank, now_status, next_bank, next_status, duration, video_length = self.video_driver.get_info_for_video_display()
banner = create_video_display_banner(duration,video_length)
time_been = data_centre.convert_int_to_string_for_display(duration)
time_left = data_centre.convert_int_to_string_for_display(video_length - duration)
logger.info(VIDEO_DISPLAY_BANNER_TEXT.format(time_been,banner,time_left))
return VIDEO_DISPLAY_BANNER_TEXT.format(time_been,banner,time_left),VIDEO_DISPLAY_TEXT.format(now_bank , now_status, next_bank, next_status, duration)
def _update(self, frame_no):
if frame_no - self._last_frame >= self.frame_update_count or self._last_frame == 0:
self._last_frame = frame_no
video_display_text, video_banner_text = self.get_text_for_video_display()
self.player_info_label._text = video_display_text
self.player_info_banner._text = video_banner_text
super(Display, self)._update(frame_no)
@property
def frame_update_count(self):
# Refresh once every 1 seconds by default.
return 20
def get_focus_on_list(self, list):
#return self._layouts[self._focus]
return list.options[list.value][0][0]
def process_event(self, event):
if isinstance(event, KeyboardEvent):
if event.key_code in [ord('n'), ord('N')]:
raise NextScene
return super(Display, self).process_event(event)
class Browser(Display):
def __init__(self, screen, data, driver):
super(Browser, self).__init__([1,0,0],screen,driver, on_load=self._reload_list)
self._data_object = data
layout = Layout([100], fill_frame=True)
self.add_layout(layout)
self._browser_data_view = ScrollingMultiColumnListBox(
Widget.FILL_FRAME,
[50,10],
self._data_object.get_browser_data_for_display(),
titles=['path','bank']
)
layout.add_widget(self._browser_data_view)
self.fix()
def process_event(self, event):
numberMapping = [ord('q'),ord('w'),ord('e'),ord('r'),ord('t'),ord('y'),ord('u'),ord('i'),ord('o'),ord('p') ]
if isinstance(event, KeyboardEvent):
if event.key_code in numberMapping:
focus = self.get_focus_on_list(self._browser_data_view)
is_file, name = data_centre.extract_file_type_and_name_from_browser_format(focus)
if(is_file):
bank_number = numberMapping.index(event.key_code)
data_centre.create_new_bank_mapping(bank_number,name)
self._data_object.rewrite_browser_list()
self._reload_list(self._browser_data_view.value)
if event.key_code in [ord('m')]:
focus = self.get_focus_on_list(self._browser_data_view)
is_file , name = data_centre.extract_file_type_and_name_from_browser_format(focus)
if(is_file):
data_centre.create_new_bank_mapping_in_first_open(name)
self._data_object.rewrite_browser_list()
self._reload_list(self._browser_data_view.value)
else:
self._data_object.update_open_folders(name)
self._data_object.rewrite_browser_list()
self._reload_list(self._browser_data_view.value)
if event.key_code in [ord('c')]:
#self.popup_message = PopUpDialog(self._screen, 'Deleting all banks',['|'])
#self._scene.add_effect()
data_centre.clear_all_banks()
#time.sleep(1)
#self._scene.remove_effect(popup_message)
self._data_object.rewrite_browser_list()
self._reload_list(self._browser_data_view.value)
return super(Browser, self).process_event(event)
# Now pass on to lower levels for normal handling of the event.
def _update(self, frame_no):
logger.info('the BROWSER frame number is {}'.format(frame_no))
super(Browser, self)._update(frame_no)
def _reload_list(self, new_value=None):
self._browser_data_view.options = self._data_object.get_browser_data_for_display()
self._browser_data_view.value = new_value
class Looper(Display):
def __init__(self, screen, data,driver):
super(Looper, self).__init__([0, 1, 0],screen,driver,on_load=self._reload_list,)
self._data_object = data
layout = Layout([100], fill_frame=True)
self.add_layout(layout)
self._bank_data_view = MultiColumnListBox(
Widget.FILL_FRAME,
[10,35,10,10,10],
data_centre.get_all_looper_data_for_display(),
titles=['bank','name','length','start','end'])
layout.add_widget(self._bank_data_view)
self.fix()
def process_event(self, event):
# if isinstance(event, KeyboardEvent):
# if event.key_code in [ord('q'), ord('Q'), Screen.ctrl("c")]:
# raise StopApplication("User quit")
# elif event.key_code in [ord("r"), ord("R")]:
# self._reverse = not self._reverse
# elif event.key_code == ord("<"):
# self._sort = max(0, self._sort - 1)
# elif event.key_code == ord(">"):
# self._sort = min(7, self._sort + 1)
#self._last_frame = 0
# Now pass on to lower levels for normal handling of the event.
return super(Looper, self).process_event(event)
def _reload_list(self, new_value=None):
self._bank_data_view.options = data_centre.get_all_looper_data_for_display()
self._bank_data_view.value = new_value
class Settings(Display):
def __init__(self, screen, data,driver):
super(Settings, self).__init__([0, 0, 1], screen,driver,on_load=self._reload_list)
self._data_object = data
layout = Layout([100], fill_frame=True)
self.add_layout(layout)
self._settings_data_view = MultiColumnListBox(
Widget.FILL_FRAME,
[30, 30],
data_centre.get_all_settings_data_for_display(),
titles=['setting', 'value'])
layout.add_widget(self._settings_data_view)
self.fix()
def _reload_list(self,new_value=None):
self._settings_data_view.options = data_centre.get_all_settings_data_for_display()
self._settings_data_view.value = new_value
def process_event(self, event):
if isinstance(event, KeyboardEvent):
if event.key_code in [ord('m')]:
focus = self.get_focus_on_list(self._settings_data_view)
data_centre.switch_settings(focus)
self._reload_list(self._settings_data_view.value)
return super(Settings, self).process_event(event)
class ScrollingMultiColumnListBox(MultiColumnListBox):
def __init__(self, height, columns, options, titles):
super(ScrollingMultiColumnListBox, self).__init__(height, columns, options, titles)
def process_event(self, event):
if isinstance(event, KeyboardEvent):
if len(self._options) > 0 and event.key_code == Screen.KEY_UP and self._line == 0:
self._line = len(self._options)
elif len(self._options) > 0 and event.key_code == Screen.KEY_DOWN and self._line == len(self._options) - 1:
self._line = -1
super(ScrollingMultiColumnListBox,self).process_event(event)
def inspect_browser_focus(dir_name):
if(dir_name.endswith('|') or dir_name.endswith('/')):
return False , dir_name.lstrip()[:-1]
else:
return True , dir_name.lstrip()
def create_video_display_banner(duration,video_length):
banner_list = ['[','-','-','-','-','-','-','-','-','-','-','-','-','-','-','-','-','-','-','-','-','-','-','-','-','-','-','-','-','-','-','-','-','-','-','-',']']
max = len(banner_list) - 1
if duration <= 0:
banner_list[0] = '<'
elif duration >= video_length:
banner_list[max] = '>'
else:
marker = int(math.floor(float(duration)/float(video_length)*(max-1))+1)
banner_list[marker] = '*'
return ''.join(banner_list)
def demo(screen):
scenes = [Scene([Browser(screen, data,video_driver)], -1),
Scene([Looper(screen, data,video_driver)], -1),
Scene([Settings(screen, data,video_driver)], -1)]
screen.play(scenes)
data = data_centre.data()
video_driver = video_centre.video_driver()
last_scene = None
while True:
try:
Screen.wrapper(demo, catch_interrupt=True)
sys.exit(0)
except ResizeScreenError as e:
last_scene = e.scene
except Exception as e:
logger.error(traceback.format_exc())
logger.error(str(e))
# Logs the error appropriately.