mirror of
https://github.com/cyberboy666/r_e_c_u_r.git
synced 2025-12-05 16:00:06 +01:00
40
actions.py
40
actions.py
@@ -1,20 +1,20 @@
|
||||
import subprocess
|
||||
import tracemalloc
|
||||
import data_centre.length_setter as length_setter
|
||||
from inspect import signature
|
||||
import sys
|
||||
import shlex
|
||||
import argparse
|
||||
import os
|
||||
import re
|
||||
from pythonosc import osc_message_builder
|
||||
import subprocess
|
||||
import sys
|
||||
import threading
|
||||
from inspect import signature
|
||||
|
||||
import git
|
||||
from pythonosc import dispatcher
|
||||
from pythonosc import osc_server
|
||||
import git
|
||||
import threading
|
||||
import argparse
|
||||
|
||||
import data_centre.length_setter as length_setter
|
||||
from video_centre.capture import Capture
|
||||
from video_centre.of_capture import OfCapture
|
||||
|
||||
|
||||
class Actions(object):
|
||||
def __init__(self, tk, message_handler, data, video_driver, shaders, display, osc_client):
|
||||
self.tk = tk
|
||||
@@ -54,7 +54,6 @@ class Actions(object):
|
||||
def move_browser_selection_page_up(self):
|
||||
self.display.browser_menu.navigate_menu_page_up()
|
||||
|
||||
|
||||
def enter_on_browser_selection(self):
|
||||
self.display.browser_menu.enter_on_browser_selection()
|
||||
|
||||
@@ -70,7 +69,6 @@ class Actions(object):
|
||||
def move_settings_selection_page_up(self):
|
||||
self.display.settings_menu.navigate_menu_page_up()
|
||||
|
||||
|
||||
def enter_on_settings_selection(self):
|
||||
is_setting, setting = self.display.settings_menu.enter_on_setting_selection()
|
||||
if is_setting:
|
||||
@@ -92,7 +90,6 @@ class Actions(object):
|
||||
def move_shaders_selection_page_up(self):
|
||||
self.shaders.shaders_menu.navigate_menu_page_up()
|
||||
|
||||
|
||||
def enter_on_shaders_selection(self):
|
||||
##want to select shader if its not selected, and want to enter 'param' mode if it already is
|
||||
is_shader, is_selected_shader, selected_shader = self.shaders.enter_on_shaders_selection()
|
||||
@@ -135,8 +132,6 @@ class Actions(object):
|
||||
if self.data.update_next_slot_number(slot, is_current=True):
|
||||
self.video_driver.reload_current_player()
|
||||
|
||||
|
||||
|
||||
def load_slot_0_into_next_player(self):
|
||||
self._load_this_slot_into_next_player(0)
|
||||
|
||||
@@ -207,7 +202,6 @@ class Actions(object):
|
||||
self.data.display_mode = display_modes[next_mode_index][0]
|
||||
self.data.control_mode = display_modes[next_mode_index][1]
|
||||
|
||||
|
||||
def toggle_action_on_player(self):
|
||||
play = 'play' in self.data.settings['sampler']['ON_ACTION']['value']
|
||||
show = 'show' in self.data.settings['sampler']['ON_ACTION']['value']
|
||||
@@ -234,14 +228,12 @@ class Actions(object):
|
||||
self.data.update_setting_value('sampler', 'SEEK_TIME', options[(current_index + 1) % len(options)])
|
||||
self.message_handler.set_message('INFO', 'The Seek Time is now ' + str(self.data.settings['sampler']['SEEK_TIME']['value']) + 's')
|
||||
|
||||
|
||||
def decrease_seek_time(self):
|
||||
options = self.data.settings['sampler']['SEEK_TIME']['options']
|
||||
current_index = [index for index, item in enumerate(options) if item == self.data.settings['sampler']['SEEK_TIME']['value']][0]
|
||||
self.data.update_setting_value('sampler', 'SEEK_TIME', options[(current_index - 1) % len(options)])
|
||||
self.message_handler.set_message('INFO', 'The Seek Time is now ' + str(self.data.settings['sampler']['SEEK_TIME']['value']) + 's')
|
||||
|
||||
|
||||
def seek_forward_on_player(self):
|
||||
self.video_driver.current_player.seek(self.data.settings['sampler']['SEEK_TIME']['value'])
|
||||
|
||||
@@ -312,7 +304,6 @@ class Actions(object):
|
||||
# if is_successful and self.video_driver.current_player.status != 'PAUSED':
|
||||
# self.video_driver.current_player.toggle_pause()
|
||||
|
||||
|
||||
def toggle_capture_recording(self):
|
||||
is_recording = self.capture.is_recording
|
||||
if is_recording:
|
||||
@@ -480,7 +471,6 @@ class Actions(object):
|
||||
self.data.detour_settings['current_detour'] = number
|
||||
self.video_driver.osc_client.send_message("/detour/switch_to_detour_number", number)
|
||||
|
||||
|
||||
def set_detour_delay_mode(self, state):
|
||||
self.video_driver.osc_client.send_message("/detour/set_delay_mode", state == 'enabled')
|
||||
self.data.update_conjur_delay_mode(state == 'enabled')
|
||||
@@ -634,7 +624,6 @@ class Actions(object):
|
||||
|
||||
self.change_hdmi_settings('CEA 4 HDMI')
|
||||
|
||||
|
||||
def check_dev_mode(self):
|
||||
#### check if in dev mode:(ie not using the lcd screen)
|
||||
with open('/boot/config.txt', 'r') as config:
|
||||
@@ -686,7 +675,6 @@ class Actions(object):
|
||||
self.refresh_frame_buffer_and_restart_openframeworks()
|
||||
self.persist_composite_setting(mode, progressive, aspect)
|
||||
|
||||
|
||||
def _refresh_frame_buffer(self):
|
||||
self.data.open_omxplayer_for_reset()
|
||||
subprocess.run(["fbset -depth 16; fbset -depth 32; xrefresh -display :0"], shell=True)
|
||||
@@ -734,7 +722,6 @@ class Actions(object):
|
||||
else:
|
||||
self.message_handler.set_message('INFO', 'failed to switch display')
|
||||
|
||||
|
||||
def switch_display_to_lcd(self):
|
||||
with open('/boot/config.txt', 'r') as config:
|
||||
with open('/usr/share/X11/xorg.conf.d/99-fbturbo.conf') as framebuffer_conf:
|
||||
@@ -756,7 +743,6 @@ class Actions(object):
|
||||
subprocess.call(['xset', 'r', 'on'])
|
||||
self.data.auto_repeat_on = True
|
||||
|
||||
|
||||
def quit_the_program(self):
|
||||
self.data._update_json(self.data.SETTINGS_JSON, self.data.settings)
|
||||
self.data.plugins.quit_plugins()
|
||||
@@ -808,7 +794,6 @@ class Actions(object):
|
||||
self.message_handler.set_message('INFO', 'tap: ■ ; < > : back')
|
||||
self.fixed_length_setter = length_setter.FixedLengthSetter(self.data)
|
||||
|
||||
|
||||
def return_to_default_control_mode(self):
|
||||
display_list = self.data.get_display_modes_list(with_nav_mode=True)
|
||||
for display, control in display_list:
|
||||
@@ -843,7 +828,6 @@ class Actions(object):
|
||||
self.fixed_length_setter.record_input()
|
||||
self.display.settings_menu.generate_settings_list()
|
||||
|
||||
|
||||
def setup_osc_server(self):
|
||||
server_parser = argparse.ArgumentParser()
|
||||
server_parser.add_argument("--ip", default="127.0.0.1", help="the ip")
|
||||
@@ -914,7 +898,6 @@ class Actions(object):
|
||||
def enable_osc(self, osc_setting_state):
|
||||
self.data.update_setting_value('user_input', 'OSC_INPUT', osc_setting_state)
|
||||
|
||||
|
||||
def show_ip(self, *args):
|
||||
address = self.data.get_ip_address()
|
||||
self.message_handler.set_message('INFO', 'ip is {}:8080'.format(address))
|
||||
@@ -929,7 +912,6 @@ class Actions(object):
|
||||
self.serial_port_process.kill()
|
||||
self.serial_port_process = None
|
||||
|
||||
|
||||
def stop_remote_process(self):
|
||||
if self.remote_process is not None:
|
||||
self.remote_process.kill()
|
||||
@@ -1019,7 +1001,6 @@ class Actions(object):
|
||||
subprocess.call(['sudo', 'eject', '/dev/sda{}'.format(i)])
|
||||
self.message_handler.set_message('INFO', 'usb ejected')
|
||||
|
||||
|
||||
# TODO: make this interrogate the various components for available routes to parse
|
||||
# this would include eg a custom script module..
|
||||
@property
|
||||
@@ -1114,4 +1095,3 @@ class Actions(object):
|
||||
print("Exception calling action for '%s' with arguments ( %s ) " % (method_name, arguments))
|
||||
import traceback
|
||||
traceback.print_exc()
|
||||
|
||||
|
||||
@@ -1,17 +1,17 @@
|
||||
import subprocess
|
||||
import json
|
||||
import xml.etree.ElementTree as ET
|
||||
import os
|
||||
import collections
|
||||
from random import randint
|
||||
import inspect
|
||||
from itertools import cycle
|
||||
from omxplayer.player import OMXPlayer
|
||||
from shutil import copyfile
|
||||
import json
|
||||
import os
|
||||
import subprocess
|
||||
import threading
|
||||
import xml.etree.ElementTree as ET
|
||||
from random import randint
|
||||
from shutil import copyfile
|
||||
|
||||
from omxplayer.player import OMXPlayer
|
||||
|
||||
from data_centre import plugin_collection
|
||||
|
||||
|
||||
class AsyncWrite(threading.Thread):
|
||||
def __init__(self, filename, data, mode='json'):
|
||||
threading.Thread.__init__(self)
|
||||
@@ -29,7 +29,6 @@ class AsyncWrite(threading.Thread):
|
||||
|
||||
|
||||
class Data(object):
|
||||
|
||||
BANK_DATA_JSON = 'display_data.json'
|
||||
SHADER_BANK_DATA_JSON = 'shader_bank_data.json'
|
||||
SETTINGS_JSON = 'settings.json'
|
||||
@@ -274,7 +273,6 @@ class Data(object):
|
||||
|
||||
######## setting and adding to shader mapping
|
||||
|
||||
|
||||
def create_new_shader_mapping_in_first_open(self, file_name):
|
||||
######## used for mapping current shader to next available slot ########
|
||||
for index, slot in enumerate(self.shader_bank_data[self.shader_layer]):
|
||||
@@ -297,8 +295,6 @@ class Data(object):
|
||||
def update_shader_layer_by_amount(self, amount):
|
||||
self.shader_layer = (self.shader_layer + amount) % len(self.shader_bank_data)
|
||||
|
||||
|
||||
|
||||
def update_setting_value(self, setting_folder, setting_name, setting_value):
|
||||
self.settings[setting_folder][setting_name]['value'] = setting_value
|
||||
self._update_json(self.SETTINGS_JSON, self.settings)
|
||||
@@ -424,7 +420,6 @@ class Data(object):
|
||||
self.message_handler.set_message('INFO', 'cannot load video')
|
||||
return None
|
||||
|
||||
|
||||
def _get_path_for_file(self, file_name):
|
||||
######## returns full path for a given file name ########
|
||||
for path in self.PATHS_TO_BROWSER + self.PATHS_TO_SHADERS:
|
||||
@@ -433,7 +428,6 @@ class Data(object):
|
||||
return True, '{}/{}'.format(root, file_name)
|
||||
return False, ''
|
||||
|
||||
|
||||
def is_this_path_broken(self, path):
|
||||
external_devices = os.listdir(self.PATH_TO_EXTERNAL_DEVICES)
|
||||
has_device_in_path = self.PATH_TO_EXTERNAL_DEVICES in path
|
||||
@@ -522,5 +516,3 @@ class Data(object):
|
||||
def try_remove_file(path):
|
||||
if os.path.exists(path):
|
||||
os.remove(path)
|
||||
|
||||
|
||||
|
||||
@@ -1,5 +1,6 @@
|
||||
import datetime
|
||||
|
||||
|
||||
class FixedLengthSetter(object):
|
||||
DELTA_NUMBER = 2
|
||||
|
||||
|
||||
@@ -1,14 +1,15 @@
|
||||
import inspect
|
||||
import os
|
||||
import pkgutil
|
||||
import re
|
||||
|
||||
from plugins.frame_manager import FrameManager, Frame
|
||||
from plugins.frame_manager import FrameManager
|
||||
|
||||
|
||||
class Plugin(object):
|
||||
"""Base class that each plugin must inherit from. within this class
|
||||
you must define the methods that all of your plugins must implement
|
||||
"""
|
||||
|
||||
@property
|
||||
def disabled(self):
|
||||
return type(self).__name__ not in self.pc.data.get_enabled_plugin_class_names()
|
||||
@@ -23,9 +24,11 @@ class Plugin(object):
|
||||
def start_plugin(self):
|
||||
print(">>Starting plugin " + type(self).__name__)
|
||||
|
||||
|
||||
class MidiFeedbackPlugin(Plugin):
|
||||
"""Base class for MIDI feedback plugins
|
||||
"""
|
||||
|
||||
def __init__(self, plugin_collection):
|
||||
super().__init__(plugin_collection)
|
||||
self.description = 'Outputs feedback about status to device eg MIDI pads'
|
||||
@@ -39,8 +42,10 @@ class MidiFeedbackPlugin(Plugin):
|
||||
def refresh_midi_feedback(self):
|
||||
raise NotImplementedError
|
||||
|
||||
|
||||
class SequencePlugin(Plugin):
|
||||
"""Base class for plugins that run constantly or on demand for eg automation"""
|
||||
|
||||
def __init__(self, plugin_collection):
|
||||
super().__init__(plugin_collection)
|
||||
|
||||
@@ -60,7 +65,8 @@ class SequencePlugin(Plugin):
|
||||
speed = 2.0 * (speed - 0.5) # adjust to range -1 to +1
|
||||
negative = speed < 0.0 # remember negative state cos we'll lose it in next
|
||||
self.speed = (speed * speed) * 2.0
|
||||
if negative: self.speed *= -1
|
||||
if negative:
|
||||
self.speed *= -1
|
||||
print("automation speed is now %s" % self.speed)
|
||||
|
||||
def toggle_automation(self):
|
||||
@@ -86,6 +92,7 @@ class SequencePlugin(Plugin):
|
||||
self.run_automation()
|
||||
|
||||
last_delta = -1
|
||||
|
||||
def delta(self, now):
|
||||
if self.last_delta == -1:
|
||||
self.last_delta = now
|
||||
@@ -94,6 +101,7 @@ class SequencePlugin(Plugin):
|
||||
return r
|
||||
|
||||
speed = 0.25 # 1.0
|
||||
|
||||
def move_delta(self, delta, speed):
|
||||
self.position += delta * speed
|
||||
if self.position > 1.0:
|
||||
@@ -111,6 +119,7 @@ class SequencePlugin(Plugin):
|
||||
iterations_count = 0
|
||||
duration = 2000
|
||||
frequency = 100
|
||||
|
||||
def run_automation(self):
|
||||
import time
|
||||
|
||||
@@ -141,6 +150,7 @@ class SequencePlugin(Plugin):
|
||||
def run_sequence(self, position):
|
||||
raise NotImplementedError
|
||||
|
||||
|
||||
class ActionsPlugin(Plugin):
|
||||
def __init__(self, plugin_collection):
|
||||
super().__init__(plugin_collection)
|
||||
@@ -185,8 +195,10 @@ class ActionsPlugin(Plugin):
|
||||
|
||||
return (found_method, args)
|
||||
|
||||
|
||||
class DisplayPlugin(Plugin):
|
||||
"""Base class for plugins that want to show a user interface on the recur screen"""
|
||||
|
||||
def __init__(self, plugin_collection):
|
||||
super().__init__(plugin_collection)
|
||||
|
||||
@@ -197,12 +209,14 @@ class DisplayPlugin(Plugin):
|
||||
raise NotImplementedError
|
||||
|
||||
def show_plugin(self, display):
|
||||
from tkinter import Text, END
|
||||
from tkinter import END
|
||||
# display_text.insert(END, 'test from DisplayPlugin')
|
||||
display.display_text.insert(END, '{} \n'.format(display.body_title))
|
||||
|
||||
|
||||
class ModulationReceiverPlugin(Plugin):
|
||||
"""Base class for plugins that want to be notified of a change to modulation values"""
|
||||
|
||||
def __init__(self, plugin_collection):
|
||||
super().__init__(plugin_collection)
|
||||
|
||||
@@ -210,8 +224,10 @@ class ModulationReceiverPlugin(Plugin):
|
||||
print("||||||set_modulation_value dummy!")
|
||||
raise NotImplementedError
|
||||
|
||||
|
||||
class AutomationSourcePlugin(Plugin):
|
||||
"""Base class for plugins that offer things to save&playback to&from automation"""
|
||||
|
||||
@property
|
||||
def frame_key(self):
|
||||
return self.__class__.__name__
|
||||
@@ -281,6 +297,7 @@ class AutomationSourcePlugin(Plugin):
|
||||
|
||||
### TODO: experimental value interpolation -- doesn't work, and is slow!
|
||||
cmd_size = {}
|
||||
|
||||
def process_interpolate_clip(self, frames):
|
||||
# loop over every frame
|
||||
# for each property of each frame
|
||||
@@ -367,6 +384,7 @@ class AutomationSourcePlugin(Plugin):
|
||||
self.distance_cache = {}
|
||||
|
||||
distance_cache = {}
|
||||
|
||||
def get_distance_value_command(self, frames, findex, queue, argindex):
|
||||
|
||||
distance_cache = self.distance_cache
|
||||
@@ -403,7 +421,6 @@ class AutomationSourcePlugin(Plugin):
|
||||
distance_cache[queue][argindex] = {'position': i, 'value': command[1][argindex]}
|
||||
return i, command[1][argindex]
|
||||
|
||||
|
||||
"""if frames[search_findex] is not None and frames[search_findex].f.get(self.frame_key,{}).get(queue,[])[argindex] is not None:
|
||||
return i, frames[search_findex].f.get(self.frame_key,{}).get(queue,[])[argindex]"""
|
||||
return 0, None
|
||||
@@ -416,6 +433,7 @@ class PluginCollection(object):
|
||||
"""Upon creation, this class will read the plugins package for modules
|
||||
that contain a class definition that is inheriting from the Plugin class
|
||||
"""
|
||||
|
||||
@property
|
||||
def display(self):
|
||||
return self.actions.display
|
||||
@@ -448,6 +466,7 @@ class PluginCollection(object):
|
||||
|
||||
def read_json(self, file_name):
|
||||
return self.data._read_plugin_json(file_name)
|
||||
|
||||
def update_json(self, file_name, data):
|
||||
return self.data._update_plugin_json(file_name, data)
|
||||
|
||||
@@ -464,7 +483,8 @@ class PluginCollection(object):
|
||||
def quit_plugins(self):
|
||||
# tell each plugin to quit
|
||||
for plugin in self.get_plugins():
|
||||
if not plugin.disabled: plugin.stop_plugin()
|
||||
if not plugin.disabled:
|
||||
plugin.stop_plugin()
|
||||
|
||||
def stop_plugin_name(self, name):
|
||||
for plugin in self.get_plugins(include_disabled=True):
|
||||
@@ -479,7 +499,6 @@ class PluginCollection(object):
|
||||
# print("starting %s" %name)
|
||||
plugin.start_plugin()
|
||||
|
||||
|
||||
def get_plugins(self, clazz=None, include_disabled=False):
|
||||
if clazz:
|
||||
return [c for c in self.plugins if isinstance(c, clazz) and (include_disabled or not c.disabled)]
|
||||
@@ -510,7 +529,6 @@ class PluginCollection(object):
|
||||
print(' Found plugin class: %s.%s' % (c.__module__, c.__name__))
|
||||
self.plugins.append(c(self))
|
||||
|
||||
|
||||
# Now that we have looked at all the modules in the current package, start looking
|
||||
# recursively for additional modules in sub packages
|
||||
# disabled 03-2020 to try and avoid problem with subclasses-of-subclasses being listed twice..
|
||||
@@ -532,7 +550,6 @@ class PluginCollection(object):
|
||||
for child_pkg in child_pkgs:
|
||||
self.walk_package(package + '.' + child_pkg)"""
|
||||
|
||||
|
||||
## helpers
|
||||
def get_variable(self, varname, default=0.0):
|
||||
from plugins.ManipulatePlugin import ManipulatePlugin
|
||||
|
||||
@@ -1,8 +1,10 @@
|
||||
from tkinter import Text, END
|
||||
import math
|
||||
import time
|
||||
from tkinter import END, Text
|
||||
|
||||
import display_centre.menu as menu
|
||||
|
||||
|
||||
class Display(object):
|
||||
MENU_HEIGHT = 10
|
||||
SELECTOR_WIDTH = 0.47
|
||||
@@ -105,7 +107,6 @@ class Display(object):
|
||||
self.display_text.tag_add("DISPLAY_MODE", 4.19, 4.29)
|
||||
self.display_text.tag_add("COLUMN_NAME", 5.0, 6.0)
|
||||
|
||||
|
||||
def _load_plugin_page(self, display_mode, plugin):
|
||||
plugin.show_plugin(self, display_mode)
|
||||
|
||||
@@ -202,7 +203,6 @@ class Display(object):
|
||||
|
||||
self._highlight_this_row(self.plugins_menu.selected_list_index - self.plugins_menu.top_menu_index)
|
||||
|
||||
|
||||
def _load_shaders(self):
|
||||
line_count = 0
|
||||
self.display_text.insert(END, '{} \n'.format(self.body_title))
|
||||
@@ -358,7 +358,6 @@ class Display(object):
|
||||
column_offset = 0.1
|
||||
)"""
|
||||
|
||||
|
||||
def _load_detour(self):
|
||||
line_count = 0
|
||||
self.display_text.insert(END, '{} \n'.format(self.body_title))
|
||||
@@ -426,7 +425,6 @@ class Display(object):
|
||||
capture_status = ''
|
||||
preview_alpha = 0
|
||||
|
||||
|
||||
if preview_alpha == None:
|
||||
preview_alpha = 0
|
||||
# print('capture alpha is {}'.format(preview_alpha))
|
||||
@@ -471,8 +469,10 @@ class Display(object):
|
||||
if value is None:
|
||||
return " "
|
||||
value = abs(value / max_value) # abs() so negative values make some sense
|
||||
if value>1.0: value = 1.0
|
||||
elif value<0.0: value = 0.0
|
||||
if value > 1.0:
|
||||
value = 1.0
|
||||
elif value < 0.0:
|
||||
value = 0.0
|
||||
bar = u"_\u2581\u2582\u2583\u2584\u2585\u2586\u2587\u2588"
|
||||
g = '%s' % bar[int(value * (len(bar) - 1))]
|
||||
return g
|
||||
@@ -529,8 +529,6 @@ class Display(object):
|
||||
# s += "#" if selected else "-"
|
||||
return s
|
||||
|
||||
|
||||
|
||||
@staticmethod
|
||||
def create_video_display_banner(start, end, position):
|
||||
banner_list = ['[', '-', '-', '-', '-', '-', '-', '-', '-',
|
||||
@@ -639,6 +637,7 @@ class Display(object):
|
||||
|
||||
last_refreshed = 0
|
||||
REFRESH_LIMIT = 100
|
||||
|
||||
def refresh_display(self):
|
||||
if self.data.update_screen:
|
||||
if time.time() * 1000 - self.last_refreshed < self.REFRESH_LIMIT:
|
||||
|
||||
@@ -1,5 +1,6 @@
|
||||
import os
|
||||
|
||||
|
||||
class Menu(object):
|
||||
def __init__(self, data, message_handler, menu_height):
|
||||
self.data = data
|
||||
@@ -50,7 +51,6 @@ class Menu(object):
|
||||
self.top_menu_index += self.menu_height
|
||||
self.selected_list_index = min(self.menu_height + self.selected_list_index, len(self.menu_list) - 1)
|
||||
|
||||
|
||||
def update_open_folders(self, folder_name):
|
||||
if folder_name not in self.open_folders:
|
||||
self.open_folders.append(folder_name)
|
||||
@@ -72,6 +72,7 @@ class Menu(object):
|
||||
else:
|
||||
return True, dir_name.lstrip()
|
||||
|
||||
|
||||
class BrowserMenu(Menu):
|
||||
def __init__(self, data, message_handler, menu_height):
|
||||
Menu.__init__(self, data, message_handler, menu_height)
|
||||
@@ -119,7 +120,6 @@ class BrowserMenu(Menu):
|
||||
return True, '{}-{}'.format(bank_index, slot_index)
|
||||
return False, ''
|
||||
|
||||
|
||||
def enter_on_browser_selection(self):
|
||||
is_file, name = self.extract_file_type_and_name_from_menu_format(
|
||||
self.menu_list[self.selected_list_index]['name'])
|
||||
@@ -133,7 +133,6 @@ class BrowserMenu(Menu):
|
||||
|
||||
|
||||
class SettingsMenu(Menu):
|
||||
|
||||
FOLDER_ORDER = ['video', 'sampler', 'user_input', 'capture', 'shader', 'detour', 'system']
|
||||
SAMPLER_ORDER = ['LOOP_TYPE', 'LOAD_NEXT', 'RAND_START_MODE', 'RESET_PLAYERS', 'FIXED_LENGTH_MODE', 'FIXED_LENGTH', 'FIXED_LENGTH_MULTIPLY']
|
||||
VIDEO_ORDER = ['VIDEOPLAYER_BACKEND']
|
||||
@@ -229,7 +228,6 @@ class ShadersMenu(Menu):
|
||||
self._add_folder_to_shaders_list(path, 0)
|
||||
return self.menu_list
|
||||
|
||||
|
||||
def _add_folder_to_shaders_list(self, current_path, current_level):
|
||||
######## adds the folders and shader files at the current level to the results list. recursively recalls at deeper level if folder is open ########
|
||||
|
||||
@@ -249,8 +247,3 @@ class ShadersMenu(Menu):
|
||||
split_name = os.path.splitext(f)
|
||||
if (split_name[1].lower() in ['.frag', '.shader', '.glsl', '.glslf', '.fsh']):
|
||||
self.menu_list.append(dict(name='{}{}'.format(indent, f), is_shader=True))
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
@@ -1,5 +1,6 @@
|
||||
import logging
|
||||
|
||||
|
||||
class MessageHandler(object):
|
||||
def __init__(self):
|
||||
self.current_message = [None, None, None]
|
||||
|
||||
@@ -1,8 +1,8 @@
|
||||
from pythonosc import osc_message_builder
|
||||
from pythonosc import udp_client
|
||||
from pythonosc import dispatcher
|
||||
import argparse
|
||||
|
||||
from pythonosc import udp_client
|
||||
|
||||
|
||||
def setup_osc_client(ip, port):
|
||||
client_parser = argparse.ArgumentParser()
|
||||
client_parser.add_argument("--ip", default=ip, help="the ip")
|
||||
@@ -12,6 +12,7 @@ def setup_osc_client(ip, port):
|
||||
|
||||
return udp_client.SimpleUDPClient(client_args.ip, client_args.port)
|
||||
|
||||
|
||||
client = setup_osc_client('127.0.0.1', 5433)
|
||||
client.send_message("/shutdown", True)
|
||||
|
||||
|
||||
@@ -1,9 +1,9 @@
|
||||
import math
|
||||
import data_centre.plugin_collection
|
||||
from data_centre.plugin_collection import ActionsPlugin, SequencePlugin, DisplayPlugin, AutomationSourcePlugin
|
||||
|
||||
from data_centre.plugin_collection import ActionsPlugin, AutomationSourcePlugin, DisplayPlugin, SequencePlugin
|
||||
|
||||
|
||||
class LFOModulationPlugin(ActionsPlugin, SequencePlugin, DisplayPlugin, AutomationSourcePlugin):
|
||||
|
||||
MAX_LFOS = 4
|
||||
|
||||
PRESET_FILE_NAME = "LFOModulationPlugin/config.json"
|
||||
@@ -25,6 +25,7 @@ class LFOModulationPlugin(ActionsPlugin,SequencePlugin,DisplayPlugin, Automation
|
||||
|
||||
stop_flag = False
|
||||
pause_flag = False
|
||||
|
||||
def __init__(self, plugin_collection):
|
||||
super().__init__(plugin_collection)
|
||||
|
||||
@@ -58,7 +59,7 @@ class LFOModulationPlugin(ActionsPlugin,SequencePlugin,DisplayPlugin, Automation
|
||||
return ['LFOMODU', 'NAV_LFO']
|
||||
|
||||
def show_plugin(self, display, display_mode):
|
||||
from tkinter import Text, END
|
||||
from tkinter import END
|
||||
# super(DisplayPlugin).show_plugin(display, display_mode)
|
||||
display.display_text.insert(END, '{} \n'.format(display.body_title))
|
||||
display.display_text.insert(END, "LFOModulation is ")
|
||||
@@ -130,8 +131,10 @@ class LFOModulationPlugin(ActionsPlugin,SequencePlugin,DisplayPlugin, Automation
|
||||
]
|
||||
|
||||
def set_lfo_modulation_level(self, slot, value):
|
||||
if (value<0.0): value = 0.0
|
||||
if (value>1.0): value = 1.0
|
||||
if (value < 0.0):
|
||||
value = 0.0
|
||||
if (value > 1.0):
|
||||
value = 1.0
|
||||
self.level[slot] = value
|
||||
|
||||
def set_lfo_speed(self, speed):
|
||||
@@ -157,25 +160,31 @@ class LFOModulationPlugin(ActionsPlugin,SequencePlugin,DisplayPlugin, Automation
|
||||
|
||||
def select_next_lfo(self):
|
||||
self.select_lfo(self.selected_lfo + 1)
|
||||
|
||||
def select_previous_lfo(self):
|
||||
self.select_lfo(self.selected_lfo - 1)
|
||||
|
||||
level_step = 0.125
|
||||
|
||||
def increase_lfo_level(self, slot):
|
||||
self.set_lfo_modulation_level(slot, self.level[slot] + self.level_step)
|
||||
|
||||
def decrease_lfo_level(self, slot):
|
||||
self.set_lfo_modulation_level(slot, self.level[slot] - self.level_step)
|
||||
|
||||
def increase_selected_lfo_level(self):
|
||||
self.increase_lfo_level(self.selected_lfo)
|
||||
|
||||
def decrease_selected_lfo_level(self):
|
||||
self.decrease_lfo_level(self.selected_lfo)
|
||||
|
||||
lfo_step = 0.25
|
||||
|
||||
def increase_lfo_speed(self):
|
||||
self.set_lfo_speed_direct(self.speed + self.lfo_step)
|
||||
if self.speed == 0.0: # dont rest on 0 - set to a small amount forward
|
||||
self.speed = 0.05
|
||||
|
||||
def decrease_lfo_speed(self):
|
||||
self.set_lfo_speed_direct(self.speed - self.lfo_step)
|
||||
if self.speed == 0.0: # dont rest on 0 - set to a small amount forward
|
||||
@@ -195,6 +204,7 @@ class LFOModulationPlugin(ActionsPlugin,SequencePlugin,DisplayPlugin, Automation
|
||||
# run the formula for the stored lfo configuration
|
||||
last_lfo_status = [None] * MAX_LFOS # for displaying status
|
||||
last_lfo_value = [None] * MAX_LFOS
|
||||
|
||||
# lfo_speed = [1.0]*MAX_LFOS
|
||||
def getLFO(self, position, lfo):
|
||||
lfo_value = getattr(self, self.formula[lfo])(position, self.level[lfo])
|
||||
|
||||
@@ -1,7 +1,6 @@
|
||||
import data_centre.plugin_collection
|
||||
from data_centre.plugin_collection import ActionsPlugin, DisplayPlugin, ModulationReceiverPlugin # , SequencePlugin
|
||||
|
||||
# import math
|
||||
from math import sin, cos, tan, log, exp, pi
|
||||
|
||||
"""
|
||||
add to midi or osc mapping
|
||||
@@ -41,8 +40,8 @@ TODO: >> ?? invert|set_the_shader_param_0_layer_>>print_arguments>>set_variab
|
||||
|
||||
"""
|
||||
|
||||
class ManipulatePlugin(ActionsPlugin,DisplayPlugin,ModulationReceiverPlugin):
|
||||
|
||||
class ManipulatePlugin(ActionsPlugin, DisplayPlugin, ModulationReceiverPlugin):
|
||||
DEBUG = False
|
||||
|
||||
def __init__(self, plugin_collection):
|
||||
@@ -62,7 +61,7 @@ class ManipulatePlugin(ActionsPlugin,DisplayPlugin,ModulationReceiverPlugin):
|
||||
|
||||
# DisplayPlugin methods
|
||||
def show_plugin(self, display, display_mode):
|
||||
from tkinter import Text, END
|
||||
from tkinter import END
|
||||
# super(DisplayPlugin).show_plugin(display, display_mode)
|
||||
display.display_text.insert(END, '{} \n'.format(display.body_title))
|
||||
display.display_text.insert(END, "test from ManipulatePlugin!\n")
|
||||
@@ -75,7 +74,8 @@ class ManipulatePlugin(ActionsPlugin,DisplayPlugin,ModulationReceiverPlugin):
|
||||
|
||||
# Actions
|
||||
def run_multi(self, action1, action2, value):
|
||||
if self.DEBUG: print("ManipulatePlugin>> multi-running '%s' and '%s' with value %s" % (action1, action2, value))
|
||||
if self.DEBUG:
|
||||
print("ManipulatePlugin>> multi-running '%s' and '%s' with value %s" % (action1, action2, value))
|
||||
self.pc.actions.call_method_name(action1, value)
|
||||
self.pc.actions.call_method_name(action2, value)
|
||||
|
||||
@@ -91,16 +91,19 @@ class ManipulatePlugin(ActionsPlugin,DisplayPlugin,ModulationReceiverPlugin):
|
||||
|
||||
def formula(self, formula, action, value):
|
||||
self.variables['x'] = value
|
||||
if self.DEBUG: print("ManipulatePlugin>> evaluating formula `%s` with value `%s`" % (formula, value))
|
||||
if self.DEBUG:
|
||||
print("ManipulatePlugin>> evaluating formula `%s` with value `%s`" % (formula, value))
|
||||
value = eval(formula, globals(), self.variables)
|
||||
if self.DEBUG: print("ManipulatePlugin>> got evaluated value `%s`" % value)
|
||||
if self.DEBUG:
|
||||
print("ManipulatePlugin>> got evaluated value `%s`" % value)
|
||||
|
||||
self.pc.actions.call_method_name(
|
||||
action, value
|
||||
)
|
||||
|
||||
def set_variable(self, var_name, value):
|
||||
if self.DEBUG: print("ManipulatePlugin>> set_variable (%s) to %s" % (var_name, value))
|
||||
if self.DEBUG:
|
||||
print("ManipulatePlugin>> set_variable (%s) to %s" % (var_name, value))
|
||||
self.variables[var_name] = value
|
||||
|
||||
def get_variable(self, var_name, default):
|
||||
@@ -110,16 +113,16 @@ class ManipulatePlugin(ActionsPlugin,DisplayPlugin,ModulationReceiverPlugin):
|
||||
return default
|
||||
|
||||
def recall_variable(self, var_name, action, *args):
|
||||
if self.DEBUG: print ("ManipulatePlugin>> recall_variable (%s) as %s" % (var_name,args))
|
||||
if self.DEBUG:
|
||||
print("ManipulatePlugin>> recall_variable (%s) as %s" % (var_name, args))
|
||||
self.pc.actions.call_method_name(
|
||||
action, self.variables.get(var_name) # + list(args)
|
||||
)
|
||||
|
||||
|
||||
# ModulationReceiverPlugin methods
|
||||
# methods for ModulationReceiverPlugin - receives changes to the in-built modulation levels (-1 to +1)
|
||||
def set_modulation_value(self, param, value):
|
||||
# take modulation value and throw it to local parameter
|
||||
if self.DEBUG: print("||||| ManipulatePlugin received set_modulation_value for param %s with value %s!" % (param, value))
|
||||
if self.DEBUG:
|
||||
print("||||| ManipulatePlugin received set_modulation_value for param %s with value %s!" % (param, value))
|
||||
self.set_variable("MODVALUE%s" % ('ABCD'[param]), value)
|
||||
|
||||
|
||||
@@ -1,7 +1,8 @@
|
||||
from data_centre import plugin_collection
|
||||
from data_centre.plugin_collection import MidiFeedbackPlugin
|
||||
import mido
|
||||
|
||||
from data_centre.plugin_collection import MidiFeedbackPlugin
|
||||
|
||||
|
||||
class MidiFeedbackAPCKey25Plugin(MidiFeedbackPlugin):
|
||||
# disabled = False
|
||||
|
||||
@@ -70,7 +71,8 @@ class MidiFeedbackAPCKey25Plugin(MidiFeedbackPlugin):
|
||||
self.set_status(note=self.NOTE_CAPTURE_PREVIEW, velocity=int(on))
|
||||
|
||||
def feedback_shader_on(self, layer, slot, colour=None):
|
||||
if colour is None: colour = self.COLOUR_GREEN
|
||||
if colour is None:
|
||||
colour = self.COLOUR_GREEN
|
||||
self.set_status(note=(self.NOTE_PLAY_SHADER - (layer) * 8) + slot, velocity=int(colour))
|
||||
|
||||
def feedback_shader_off(self, layer, slot):
|
||||
@@ -231,6 +233,7 @@ class MidiFeedbackAPCKey25Plugin(MidiFeedbackPlugin):
|
||||
# print("refresh_midi_feedback")
|
||||
|
||||
last_state = None
|
||||
|
||||
def update_device(self):
|
||||
from copy import deepcopy
|
||||
# print("in update device status is %s" % self.status)
|
||||
|
||||
@@ -1,11 +1,9 @@
|
||||
from data_centre import plugin_collection
|
||||
from data_centre.plugin_collection import MidiFeedbackPlugin
|
||||
import mido
|
||||
import plugins
|
||||
|
||||
|
||||
# from plugins.MidiFeedbackAPCKey25Plugin import MidiFeedbackAPCKey25Plugin
|
||||
|
||||
class MidiFeedbackLaunchpadPlugin(plugins.MidiFeedbackAPCKey25Plugin.MidiFeedbackAPCKey25Plugin):
|
||||
|
||||
status = {}
|
||||
|
||||
def __init__(self, plugin_collection):
|
||||
@@ -31,7 +29,8 @@ class MidiFeedbackLaunchpadPlugin(plugins.MidiFeedbackAPCKey25Plugin.MidiFeedbac
|
||||
return True
|
||||
|
||||
def feedback_shader_on(self, layer, slot, colour=None):
|
||||
if colour is None: colour = self.COLOUR_GREEN
|
||||
if colour is None:
|
||||
colour = self.COLOUR_GREEN
|
||||
self.set_status(note=(self.NOTE_PLAY_SHADER + (layer) * 16) + slot, velocity=int(colour))
|
||||
|
||||
def feedback_shader_off(self, layer, slot):
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
import data_centre.plugin_collection
|
||||
from data_centre.plugin_collection import ActionsPlugin
|
||||
|
||||
|
||||
class MultiActionsPlugin(ActionsPlugin):
|
||||
disabled = False # this is only a demo of very basic multi-actions plugin -- superceded by ManipulatePlugin
|
||||
|
||||
|
||||
@@ -1,9 +1,8 @@
|
||||
import data_centre.plugin_collection
|
||||
from data_centre.plugin_collection import ActionsPlugin, SequencePlugin, DisplayPlugin
|
||||
from data_centre.plugin_collection import ActionsPlugin, DisplayPlugin, SequencePlugin
|
||||
from plugins.frame_manager import Frame
|
||||
|
||||
class ShaderLoopRecordPlugin(ActionsPlugin,SequencePlugin,DisplayPlugin):
|
||||
|
||||
class ShaderLoopRecordPlugin(ActionsPlugin, SequencePlugin, DisplayPlugin):
|
||||
MAX_CLIPS = 8
|
||||
frames = []
|
||||
|
||||
@@ -54,7 +53,7 @@ class ShaderLoopRecordPlugin(ActionsPlugin,SequencePlugin,DisplayPlugin):
|
||||
return ['LOOPREC', 'NAV_LPRC']
|
||||
|
||||
def show_plugin(self, display, display_mode):
|
||||
from tkinter import Text, END
|
||||
from tkinter import END
|
||||
# super(DisplayPlugin).show_plugin(display, display_mode)
|
||||
display.display_text.insert(END, '{} \n'.format(display.body_title))
|
||||
display.display_text.insert(END, "test from ShaderLoopRecordPlugin!\n")
|
||||
@@ -93,8 +92,6 @@ class ShaderLoopRecordPlugin(ActionsPlugin,SequencePlugin,DisplayPlugin):
|
||||
"""for key,value in self.variables.items():
|
||||
display.display_text.insert(END, "\t" + key + "\t{:03.2f}\n".format(value))"""
|
||||
|
||||
|
||||
|
||||
@property
|
||||
def parserlist(self):
|
||||
return [
|
||||
@@ -116,7 +113,6 @@ class ShaderLoopRecordPlugin(ActionsPlugin,SequencePlugin,DisplayPlugin):
|
||||
def smooth_selected_clip(self):
|
||||
self.pc.fm.interpolate_clip(self.frames[self.selected_clip])
|
||||
|
||||
|
||||
def toggle_overdub_automation(self):
|
||||
self.overdub = not self.overdub
|
||||
if not self.overdub:
|
||||
@@ -143,7 +139,8 @@ class ShaderLoopRecordPlugin(ActionsPlugin,SequencePlugin,DisplayPlugin):
|
||||
clip = self.selected_clip
|
||||
self.frames[clip] = self.get_empty_clip(self.duration) * self.MAX_CLIPS
|
||||
self.reset_ignored()
|
||||
if self.DEBUG_FRAMES: print ("clear_frames set to %s" % (int(self.duration / self.frequency)))
|
||||
if self.DEBUG_FRAMES:
|
||||
print("clear_frames set to %s" % (int(self.duration / self.frequency)))
|
||||
return self.frames
|
||||
|
||||
def toggle_clip(self, clip=None):
|
||||
@@ -180,6 +177,7 @@ class ShaderLoopRecordPlugin(ActionsPlugin,SequencePlugin,DisplayPlugin):
|
||||
last_frame = None # for tracking what's changed between frames when overdubbing
|
||||
last_saved_index = None # for backfilling
|
||||
DEBUG_FRAMES = False # True
|
||||
|
||||
def run_sequence(self, position):
|
||||
current_frame_index = int(position * (int(self.duration / self.frequency)))
|
||||
if current_frame_index < 0:
|
||||
@@ -187,14 +185,16 @@ class ShaderLoopRecordPlugin(ActionsPlugin,SequencePlugin,DisplayPlugin):
|
||||
if current_frame_index >= self.duration: # self.duration/self.frequency:
|
||||
current_frame_index = "(self.duration/self.frequency) +"""(current_frame_index % self.duration)
|
||||
|
||||
if self.DEBUG_FRAMES: print (">>>>>>>>>>>>>>frame at %i%%: %i" % (position*100, current_frame_index))
|
||||
if self.DEBUG_FRAMES:
|
||||
print(">>>>>>>>>>>>>>frame at %i%%: %i" % (position * 100, current_frame_index))
|
||||
# print("got frame index %s" % current_frame_index)
|
||||
|
||||
if self.recording:
|
||||
current_frame = self.pc.fm.get_live_frame() # .copy()
|
||||
|
||||
selected_clip = self.selected_clip
|
||||
if self.DEBUG_FRAMES: print("current_frame copy before recall is %s" % current_frame['shader_params'])
|
||||
if self.DEBUG_FRAMES:
|
||||
print("current_frame copy before recall is %s" % current_frame['shader_params'])
|
||||
# print ("%s clips, looks like %s" % (len(self.frames),self.frames))
|
||||
|
||||
# print("selected_clip is %s "%selected_clip)
|
||||
@@ -203,7 +203,8 @@ class ShaderLoopRecordPlugin(ActionsPlugin,SequencePlugin,DisplayPlugin):
|
||||
self.running_clips += [self.selected_clip]
|
||||
if self.recording:
|
||||
current_frame = self.pc.fm.get_live_frame() # .copy()
|
||||
if self.DEBUG_FRAMES: print("current_frame copy before recall is %s" % current_frame['shader_params'])
|
||||
if self.DEBUG_FRAMES:
|
||||
print("current_frame copy before recall is %s" % current_frame['shader_params'])
|
||||
|
||||
for selected_clip in self.running_clips:
|
||||
saved_frame = self.frames[selected_clip][current_frame_index]
|
||||
@@ -212,16 +213,21 @@ class ShaderLoopRecordPlugin(ActionsPlugin,SequencePlugin,DisplayPlugin):
|
||||
if self.recording and selected_clip == self.selected_clip:
|
||||
if self.last_frame is None:
|
||||
self.last_frame = current_frame
|
||||
if self.DEBUG_FRAMES: print("last frame is \t\t%s" % self.last_frame['shader_params'])
|
||||
if self.DEBUG_FRAMES: print("current f is \t\t%s" % current_frame['shader_params'])
|
||||
if self.DEBUG_FRAMES:
|
||||
print("last frame is \t\t%s" % self.last_frame['shader_params'])
|
||||
if self.DEBUG_FRAMES:
|
||||
print("current f is \t\t%s" % current_frame['shader_params'])
|
||||
diff = self.pc.fm.get_frame_diff(self.last_frame, current_frame)
|
||||
if self.DEBUG_FRAMES: print("diffed frame is \t%s" % diff['shader_params'])
|
||||
if self.DEBUG_FRAMES:
|
||||
print("diffed frame is \t%s" % diff['shader_params'])
|
||||
|
||||
if self.overdub and saved_frame:
|
||||
# add the params tweaked this frame to the params to be ignored by recall
|
||||
if self.DEBUG_FRAMES: print("saved frame is \t%s" % saved_frame['shader_params'])
|
||||
if self.DEBUG_FRAMES:
|
||||
print("saved frame is \t%s" % saved_frame['shader_params'])
|
||||
self.ignored = self.pc.fm.merge_frames(self.ignored, diff)
|
||||
if self.DEBUG_FRAMES: print("about to call get_ignored_frames with %s\n and\n %s" % (saved_frame.f, self.ignored.f))
|
||||
if self.DEBUG_FRAMES:
|
||||
print("about to call get_ignored_frames with %s\n and\n %s" % (saved_frame.f, self.ignored.f))
|
||||
"""print("got self.ignored:\n\t%s\n" % self.ignored.f)
|
||||
print("diff is currently:\n\t%s\n" % diff.f)
|
||||
print("saved_frame is currently:\n\t%s\n" % saved_frame.f)"""
|
||||
@@ -232,8 +238,10 @@ class ShaderLoopRecordPlugin(ActionsPlugin,SequencePlugin,DisplayPlugin):
|
||||
# print("got merged:\n\t%s\n" % diff.f)
|
||||
# diff = self.pc.shaders.merge_frames(self.pc.shaders.get_live_frame(), diff)
|
||||
self.pc.fm.recall_frame(diff)
|
||||
if self.DEBUG_FRAMES: print("after diff2 is: \t%s" % diff['shader_params'])
|
||||
if self.DEBUG_FRAMES: print("||||saving frame \t%s" % (diff['shader_params']))
|
||||
if self.DEBUG_FRAMES:
|
||||
print("after diff2 is: \t%s" % diff['shader_params'])
|
||||
if self.DEBUG_FRAMES:
|
||||
print("||||saving frame \t%s" % (diff['shader_params']))
|
||||
self.frames[selected_clip][current_frame_index] = diff # self.get_frame_diff(self.last_frame,current_frame)
|
||||
# backfill frames
|
||||
"""if self.last_saved_index is not None:
|
||||
@@ -243,8 +251,8 @@ class ShaderLoopRecordPlugin(ActionsPlugin,SequencePlugin,DisplayPlugin):
|
||||
self.frames[selected_clip][(self.last_saved_index+i+1)%len(self.frames[selected_clip])] = diff"""
|
||||
self.last_saved_index = current_frame_index
|
||||
self.last_frame = self.pc.fm.get_live_frame() # diff
|
||||
if self.DEBUG_FRAMES: print("<<<<<<<<<<<<<< frame at %s" % current_frame_index)
|
||||
if self.DEBUG_FRAMES:
|
||||
print("<<<<<<<<<<<<<< frame at %s" % current_frame_index)
|
||||
|
||||
"""def recall_frame_index(self, index):
|
||||
self.pc.shaders.recall_frame_params(self.frames[index].copy())"""
|
||||
|
||||
|
||||
@@ -1,8 +1,7 @@
|
||||
import data_centre.plugin_collection
|
||||
from data_centre.plugin_collection import ActionsPlugin, SequencePlugin, DisplayPlugin
|
||||
import copy
|
||||
from data_centre.plugin_collection import ActionsPlugin, DisplayPlugin
|
||||
from plugins.frame_manager import Frame
|
||||
|
||||
|
||||
class ShaderQuickPresetPlugin(ActionsPlugin, DisplayPlugin): # ,SequencePlugin):
|
||||
|
||||
MAX_PRESETS = 8
|
||||
@@ -55,7 +54,7 @@ class ShaderQuickPresetPlugin(ActionsPlugin,DisplayPlugin): #,SequencePlugin):
|
||||
return ['QUIKSHDR', ['NAV_QKSH', 'PLAY_SHADER']]
|
||||
|
||||
def show_plugin(self, display, display_mode):
|
||||
from tkinter import Text, END
|
||||
from tkinter import END
|
||||
# super(DisplayPlugin).show_plugin(display, display_mode)
|
||||
display.display_text.insert(END, '{} \n'.format(display.body_title))
|
||||
display.display_text.insert(END, "ShaderQuickPresetPlugin")
|
||||
@@ -115,7 +114,8 @@ class ShaderQuickPresetPlugin(ActionsPlugin,DisplayPlugin): #,SequencePlugin):
|
||||
self.save_presets()
|
||||
|
||||
def store_current_preset(self):
|
||||
if self.selected_preset is None: self.selected_preset = 0
|
||||
if self.selected_preset is None:
|
||||
self.selected_preset = 0
|
||||
|
||||
insert_position = self.selected_preset
|
||||
self.presets[insert_position] = self.pc.fm.get_live_frame()
|
||||
@@ -170,6 +170,3 @@ class ShaderQuickPresetPlugin(ActionsPlugin,DisplayPlugin): #,SequencePlugin):
|
||||
self.selected_preset -= 1
|
||||
if self.selected_preset < 0:
|
||||
self.selected_preset = self.MAX_PRESETS - 1
|
||||
|
||||
|
||||
|
||||
|
||||
@@ -1,18 +1,16 @@
|
||||
import math
|
||||
import data_centre.plugin_collection
|
||||
from data_centre.plugin_collection import ActionsPlugin, SequencePlugin, DisplayPlugin, AutomationSourcePlugin
|
||||
|
||||
import pyaudio
|
||||
import numpy as np
|
||||
from random import randint
|
||||
from statistics import mean
|
||||
|
||||
import numpy as np
|
||||
import pyaudio
|
||||
|
||||
from data_centre.plugin_collection import ActionsPlugin, DisplayPlugin, SequencePlugin
|
||||
|
||||
# import matplotlib.pyplot as plt
|
||||
|
||||
np.set_printoptions(suppress=True) # don't use scientific notationn
|
||||
|
||||
class SoundReactPlugin(ActionsPlugin,SequencePlugin,DisplayPlugin):
|
||||
|
||||
class SoundReactPlugin(ActionsPlugin, SequencePlugin, DisplayPlugin):
|
||||
DEBUG = False
|
||||
|
||||
active = True
|
||||
@@ -112,7 +110,7 @@ class SoundReactPlugin(ActionsPlugin,SequencePlugin,DisplayPlugin):
|
||||
return ['SOUNDMOD', 'NAV_SND']
|
||||
|
||||
def show_plugin(self, display, display_mode):
|
||||
from tkinter import Text, END
|
||||
from tkinter import END
|
||||
# super(DisplayPlugin).show_plugin(display, display_mode)
|
||||
display.display_text.insert(END, '{} \n'.format(display.body_title))
|
||||
display.display_text.insert(END, "SoundReactPlugin - ")
|
||||
@@ -136,6 +134,7 @@ class SoundReactPlugin(ActionsPlugin,SequencePlugin,DisplayPlugin):
|
||||
display.display_text.insert(END, "\n\n\n")
|
||||
|
||||
energy_history = []
|
||||
|
||||
def run_sequence(self, position):
|
||||
# position is irrelvant for this plugin, we just want to run continuously
|
||||
if not self.active or self.stream is None:
|
||||
@@ -168,12 +167,10 @@ class SoundReactPlugin(ActionsPlugin,SequencePlugin,DisplayPlugin):
|
||||
self.energy_history.append(diff) # self.values.get(sourcename,0.0))
|
||||
# print("logging %s" % diff) #self.values.get(sourcename,0.0))
|
||||
|
||||
|
||||
|
||||
|
||||
config.setdefault('energy', {})['gain'] = 0.5 # how much to multiply signal by
|
||||
config.setdefault('energy', {})['threshold'] = 0.5 # subtract from post-gain signal (hence ignore all values below this value)
|
||||
GAIN_MULT = 1.0
|
||||
|
||||
def energy(self, data):
|
||||
peak = np.average(np.abs(data)) * 2
|
||||
value = (peak / 2 ** 16) / 16 * 100
|
||||
@@ -187,7 +184,8 @@ class SoundReactPlugin(ActionsPlugin,SequencePlugin,DisplayPlugin):
|
||||
value = 1.0
|
||||
|
||||
bars = "#" * int(50 * value)
|
||||
if self.DEBUG: print("energy:\t\t%05d %s\t(converted to %s)"%(peak,bars,value))
|
||||
if self.DEBUG:
|
||||
print("energy:\t\t%05d %s\t(converted to %s)" % (peak, bars, value))
|
||||
self.display_values['energy'] = "{} gn:{} trsh:{} trg:{}".format(
|
||||
self.pc.display.get_bar(value),
|
||||
self.pc.display.get_bar(self.config['energy']['gain']),
|
||||
@@ -198,6 +196,7 @@ class SoundReactPlugin(ActionsPlugin,SequencePlugin,DisplayPlugin):
|
||||
return value
|
||||
|
||||
# dont think this works properly, or maybe it do just be like that
|
||||
|
||||
def peakfreq(self, data):
|
||||
data = data.copy() * np.hanning(len(data)) # smooth the FFT by windowing data
|
||||
fft = abs(np.fft.fft(data).real)
|
||||
@@ -209,12 +208,12 @@ class SoundReactPlugin(ActionsPlugin,SequencePlugin,DisplayPlugin):
|
||||
return False
|
||||
value = freqPeak / 2000 # ?
|
||||
# value = (value**16)
|
||||
if self.DEBUG: print("peak frequency:\t%d\tHz\t(converted to %s)"%(freqPeak,value))
|
||||
if self.DEBUG:
|
||||
print("peak frequency:\t%d\tHz\t(converted to %s)" % (freqPeak, value))
|
||||
self.display_values['peakfreq'] = ("%d Hz\t" % freqPeak) + "{:03.2f}".format(value)
|
||||
|
||||
return value
|
||||
|
||||
|
||||
# ActionsPlugin methods
|
||||
@property
|
||||
def parserlist(self):
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
import data_centre.plugin_collection
|
||||
from data_centre.plugin_collection import ActionsPlugin, SequencePlugin
|
||||
|
||||
|
||||
class TestPlugin(ActionsPlugin, SequencePlugin):
|
||||
disabled = True
|
||||
|
||||
@@ -26,6 +26,7 @@ class TestPlugin(ActionsPlugin,SequencePlugin):
|
||||
# can now access various parts of recur via self.pc
|
||||
|
||||
cycle_count = 0
|
||||
|
||||
def cycle_shaders(self):
|
||||
print("Cycle shaders!!!")
|
||||
if self.cycle_count > 9:
|
||||
@@ -42,6 +43,7 @@ class TestPlugin(ActionsPlugin,SequencePlugin):
|
||||
|
||||
duration = 5000
|
||||
frequency = 50
|
||||
|
||||
def run_sequence(self, position):
|
||||
self.pc.actions.call_method_name(
|
||||
"set_the_shader_param_3_layer_0_continuous", position
|
||||
|
||||
@@ -1,13 +1,15 @@
|
||||
import serial
|
||||
from serial import Serial
|
||||
import data_centre.plugin_collection
|
||||
from data_centre.plugin_collection import ActionsPlugin, SequencePlugin, DisplayPlugin, ModulationReceiverPlugin, AutomationSourcePlugin
|
||||
import threading
|
||||
import time
|
||||
|
||||
import serial
|
||||
|
||||
from data_centre.plugin_collection import ActionsPlugin, AutomationSourcePlugin, DisplayPlugin, ModulationReceiverPlugin, SequencePlugin
|
||||
|
||||
|
||||
class AsyncWriter(threading.Thread):
|
||||
queue = []
|
||||
quit_flag = False
|
||||
|
||||
def __init__(self, plugin):
|
||||
super().__init__()
|
||||
self.plugin = plugin
|
||||
@@ -112,10 +114,10 @@ class WJSendPlugin(ActionsPlugin, SequencePlugin, DisplayPlugin, ModulationRecei
|
||||
self.asyncwriter = None
|
||||
self.save_presets()
|
||||
|
||||
|
||||
# methods/vars for AutomationSourcePlugin
|
||||
# a lot of the nitty-gritty handled in parent class, these are for interfacing to the plugin
|
||||
last_record = {}
|
||||
|
||||
def get_frame_data(self):
|
||||
diff = self.last_record.copy()
|
||||
# self.last_record = {}
|
||||
@@ -141,13 +143,15 @@ class WJSendPlugin(ActionsPlugin, SequencePlugin, DisplayPlugin, ModulationRecei
|
||||
# experimental & hardcoded !
|
||||
# TODO: make this not hardcoded and configurable mapping modulation to parameters, preferably on-the-fly..
|
||||
modulation_value = [0.0, 0.0, 0.0, 0.0]
|
||||
|
||||
def set_modulation_value(self, param, value):
|
||||
|
||||
self.modulation_value[param] = value ## invert so that no signal always gives a value ..
|
||||
# print("storing modulation slot %s as %s" % (param,value))
|
||||
|
||||
# take modulation value and throw it to local parameter
|
||||
if self.DEBUG: print("||||| WJSendPlugin received set_modulation_value for param %s with value %s!" % (param, value))
|
||||
if self.DEBUG:
|
||||
print("||||| WJSendPlugin received set_modulation_value for param %s with value %s!" % (param, value))
|
||||
# v = (0.5+value)/2
|
||||
"""mapped = [
|
||||
'mix',
|
||||
@@ -163,9 +167,11 @@ class WJSendPlugin(ActionsPlugin, SequencePlugin, DisplayPlugin, ModulationRecei
|
||||
for queue, cmd in sorted(self.command_by_queue.items(), reverse=True):
|
||||
cmd.setdefault('modulation', [{}, {}, {}, {}])
|
||||
|
||||
if self.DEBUG: print("\tparam %s, checking modulation %s" % (param, cmd.get('modulation')))
|
||||
if self.DEBUG:
|
||||
print("\tparam %s, checking modulation %s" % (param, cmd.get('modulation')))
|
||||
if len(cmd['modulation'][param]) > 0:
|
||||
if self.DEBUG: print("\tParam %s has modulation! sending update of values? %s" %
|
||||
if self.DEBUG:
|
||||
print("\tParam %s has modulation! sending update of values? %s" %
|
||||
(param, [cmd['arguments'][y] for y in cmd['arg_names']]))
|
||||
# self.send_buffered(cmd['queue'], cmd['form'], [x for x in [ cmd['arguments'][y] for y in cmd['arg_names'] ] ], record=False)
|
||||
to_send[cmd['queue']] = cmd
|
||||
@@ -178,7 +184,7 @@ class WJSendPlugin(ActionsPlugin, SequencePlugin, DisplayPlugin, ModulationRecei
|
||||
|
||||
# methods for DisplayPlugin
|
||||
def show_plugin(self, display, display_mode):
|
||||
from tkinter import Text, END
|
||||
from tkinter import END
|
||||
display.display_text.insert(END, '{} \n'.format(display.body_title))
|
||||
display.display_text.insert(END, "WJSendPlugin {}\n\n".format('ACTIVE' if self.active else 'not active'))
|
||||
|
||||
@@ -210,7 +216,6 @@ class WJSendPlugin(ActionsPlugin, SequencePlugin, DisplayPlugin, ModulationRecei
|
||||
def get_display_modes(self):
|
||||
return ["WJMXSEND", "NAV_WJMX"]
|
||||
|
||||
|
||||
# methods for SerialPlugin (TODO: if this needs generalising out!) and serial command queueing
|
||||
def open_serial(self, port='/dev/ttyUSB0', baudrate=9600):
|
||||
if self.ser is not None:
|
||||
@@ -237,6 +242,7 @@ class WJSendPlugin(ActionsPlugin, SequencePlugin, DisplayPlugin, ModulationRecei
|
||||
|
||||
import threading
|
||||
serial_lock = threading.Lock()
|
||||
|
||||
def send_serial_string(self, string):
|
||||
# TODO: thread this so can implement throttling and reduce bottleneck...
|
||||
if not self.active:
|
||||
@@ -270,6 +276,7 @@ class WJSendPlugin(ActionsPlugin, SequencePlugin, DisplayPlugin, ModulationRecei
|
||||
queue = {}
|
||||
import threading
|
||||
queue_lock = threading.Lock()
|
||||
|
||||
# send the queued commands to WJMX
|
||||
def refresh(self):
|
||||
if not self.ser or self.ser is None:
|
||||
@@ -299,6 +306,7 @@ class WJSendPlugin(ActionsPlugin, SequencePlugin, DisplayPlugin, ModulationRecei
|
||||
|
||||
last = {}
|
||||
last_modulated = {}
|
||||
|
||||
def send_buffered(self, queue, form, args, record=True):
|
||||
# only send if new command is different to the last one we sent
|
||||
mod_args = self.modulate_arguments(self.command_by_queue.get(queue), args)
|
||||
@@ -308,7 +316,8 @@ class WJSendPlugin(ActionsPlugin, SequencePlugin, DisplayPlugin, ModulationRecei
|
||||
output = form.format(*mod_args)
|
||||
self.send_serial_string(output)
|
||||
else:
|
||||
if self.DEBUG: print("WJSendPlugin>> skipping sending %s %s as it is similar to what was previously sent" % (form,mod_args))
|
||||
if self.DEBUG:
|
||||
print("WJSendPlugin>> skipping sending %s %s as it is similar to what was previously sent" % (form, mod_args))
|
||||
|
||||
self.last[queue] = (form, args)
|
||||
self.last_modulated[queue] = (form, mod_args)
|
||||
@@ -326,7 +335,6 @@ class WJSendPlugin(ActionsPlugin, SequencePlugin, DisplayPlugin, ModulationRecei
|
||||
# append value, padded to length - for sending commands that aren't preprogrammed
|
||||
self.send(command.split(':')[0], "{}{:0%iX}" % pad, [command, int(255 * value)])
|
||||
|
||||
|
||||
# methods for ActionPlugin - preprogrammed parameters
|
||||
@property
|
||||
def parserlist(self):
|
||||
@@ -360,8 +368,10 @@ class WJSendPlugin(ActionsPlugin, SequencePlugin, DisplayPlugin, ModulationRecei
|
||||
struct['modulation'] = [{}, {}, {}, {}]
|
||||
|
||||
def set_modulation_command_argument_level(self, command_name, argument_name, slot, level):
|
||||
if self.DEBUG: print("set_modulation_command_argument_level(%s, %s, %s, %s)" % (command_name, argument_name, slot, level))
|
||||
if not argument_name: self.commands[command_name]['arg_names'][0] #argument_name = 'v'
|
||||
if self.DEBUG:
|
||||
print("set_modulation_command_argument_level(%s, %s, %s, %s)" % (command_name, argument_name, slot, level))
|
||||
if not argument_name:
|
||||
self.commands[command_name]['arg_names'][0] # argument_name = 'v'
|
||||
|
||||
self.commands[command_name].setdefault('modulation', [{}, {}, {}, {}])[slot][argument_name] = level
|
||||
|
||||
@@ -399,7 +409,8 @@ class WJSendPlugin(ActionsPlugin, SequencePlugin, DisplayPlugin, ModulationRecei
|
||||
# arguments = packed_arguments.split("_") + [ value ]
|
||||
# print("commands looks like %s" % self.commands)
|
||||
msg = self.commands[param]
|
||||
if len(msg['arg_names'])==1: argument_name = msg['arg_names'][0]
|
||||
if len(msg['arg_names']) == 1:
|
||||
argument_name = msg['arg_names'][0]
|
||||
msg['arguments'][argument_name] = int(value * 255) # = arguments
|
||||
self.send(msg['queue'], msg['form'], [msg['arguments'][p] for p in msg['arg_names']])
|
||||
|
||||
@@ -414,16 +425,19 @@ class WJSendPlugin(ActionsPlugin, SequencePlugin, DisplayPlugin, ModulationRecei
|
||||
for arg_name, m in modlevels.items():
|
||||
if m > 0.0:
|
||||
arg_index = command.get('arg_names').index(arg_name)
|
||||
if self.DEBUG: print("\t\tupdating modulation slot %s, arg is %s\n\t with modlevel '%s' * modvalue '%s'" % (arg_index, args[arg_index], m, self.modulation_value[slot]))
|
||||
if self.DEBUG:
|
||||
print("\t\tupdating modulation slot %s, arg is %s\n\t with modlevel '%s' * modvalue '%s'" % (arg_index, args[arg_index], m, self.modulation_value[slot]))
|
||||
# amount, value, level
|
||||
newvalue = self.pc.shaders.get_modulation_value(
|
||||
args[arg_index] / 255.0,
|
||||
self.modulation_value[slot],
|
||||
m
|
||||
)
|
||||
if self.DEBUG: print("\t\tnewvalue is %s" %newvalue)
|
||||
if self.DEBUG:
|
||||
print("\t\tnewvalue is %s" % newvalue)
|
||||
args[arg_index] = int(255 * newvalue)
|
||||
if self.DEBUG: print("modulate_arguments returning:\n\t%s" % args)
|
||||
if self.DEBUG:
|
||||
print("modulate_arguments returning:\n\t%s" % args)
|
||||
return args
|
||||
|
||||
# panasonic parameters are 8 bit so go 0-255, so 127 is default of centre value
|
||||
@@ -473,4 +487,3 @@ class WJSendPlugin(ActionsPlugin, SequencePlugin, DisplayPlugin, ModulationRecei
|
||||
# }
|
||||
}
|
||||
command_by_queue = {}
|
||||
|
||||
|
||||
@@ -1,7 +1,7 @@
|
||||
import copy
|
||||
import json
|
||||
from json import JSONEncoder
|
||||
|
||||
|
||||
def _default(self, obj):
|
||||
if getattr(obj.__class__, 'to_json'):
|
||||
# return _default.default(obj.to_json())
|
||||
@@ -9,9 +9,11 @@ def _default(self, obj):
|
||||
else:
|
||||
return _default.default(obj)
|
||||
|
||||
|
||||
_default.default = JSONEncoder().default
|
||||
JSONEncoder.default = _default
|
||||
|
||||
|
||||
class Frame:
|
||||
f = {'shader_params': [[None] * 4, [None] * 4, [None] * 4]}
|
||||
pc = None
|
||||
@@ -19,7 +21,6 @@ class Frame:
|
||||
DEBUG_FRAMES = False # True
|
||||
|
||||
def __init__(self, pc):
|
||||
import copy #from copy import deepcopy
|
||||
self.pc = pc
|
||||
|
||||
def to_json(self):
|
||||
@@ -27,6 +28,7 @@ class Frame:
|
||||
|
||||
def get(self, key, default=None):
|
||||
return self.f.get(key, default)
|
||||
|
||||
def has(self, key):
|
||||
return self.get(key) is not None
|
||||
|
||||
@@ -144,8 +146,6 @@ class Frame:
|
||||
|
||||
return s
|
||||
|
||||
|
||||
|
||||
def get_shader_param_summary(self, layer):
|
||||
if self.get('shader_params') is None:
|
||||
return ""
|
||||
@@ -265,7 +265,8 @@ class Frame:
|
||||
for plugin in self.pc.get_plugins(AutomationSourcePlugin):
|
||||
f[plugin.frame_key] = plugin.merge_data(f.get(plugin.frame_key), frame2.get(plugin.frame_key))
|
||||
|
||||
if self.DEBUG_FRAMES: print("merge_frames: got return\t%s" % f)
|
||||
if self.DEBUG_FRAMES:
|
||||
print("merge_frames: got return\t%s" % f)
|
||||
return Frame(self.pc).store_copy(f)
|
||||
|
||||
def get_ignored(self, ignored):
|
||||
@@ -273,7 +274,8 @@ class Frame:
|
||||
f = deepcopy(self.f) # frame1.copy()
|
||||
frame = self.f
|
||||
ignored = ignored.f
|
||||
if self.DEBUG_FRAMES: print("get_frame_ignored: got frame\t%s" % self.f)
|
||||
if self.DEBUG_FRAMES:
|
||||
print("get_frame_ignored: got frame\t%s" % self.f)
|
||||
for i, f2 in enumerate(frame.get('shader_params', [])):
|
||||
for i2, p in enumerate(f2):
|
||||
if ignored['shader_params'][i][i2] is not None:
|
||||
@@ -295,14 +297,16 @@ class Frame:
|
||||
# print("ignoring for %s:\n\t%s\n" % (plugin.frame_key, ignored.get(plugin.frame_key)))
|
||||
f[plugin.frame_key] = plugin.get_ignored_data(f.get(plugin.frame_key, {}), ignored.get(plugin.frame_key, {}))
|
||||
|
||||
if self.DEBUG_FRAMES: print("get_frame_ignored: got return\t%s" % f)
|
||||
if self.DEBUG_FRAMES:
|
||||
print("get_frame_ignored: got return\t%s" % f)
|
||||
return Frame(self.pc).store_copy(f)
|
||||
|
||||
def is_empty(self):
|
||||
# from copy import deepcopy
|
||||
# f = deepcopy(frame) #frame1.copy()
|
||||
frame = self.f
|
||||
if self.DEBUG_FRAMES: print("is_frame_empty: got frame\t%s" % frame)
|
||||
if self.DEBUG_FRAMES:
|
||||
print("is_frame_empty: got frame\t%s" % frame)
|
||||
|
||||
if self.has('feedback_active'):
|
||||
return False
|
||||
@@ -328,7 +332,8 @@ class Frame:
|
||||
if not plugin.is_frame_data_empty(frame.get(plugin.frame_key)):
|
||||
return False
|
||||
|
||||
if self.DEBUG_FRAMES: print("is_frame_empty: got return true")
|
||||
if self.DEBUG_FRAMES:
|
||||
print("is_frame_empty: got return true")
|
||||
return True
|
||||
|
||||
def get_diff(self, current_frame):
|
||||
@@ -346,7 +351,8 @@ class Frame:
|
||||
# if self.DEBUG_FRAMES: print("got layer %s params: %s" % (layer, params))
|
||||
for param, p in enumerate(params):
|
||||
if p is not None and p != last_frame.get('shader_params')[layer][param]:
|
||||
if self.DEBUG_FRAMES: print("setting layer %s param %s to %s" % (layer,param,p))
|
||||
if self.DEBUG_FRAMES:
|
||||
print("setting layer %s param %s to %s" % (layer, param, p))
|
||||
param_values[layer][param] = p
|
||||
|
||||
if current_frame['feedback_active'] is not None and last_frame['feedback_active'] != current_frame['feedback_active']:
|
||||
@@ -387,14 +393,12 @@ class Frame:
|
||||
'strobe_amount': strobe_amount,
|
||||
}
|
||||
diff.update(plugin_data)
|
||||
if self.DEBUG_FRAMES: print("returning\t%s\n^^^^" % diff['shader_params'])
|
||||
if self.DEBUG_FRAMES:
|
||||
print("returning\t%s\n^^^^" % diff['shader_params'])
|
||||
|
||||
return Frame(self.pc).store_copy(diff)
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
class FrameManager:
|
||||
pc = None
|
||||
|
||||
|
||||
21
r_e_c_u_r.py
21
r_e_c_u_r.py
@@ -1,24 +1,21 @@
|
||||
#!/usr/bin/python
|
||||
|
||||
import traceback
|
||||
from tkinter import Tk, Frame
|
||||
import sys
|
||||
import tracemalloc
|
||||
import argparse
|
||||
import traceback
|
||||
from tkinter import Frame, Tk
|
||||
|
||||
from pythonosc import udp_client
|
||||
|
||||
from actions import Actions
|
||||
from data_centre.data import Data
|
||||
from display_centre.display import Display
|
||||
from display_centre.messages import MessageHandler
|
||||
from user_input.analog_input import AnalogInput
|
||||
from user_input.midi_input import MidiInput
|
||||
from user_input.numpad_input import NumpadInput
|
||||
from user_input.osc_input import OscInput
|
||||
from user_input.midi_input import MidiInput
|
||||
from user_input.analog_input import AnalogInput
|
||||
from video_centre.video_driver import VideoDriver
|
||||
#from video_centre.capture import Capture
|
||||
from video_centre.shaders import Shaders
|
||||
import data_centre
|
||||
from video_centre.video_driver import VideoDriver
|
||||
|
||||
# create tk object
|
||||
tk = Tk()
|
||||
@@ -32,6 +29,7 @@ message_handler = MessageHandler()
|
||||
|
||||
data = Data(message_handler)
|
||||
|
||||
|
||||
def setup_osc_client():
|
||||
client_parser = argparse.ArgumentParser()
|
||||
client_parser.add_argument("--ip", default="127.0.0.1", help="the ip")
|
||||
@@ -41,6 +39,7 @@ def setup_osc_client():
|
||||
|
||||
return udp_client.SimpleUDPClient(client_args.ip, client_args.port)
|
||||
|
||||
|
||||
osc_client = setup_osc_client()
|
||||
# setup the video driver
|
||||
video_driver = VideoDriver(tk, osc_client, message_handler, data)
|
||||
@@ -70,14 +69,12 @@ actions.toggle_x_autorepeat()
|
||||
frame.pack()
|
||||
tk.attributes("-fullscreen", True)
|
||||
|
||||
|
||||
def handle_error(exc, val, tb):
|
||||
print('traceback for error : {}'.format(traceback.format_exc()))
|
||||
message_handler.set_message('ERROR', val, traceback.format_exc())
|
||||
|
||||
|
||||
|
||||
tk.report_callback_exception = handle_error
|
||||
|
||||
|
||||
tk.mainloop()
|
||||
|
||||
|
||||
9
requirements.txt
Normal file
9
requirements.txt
Normal file
@@ -0,0 +1,9 @@
|
||||
adafruit-mcp3008
|
||||
gitpython
|
||||
mido
|
||||
numpy
|
||||
omxplayer-wrapper
|
||||
picamera
|
||||
pyaudio
|
||||
pyserial
|
||||
python-osc
|
||||
@@ -1,6 +1,6 @@
|
||||
import Adafruit_GPIO.SPI as SPI
|
||||
import Adafruit_MCP3008
|
||||
|
||||
|
||||
class AnalogInput(object):
|
||||
def __init__(self, root, message_handler, display, actions, data):
|
||||
self.root = root
|
||||
@@ -14,7 +14,6 @@ class AnalogInput(object):
|
||||
self.analog_input = None
|
||||
self.check_if_listening_enabled()
|
||||
|
||||
|
||||
def check_if_listening_enabled(self):
|
||||
if self.data.settings['user_input']['ANALOG_INPUT']['value'] == 'enabled':
|
||||
if not self.analog_input:
|
||||
@@ -79,5 +78,3 @@ class AnalogInput(object):
|
||||
## not sure whether we want to update the screen in general; here - probably not most of the time ...
|
||||
# if 'cc' not in message_name:
|
||||
# self.display.refresh_display()
|
||||
|
||||
|
||||
|
||||
@@ -1,7 +1,5 @@
|
||||
import string
|
||||
import datetime
|
||||
import mido
|
||||
import subprocess
|
||||
|
||||
|
||||
class MidiInput(object):
|
||||
def __init__(self, root, message_handler, display, actions, data):
|
||||
@@ -164,7 +162,6 @@ class MidiInput(object):
|
||||
if self.midi_output.supports_midi_feedback(self.data.midi_device_name):
|
||||
self.root.after(self.midi_delay * 5, self.refresh_midi_feedback)
|
||||
|
||||
|
||||
def find_binding_for_action(self, action):
|
||||
for bind, a in self.midi_mappings.items():
|
||||
# print("looped over %s : %s " % (bind,a))
|
||||
@@ -172,4 +169,3 @@ class MidiInput(object):
|
||||
if action in c:
|
||||
# print ("find_binding_for_action(%s) got %s" % (action, bind))
|
||||
return bind
|
||||
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
import string
|
||||
import sys
|
||||
|
||||
|
||||
class NumpadInput(object):
|
||||
KEY_000_DELAY = 100
|
||||
@@ -111,8 +111,6 @@ class NumpadInput(object):
|
||||
if not value:
|
||||
self.display.refresh_display()
|
||||
|
||||
|
||||
|
||||
def check_key_release_settings(self, key):
|
||||
|
||||
this_mapping = self.key_mappings[key]
|
||||
@@ -172,4 +170,3 @@ class NumpadInput(object):
|
||||
elif (self.additional_0_in_event > 1):
|
||||
self.in_0_event = False
|
||||
self.run_action_for_mapped_key('n')
|
||||
|
||||
|
||||
@@ -1,12 +1,9 @@
|
||||
import argparse
|
||||
import string
|
||||
import sys
|
||||
import threading
|
||||
|
||||
|
||||
from pythonosc import dispatcher
|
||||
from pythonosc import dispatcher
|
||||
from pythonosc import osc_server
|
||||
import threading
|
||||
import argparse
|
||||
|
||||
|
||||
class OscInput(object):
|
||||
@@ -66,7 +63,6 @@ class OscInput(object):
|
||||
except:
|
||||
self.message_handler.set_message('INFO', 'failed to start osc listener')
|
||||
|
||||
|
||||
def exit_osc_server(self, unused_addr, args):
|
||||
print('%%%%%%%%%%%%%%%%%%%%% exiting external_osc')
|
||||
try:
|
||||
@@ -75,7 +71,6 @@ class OscInput(object):
|
||||
except:
|
||||
self.message_handler.set_message('INFO', 'osc shutdown failed')
|
||||
|
||||
|
||||
def on_osc_input(self, addr, args):
|
||||
if 'keyboard' in addr:
|
||||
self.on_key_osc_input(addr, args)
|
||||
@@ -84,7 +79,6 @@ class OscInput(object):
|
||||
else:
|
||||
self.on_param_osc_input(addr, args)
|
||||
|
||||
|
||||
def on_key_osc_input(self, addr, args):
|
||||
args = str(args)
|
||||
print("!!!!!!!!!!!!!!!!" + args)
|
||||
@@ -126,4 +120,3 @@ class OscInput(object):
|
||||
|
||||
if 'continuous' not in method_name:
|
||||
self.display.refresh_display()
|
||||
|
||||
|
||||
@@ -1,5 +1,3 @@
|
||||
|
||||
|
||||
def generate_mappings_doc(title, mappings, column_one_header="Note/CC"):
|
||||
# print(mappings)
|
||||
output = ""
|
||||
@@ -20,4 +18,3 @@ def generate_mappings_doc(title, mappings, column_one_header="Note/CC"):
|
||||
output += "\n----\n"
|
||||
|
||||
print(output)
|
||||
|
||||
|
||||
@@ -1,5 +1,3 @@
|
||||
|
||||
|
||||
class AltVideoPlayer:
|
||||
def __init__(self, root, message_handler, data, osc_client, name):
|
||||
self.root = root
|
||||
@@ -23,7 +21,6 @@ class AltVideoPlayer:
|
||||
|
||||
self.position = -1
|
||||
|
||||
|
||||
def try_load(self, layer, is_current=False):
|
||||
load_attempts = 0
|
||||
while (load_attempts < 2):
|
||||
@@ -37,7 +34,6 @@ class AltVideoPlayer:
|
||||
self.status = 'ERROR'
|
||||
return False
|
||||
|
||||
|
||||
def load(self, layer, is_current=False):
|
||||
self.get_context_for_player(is_current)
|
||||
print('the location is {}'.format(self.location))
|
||||
@@ -73,9 +69,6 @@ class AltVideoPlayer:
|
||||
else:
|
||||
self.set_alpha_value(0)
|
||||
|
||||
|
||||
|
||||
|
||||
def reload(self, layer, is_current=False):
|
||||
self.exit()
|
||||
self.player_running = False
|
||||
@@ -156,7 +149,6 @@ class AltVideoPlayer:
|
||||
except:
|
||||
pass
|
||||
|
||||
|
||||
## not sure if i am going to implement this atm
|
||||
def set_screen_size_for_dev_mode(self):
|
||||
if self.data.settings['system']['DEV_MODE_RESET']['value'] == 'on':
|
||||
@@ -165,17 +157,3 @@ class AltVideoPlayer:
|
||||
else:
|
||||
aspect_mode = self.data.settings['video']['SCREEN_MODE']['value']
|
||||
return False, '--aspect-mode', aspect_mode
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
@@ -1,8 +1,10 @@
|
||||
import datetime
|
||||
import fractions
|
||||
import os
|
||||
import subprocess
|
||||
import datetime
|
||||
|
||||
import picamera
|
||||
import fractions
|
||||
|
||||
|
||||
class Capture(object):
|
||||
PREVIEW_LAYER = 255
|
||||
@@ -21,7 +23,6 @@ class Capture(object):
|
||||
|
||||
## some capture settings
|
||||
|
||||
|
||||
def create_capture_device(self):
|
||||
if self.data.settings['capture']['TYPE']['value'] != 'usb':
|
||||
if self.use_capture:
|
||||
@@ -68,7 +69,6 @@ class Capture(object):
|
||||
self.device.framerate = self.framerate
|
||||
self.device.resolution = self.resolution
|
||||
|
||||
|
||||
def start_preview(self):
|
||||
if self.use_capture == False:
|
||||
self.message_handler.set_message('INFO', 'capture not enabled')
|
||||
@@ -94,7 +94,6 @@ class Capture(object):
|
||||
else:
|
||||
self.sensor_mode = 0
|
||||
|
||||
|
||||
def set_preview_screen_size(self):
|
||||
if self.data.settings['system']['DEV_MODE_RESET']['value'] == 'on':
|
||||
self.device.preview.fullscreen = False
|
||||
@@ -170,7 +169,6 @@ class Capture(object):
|
||||
error_info = e
|
||||
self.message_handler.set_message('ERROR', error_info)
|
||||
|
||||
|
||||
def wait_for_recording_to_save(self, process, name):
|
||||
print('the poll is {}'.format(process.poll()))
|
||||
if process.poll() is not None:
|
||||
@@ -253,4 +251,3 @@ class Capture(object):
|
||||
|
||||
def receive_recording_finished(self, path, value):
|
||||
pass
|
||||
|
||||
|
||||
@@ -1,10 +1,12 @@
|
||||
import os
|
||||
import subprocess
|
||||
import datetime
|
||||
import fractions
|
||||
import picamera
|
||||
import os
|
||||
import subprocess
|
||||
import time
|
||||
|
||||
import picamera
|
||||
|
||||
|
||||
class OfCapture(object):
|
||||
def __init__(self, root, osc_client, message_handler, data):
|
||||
self.root = root
|
||||
@@ -35,7 +37,6 @@ class OfCapture(object):
|
||||
self.has_capture = True
|
||||
return True
|
||||
|
||||
|
||||
def piCapture_with_no_source(self):
|
||||
is_piCapture = subprocess.check_output(['pivideo', '--query', 'ready'])
|
||||
if 'Video Processor was not found' not in str(is_piCapture):
|
||||
@@ -133,7 +134,6 @@ class OfCapture(object):
|
||||
self.wait_for_raw_file()
|
||||
# set status to saving
|
||||
|
||||
|
||||
def wait_for_raw_file(self):
|
||||
if os.path.exists(self.video_dir + 'raw.h264'):
|
||||
mp4box_process, recording_name = self.convert_raw_recording()
|
||||
@@ -167,7 +167,6 @@ class OfCapture(object):
|
||||
error_info = e
|
||||
self.message_handler.set_message('ERROR', error_info)
|
||||
|
||||
|
||||
def wait_for_recording_to_save(self, process, name):
|
||||
print('the poll is {}'.format(process.poll()))
|
||||
if process.poll() is not None:
|
||||
@@ -224,6 +223,3 @@ class OfCapture(object):
|
||||
return int(1000000 / self.framerate)
|
||||
else:
|
||||
return int(fractions.Fraction(setting_value) * 1000000)
|
||||
|
||||
|
||||
|
||||
|
||||
@@ -1,8 +1,10 @@
|
||||
import display_centre.menu as menu
|
||||
import os
|
||||
from statistics import mean
|
||||
|
||||
import display_centre.menu as menu
|
||||
from data_centre.plugin_collection import ModulationReceiverPlugin
|
||||
|
||||
|
||||
class Shaders(object):
|
||||
MENU_HEIGHT = 10
|
||||
EMPTY_SHADER = dict(name='none', is_shader=True, shad_type='-', param_number=4, path='-')
|
||||
@@ -56,7 +58,6 @@ class Shaders(object):
|
||||
shaders_menu_list.append(dict(name=line['name'], is_shader=False, shad_type='', param_number=None, path=None))
|
||||
return shaders_menu_list
|
||||
|
||||
|
||||
def get_path_for_shader(self, file_name):
|
||||
######## returns full path for a given file name ########
|
||||
for path in self.data.PATHS_TO_SHADERS:
|
||||
@@ -77,7 +78,6 @@ class Shaders(object):
|
||||
else:
|
||||
return '-'
|
||||
|
||||
|
||||
def determine_shader_parameter_number(self, path):
|
||||
max_amount = 4
|
||||
if True: # for now always assume 4 params
|
||||
@@ -240,8 +240,10 @@ class Shaders(object):
|
||||
# TODO: read from list of input formulas, from plugins etc to modulate the value
|
||||
temp_amount = amount + (value * level)
|
||||
# print("from amount %s, modulation is %s, temp_amount is %s" % (amount, modulation, temp_amount))
|
||||
if temp_amount < 0: temp_amount = 0 # input range is 0-1 so convert back
|
||||
if temp_amount > 1: temp_amount = 1 # modulation however is -1 to +1
|
||||
if temp_amount < 0:
|
||||
temp_amount = 0 # input range is 0-1 so convert back
|
||||
if temp_amount > 1:
|
||||
temp_amount = 1 # modulation however is -1 to +1
|
||||
|
||||
return temp_amount
|
||||
|
||||
@@ -292,4 +294,3 @@ class Shaders(object):
|
||||
def set_speed_layer_to_amount(self, layer, amount):
|
||||
self.osc_client.send_message("/shader/{}/speed".format(str(layer)), amount)
|
||||
self.selected_speed_list[layer] = amount
|
||||
|
||||
|
||||
@@ -1,8 +1,8 @@
|
||||
from video_centre.video_player import VideoPlayer
|
||||
from video_centre.alt_video_player import AltVideoPlayer
|
||||
from video_centre.video_player import VideoPlayer
|
||||
|
||||
|
||||
class VideoDriver(object):
|
||||
|
||||
MAX_LAYER = 254
|
||||
|
||||
def __init__(self, root, osc_client, message_handler, data):
|
||||
@@ -31,8 +31,6 @@ class VideoDriver(object):
|
||||
self.root.after(self.delay, self.begin_playing)
|
||||
# self.print_status()
|
||||
|
||||
|
||||
|
||||
def update_video_settings(self):
|
||||
self.switch_on_finish = self.data.settings['sampler']['ON_FINISH']['value'] == 'switch'
|
||||
self.loop_parallel = self.data.settings['sampler']['LOOP_TYPE']['value'] == 'parallel'
|
||||
@@ -114,7 +112,6 @@ class VideoDriver(object):
|
||||
else:
|
||||
self.in_next_load_cycle = False
|
||||
|
||||
|
||||
def get_player_info_for_status(self):
|
||||
return self.current_player.bankslot_number, self.current_player.status, self.current_player.alpha, \
|
||||
self.next_player.bankslot_number, self.next_player.status, self.next_player.alpha
|
||||
|
||||
@@ -1,5 +1,6 @@
|
||||
from omxplayer.player import OMXPlayer
|
||||
|
||||
|
||||
class VideoPlayer:
|
||||
def __init__(self, root, message_handler, data, name):
|
||||
self.root = root
|
||||
@@ -20,7 +21,6 @@ class VideoPlayer:
|
||||
self.alpha = 0
|
||||
self.show_toggle_on = False
|
||||
|
||||
|
||||
def try_load(self, layer, is_current=False):
|
||||
load_attempts = 0
|
||||
while (load_attempts < 2):
|
||||
@@ -34,7 +34,6 @@ class VideoPlayer:
|
||||
self.status = 'ERROR'
|
||||
return False
|
||||
|
||||
|
||||
def load(self, layer, is_current=False):
|
||||
# try:
|
||||
self.get_context_for_player(is_current)
|
||||
@@ -187,5 +186,3 @@ class VideoPlayer:
|
||||
else:
|
||||
aspect_mode = self.data.settings['video']['SCREEN_MODE']['value']
|
||||
return False, '--aspect-mode', aspect_mode
|
||||
|
||||
|
||||
|
||||
Reference in New Issue
Block a user