Revert "Merge branch 'dev_frame_objects' into feature_plugins"

This reverts commit 9d5792e1c9, reversing
changes made to 44ab20cb52.
This commit is contained in:
Tristan Rowley
2020-02-12 00:02:05 +00:00
parent 9d5792e1c9
commit 421e2dc6ed
8 changed files with 12 additions and 613 deletions

View File

@@ -1,8 +1,8 @@
# Auto-generated Actions list # Auto-generated Actions list
Sun 9 Feb 16:03:51 UTC 2020 Sun 9 Feb 15:57:04 UTC 2020
for branch=feature_plugins_shader_gadgets for branch=feature_plugins
# Methods # Methods
* change_composite_setting(setting_value) * change_composite_setting(setting_value)
@@ -180,24 +180,6 @@ for branch=feature_plugins_shader_gadgets
* ([A-Z0-9]+)>(.*) (from ManipulatePlugin) * ([A-Z0-9]+)>(.*) (from ManipulatePlugin)
* (.*)>&(.*) (from ManipulatePlugin) * (.*)>&(.*) (from ManipulatePlugin)
* (.*)&&(.*) (from MultiActionsPlugin) * (.*)&&(.*) (from MultiActionsPlugin)
* run_automation (from ShaderLoopRecordPlugin)
* stop_automation (from ShaderLoopRecordPlugin)
* toggle_pause_automation (from ShaderLoopRecordPlugin)
* pause_automation (from ShaderLoopRecordPlugin)
* toggle_loop_automation (from ShaderLoopRecordPlugin)
* set_automation_speed (from ShaderLoopRecordPlugin)
* toggle_record_automation (from ShaderLoopRecordPlugin)
* toggle_overdub_automation (from ShaderLoopRecordPlugin)
* clear_automation (from ShaderLoopRecordPlugin)
* select_automation_clip_([0-7]) (from ShaderLoopRecordPlugin)
* toggle_automation_clip_([0-7]) (from ShaderLoopRecordPlugin)
* load_presets (from ShaderQuickPresetPlugin)
* save_presets (from ShaderQuickPresetPlugin)
* store_next_preset (from ShaderQuickPresetPlugin)
* store_current_preset (from ShaderQuickPresetPlugin)
* switch_to_preset_([0-%i]) (from ShaderQuickPresetPlugin)
* select_preset_([0-%i]) (from ShaderQuickPresetPlugin)
* clear_current_preset (from ShaderQuickPresetPlugin)
* test_plugin (from TestPlugin) * test_plugin (from TestPlugin)
* cycle_shaders (from TestPlugin) * cycle_shaders (from TestPlugin)
* run_automation (from TestPlugin) * run_automation (from TestPlugin)

View File

@@ -1,23 +1,3 @@
This is doctea's experimental 'plugins' branch, including 'shader gadget' plugins.
Started adding some documentation for some of these features on the wiki here:
* https://github.com/langolierz/r_e_c_u_r/wiki/Sound-reactivity
* https://github.com/langolierz/r_e_c_u_r/wiki/using-the-modulation-parameters
* https://github.com/langolierz/r_e_c_u_r/wiki/Plugins
Some quick notes, including about how the modulation features work:-
* Plugins are python classes... With adaptations to recur main code to look up actions in plugins of ActionPlugin class, so plugins can provide extra actions that can be mapped to midi/keyboard/osc
* Here's the really primitive soundreact app: https://github.com/doctea/r_e_c_u_r/blob/feature_midi_feedback_plugin/helpers/soundreact.py
* All it does is send OSC messages based on the volume (the threshold stuff doesn't work and isn't actually activated)
* So then if you look in https://github.com/doctea/r_e_c_u_r/blob/feature_midi_feedback_plugin/json_objects/osc_action_mapping.json you'll see that the "/volume" osc address is bound to the set_modulation_...._value action
* So that way the modulation value is set for 'mod slot 1' to the volume value
* Then when recur is sending paramwter values to the conjur side, it calculates the value to send based on the mod slot level (changed using set_modulation..._level actions mapped in midi APC key25 JSON) and mod slot values
* So you there's 4 modulation parameters and you can assign them, with level, to any of the shader parameters as desired, and feed in params from any source into each mod slot
* At moment there's 3 types of plugin which can also be combined: midifeedback for showing leds etc on controllers that support it like APC Key 25 and Launchpad to indicate recur status, actions for adding new actions, and sequences for running short or looped sequences and adjusting speed etc
* Demo useful plugins are here in this shader gadgets branch, demonstrating shader presets and automation recording
Any questions ask me doctea@gmail.com, find me on facebook or open an issue or something :)
# r_e_c_u_r # r_e_c_u_r

View File

@@ -3,7 +3,6 @@ import os
import pkgutil import pkgutil
import re import re
from plugins.frame_manager import FrameManager, Frame
class Plugin(object): class Plugin(object):
"""Base class that each plugin must inherit from. within this class """Base class that each plugin must inherit from. within this class
@@ -211,16 +210,16 @@ class DisplayPlugin(Plugin):
def __init__(self, plugin_collection): def __init__(self, plugin_collection):
super().__init__(plugin_collection) super().__init__(plugin_collection)
def is_handled(self, name): def is_handled(self, name):
raise NotImplementedError raise NotImplementedError
def get_display_modes(self): def get_display_modes(self):
raise NotImplementedError raise NotImplementedError
def show_plugin(self, display): def show_plugin(self, display):
from tkinter import Text, END from tkinter import Text, END
#display_text.insert(END, 'test from DisplayPlugin') #display_text.insert(END, 'test from DisplayPlugin')
display.display_text.insert(END, '{} \n'.format(display.body_title)) display.display_text.insert(END, '{} \n'.format(display.body_title))
class ModulationReceiverPlugin(Plugin): class ModulationReceiverPlugin(Plugin):
def __init__(self, plugin_collection): def __init__(self, plugin_collection):
@@ -260,8 +259,6 @@ class PluginCollection(object):
#self.actions = message_handler.actions #self.actions = message_handler.actions
self.reload_plugins() self.reload_plugins()
self.fm = FrameManager(self)
def read_json(self, file_name): def read_json(self, file_name):
return self.data._read_plugin_json(file_name) return self.data._read_plugin_json(file_name)
def update_json(self, file_name, data): def update_json(self, file_name, data):

View File

@@ -1,199 +0,0 @@
import data_centre.plugin_collection
from data_centre.plugin_collection import ActionsPlugin, SequencePlugin
from plugins.frame_manager import Frame
class ShaderLoopRecordPlugin(ActionsPlugin,SequencePlugin):
disabled = False
MAX_CLIPS = 8
frames = []
def __init__(self, plugin_collection):
super().__init__(plugin_collection)
self.PRESET_FILE_NAME = "ShaderLoopRecordPlugin/frames.json"
#TODO: this doesnt work
"""self.frames = [
[
Frame(self.pc).store_copy(f)
for f in [
z for z in [
frame for frame in [
clip for clip in self.load_presets()
]
]
]
]
]"""
for clip in self.load_presets():
c = []
for frame in clip:
c.append(Frame(self.pc).store_copy(frame))
self.frames.append(c)
self.reset_ignored()
def load_presets(self):
#try:
print("trying load presets? %s " % self.PRESET_FILE_NAME)
p = self.pc.read_json(self.PRESET_FILE_NAME)
if p:
while len(p)<self.MAX_CLIPS:
print ("adding clip ")
p += self.get_empty_clip(self.duration) #[ [None] ] #*((int(self.duration / self.frequency))-len(p)) ]
for i in p:
print("got automation clip of duration %s" % len(i))
if i and len(i)<(int(self.duration / self.frequency)):
print("adding more slots due to size change")
i += [None]*((int(self.duration / self.frequency))-len(i))
print("len is now %s" % len(i))
return p
elif p:
return p
else:
return self.get_factory_reset()
#except:
# return self.clear_frames()
def save_presets(self):
self.pc.update_json(self.PRESET_FILE_NAME, self.frames)
@property
def parserlist(self):
return [
( r"run_automation", self.run_automation ),
( r"stop_automation", self.stop_automation ),
( r"toggle_pause_automation", self.toggle_pause_automation ),
( r"pause_automation", self.pause_automation ),
( r"toggle_loop_automation", self.toggle_loop_automation ),
( r"set_automation_speed", self.set_speed ),
( r"toggle_record_automation", self.toggle_record_automation ),
( r"toggle_overdub_automation", self.toggle_overdub_automation ),
( r"clear_automation", self.clear_clip ),
( r"select_automation_clip_([0-7])", self.select_clip ),
( r"toggle_automation_clip_([0-7])", self.toggle_clip )
]
def toggle_overdub_automation(self):
self.overdub = not self.overdub
if not self.overdub:
self.reset_ignored()
def toggle_record_automation(self):
self.recording = not self.recording
if self.recording and not self.overdub:
self.clear_clip()
if not self.recording:
self.reset_ignored()
self.last_frame = None
self.last_saved_index = None
self.save_presets()
def get_empty_clip(self, duration = 2000):
return [None] * (int(duration / self.frequency))
def get_factory_reset(self):
return [ self.get_empty_clip(self.duration) for i in range(self.MAX_CLIPS) ]
def clear_clip(self,clip = None):
if clip is None:
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)))
return self.frames
def toggle_clip(self,clip = None):
if clip is None:
clip = self.selected_clip
else:
self.selected_clip = clip
#self.running_clips[clip] = not self.running_clips[clip]
if clip in self.running_clips:
self.running_clips.remove(clip)
else:
self.running_clips.append(clip)
print("running clips looks like %s" %self.running_clips)
def reset_ignored(self):
# print("!!!!resetting ignored")
self.ignored = Frame(self.pc).store_copy({ 'shader_params': [[None]*4,[None]*4,[None]*4] })
def is_ignoring(self):
return not self.pc.fm.is_frame_empty(self.ignored)
def select_clip(self, clip):
self.selected_clip = clip
selected_clip = 0
running_clips = [ ] #False ] * self.MAX_CLIPS
duration = 2000
frequency = 10 #25
recording = False
overdub = True
#ignored = None # set in reset_ignored in init - used for tracking what parans have changed since overdub
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:
current_frame_index = (self.duration/self.frequency) - current_frame_index
if current_frame_index > self.duration/self.frequency:
current_frame_index = self.duration/self.frequency
if self.DEBUG_FRAMES: print (">>>>>>>>>>>>>>frame at %i%%: %i" % (position*100, current_frame_index))
#print("got frame index %s" % current_frame_index)
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'])
#print ("%s clips, looks like %s" % (len(self.frames),self.frames))
#print("selected_clip is %s "%selected_clip)
#clip = self.frames[selected_clip]
if self.is_playing() and self.recording and self.selected_clip not in self.running_clips:
self.running_clips += [ self.selected_clip ]
for selected_clip in self.running_clips:
saved_frame = self.frames[selected_clip][current_frame_index]
if not self.recording or (selected_clip!=self.selected_clip):
self.pc.fm.recall_frame(saved_frame)
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'])
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.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'])
self.ignored = self.pc.fm.merge_frames(self.ignored, diff)
print("about to call get_ignored_frames with %s\n and\n %s" % (saved_frame.f, self.ignored.f))
diff = self.pc.fm.merge_frames(
self.pc.fm.get_frame_ignored(saved_frame, self.ignored),
diff
)
#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']))
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:
if self.DEBUG_FRAMES: print ("last_saved_index is %s, current_frame_index is %s" % (self.last_saved_index, current_frame_index))
for i in range(current_frame_index - (self.last_saved_index) ):
if self.DEBUG_FRAMES:print("backfilling frame %s" % ((self.last_saved_index+i+1)%len(self.frames[selected_clip])))
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)
"""def recall_frame_index(self, index):
self.pc.shaders.recall_frame_params(self.frames[index].copy())"""

View File

@@ -1,85 +0,0 @@
import data_centre.plugin_collection
from data_centre.plugin_collection import ActionsPlugin, SequencePlugin
import copy
from plugins.frame_manager import Frame
class ShaderQuickPresetPlugin(ActionsPlugin): #,SequencePlugin):
disabled = False
MAX_PRESETS = 8
def __init__(self, plugin_collection):
super().__init__(plugin_collection)
self.PRESET_FILE_NAME = 'ShaderQuickPresetPlugin/presets.json'
self.presets = self.load_presets()
print("loaded presets %s" % self.presets)
self.selected_preset = None
self.last_recalled = None
def load_presets(self):
print("trying load presets? %s " % self.PRESET_FILE_NAME)
return [ Frame(self.pc).store_copy(x) for x in (self.pc.read_json(self.PRESET_FILE_NAME) or ([None]*self.MAX_PRESETS)) ]
def save_presets(self):
self.pc.update_json(self.PRESET_FILE_NAME, self.presets)
@property
def parserlist(self):
return [
( r"load_presets", self.load_presets ),
( r"save_presets", self.save_presets ),
( r"store_next_preset", self.store_next_preset ),
( r"store_current_preset", self.store_current_preset ),
( r"switch_to_preset_([0-%i])"%self.MAX_PRESETS, self.switch_to_preset ),
( r"select_preset_([0-%i])"%self.MAX_PRESETS, self.select_preset ),
( r"clear_current_preset", self.clear_current_preset ),
]
def store_next_preset(self):
res = [i for i, val in enumerate(self.presets) if val == None]
if res is None or not res:
self.selected_preset += 1
self.selected_preset %= self.MAX_PRESETS
else:
self.selected_preset = res[0]
self.store_current_preset()
def clear_current_preset(self):
if self.selected_preset is None:
return
self.presets[self.selected_preset] = None
self.save_presets()
def store_current_preset(self):
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()
#print ("stored %s at position %s" % (self.presets[insert_position], insert_position))
self.selected_preset = insert_position
self.last_recalled = insert_position
self.save_presets()
def select_preset(self, preset):
self.selected_preset = preset
def switch_to_preset(self, preset):
#if preset>len(self.presets):
if self.presets[preset] is None:
print ("no quick shader preset in slot %s!" % preset)
self.selected_preset = preset
return
print ("switching to preset %s" % preset)
self.selected_preset = preset
self.last_recalled = preset
preset = self.presets[preset]
print ("recalled preset %s" % preset)
self.pc.fm.recall_frame(preset)

View File

@@ -1,8 +1,8 @@
import data_centre.plugin_collection import data_centre.plugin_collection
from data_centre.plugin_collection import ActionsPlugin, SequencePlugin from data_centre.plugin_collection import ActionsPlugin, SequencePlugin
class MidiActionsTestPlugin(ActionsPlugin,SequencePlugin): class TestPlugin(ActionsPlugin,SequencePlugin):
disabled = True disabled = False
def __init__(self, plugin_collection): def __init__(self, plugin_collection):
super().__init__(plugin_collection) super().__init__(plugin_collection)

View File

@@ -1,278 +0,0 @@
import copy
import json
from json import JSONEncoder
def _default(self, obj):
if getattr(obj.__class__,'to_json'):
#return _default.default(obj.to_json())
return obj.to_json()
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
DEBUG_FRAMES = False#True
def __init__(self, pc):
import copy #from copy import deepcopy
self.pc = pc
def to_json(self):
return self.f #{ 'f': self.f }
def store_live(self):
frame = {
'selected_shader_slots': [ shader.get('slot',None) for shader in self.pc.shaders.selected_shader_list ],
'shader_params': copy.deepcopy(self.pc.shaders.selected_param_list),
'layer_active_status': copy.deepcopy(self.pc.shaders.selected_status_list),
'feedback_active': self.pc.shaders.data.feedback_active,
'x3_as_speed': self.pc.shaders.data.settings['shader']['X3_AS_SPEED']['value'],
'shader_speeds': copy.deepcopy(self.pc.shaders.selected_speed_list),
'strobe_amount': self.pc.shaders.data.settings['shader']['STROBE_AMOUNT']['value'] / 10.0
}
self.f = frame
#print("built frame: %s" % frame['shader_params'])
return self
def store_copy(self, f):
print("told to store_copy %s" % f)
if f is not None:
if f.get('f') is not None: #isinstance(f, Frame):
f = f.get('f')
return self.store_copy(f.get('f'))
self.f = f
else:
self.f = {}
return self
def recall_frame_params(self):
#print("recall_frame_params got: %s" % preset.get('shader_params'))
for (layer, param_list) in enumerate(self.f.get('shader_params',[])):
if param_list:
for param,value in enumerate(param_list):
#if (ignored is not None and ignored['shader_params'][layer][param] is not None):
# print ("ignoring %s,%s because value is %s" % (layer,param,ignored['shader_params'][layer][param]))
# continue
if (value is not None):
#print("recalling layer %s param %s: value %s" % (layer,param,value))
self.pc.actions.call_method_name('set_the_shader_param_%s_layer_%s_continuous' % (param,layer), value)
if self.f.get('feedback_active') is not None:
self.pc.data.feedback_active = self.f.get('feedback_active',self.pc.data.feedback_active)
if self.pc.data.feedback_active:
self.pc.actions.call_method_name('enable_feedback')
else:
self.pc.actions.call_method_name('disable_feedback')
if self.f.get('x3_as_speed') is not None:
self.pc.data.settings['shader']['X3_AS_SPEED']['value'] = self.f.get('x3_as_speed',self.pc.data.settings['shader']['X3_AS_SPEED']['value'])
"""if self.data.settings['shader']['X3_AS_SPEED']['value']:
self.data.plugins.actions.call_method_name('enable_x3_as_speed')
else:
self.data.plugins.actions.call_method_name('disable_x3_as_speed')"""
for (layer, speed) in enumerate(self.f.get('shader_speeds',[])):
if speed is not None:
self.pc.actions.call_method_name('set_shader_speed_layer_%s_amount' % layer, speed)
if self.f.get('strobe_amount') is not None:
self.pc.actions.set_strobe_amount_continuous(self.f.get('strobe_amount'))
def recall_frame(self):
preset = self
if preset.f is None:
return
self.pc.data.settings['shader']['X3_AS_SPEED']['value'] = preset.f.get('x3_as_speed')
# x3_as_speed affects preset recall, so do that first
self.recall_frame_params()
for (layer, slot) in enumerate(preset.f.get('selected_shader_slots',[])):
if slot is not None:
#print("setting layer %s to slot %s" % (layer, slot))
self.pc.actions.call_method_name('play_shader_%s_%s' % (layer, slot))
for (layer, active) in enumerate(preset.f.get('layer_active_status',[])):
# print ("got %s layer with status %s " % (layer,active))
if active=='':
self.pc.actions.call_method_name('start_shader_layer_%s' % layer)
else:
self.pc.actions.call_method_name('stop_shader_layer_%s' % layer)
def merge(self, frame2):
from copy import deepcopy
f = deepcopy(self.f) #frame1.copy()
#if self.DEBUG_FRAMES: print("merge_frames: got frame1\t%s" % frame1)
#if self.DEBUG_FRAMES: print("merge_frames: got frame2\t%s" % frame2)
for i,f2 in enumerate(frame2.f.get('shader_params')):
for i2,p in enumerate(f2):
if p is not None:
if 'shader_params' not in f:
f['shader_params'] = [[None]*4,[None]*4,[None]*4]
f['shader_params'][i][i2] = p
if frame2.f.get('feedback_active') is not None:
f['feedback_active'] = frame2['feedback_active']
if frame2.f.get('x3_as_speed') is not None:
f['x3_as_speed'] = frame2.f.get('x3_as_speed')
if f.get('shader_speeds') is None:
if 'shader_speeds' in frame2.f:
f['shader_speeds'] = frame2.f.get('shader_speeds')
else:
for i,s in enumerate(frame2.f.get('shader_speeds')):
if s is not None:
f['shader_speeds'][i] = s
if frame2.f.get('strobe_amount'):
f['strobe_amount'] = frame2.f.get('strobe_amount')
if self.DEBUG_FRAMES: print("merge_frames: got return\t%s" % f)
return Frame(self.pc).store_copy(f)
def get_ignored(self, ignored):
from copy import deepcopy
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)
for i,f2 in enumerate(frame.get('shader_params',[])):
for i2,p in enumerate(f2):
if ignored['shader_params'][i][i2] is not None:
f['shader_params'][i][i2] = None
if ignored.get('feedback_active') is not None:
f['feedback_active'] = None
if ignored.get('x3_as_speed') is not None:
f['x3_as_speed'] = None
if ignored.get('shader_speeds') is not None and frame.get('shader_speeds') is not None:
for i,s in enumerate(frame.get('shader_speeds')):
if ignored['shader_speeds'][i] is not None:
f['shader_speeds'][i] = None
if ignored.get('strobe_amount') is not None:
f['strobe_amount'] = None
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 frame.get('feedback_active') is not None:
return False
if frame.get('x3_as_speed') is not None:
return False
if frame.get('strobe_amount') is not None:
return False
for i,f in enumerate(frame['shader_params']):
for i2,p in enumerate(f):
if p is not None: #ignored['shader_params'][i][i2] is not None:
return False
if frame.get('shader_speeds') is not None:
for i,f in enumerate(frame['shader_speeds']):
if f is not None:
return False
if self.DEBUG_FRAMES: print("is_frame_empty: got return true")
return True
def get_diff(self, current_frame):
#if not last_frame: return current_frame
current_frame = current_frame.f
last_frame = self.f
if self.DEBUG_FRAMES:
print(">>>>get_frame_diff>>>>")
print("last_frame: \t%s" % last_frame['shader_params'])
print("current_frame: \t%s" % current_frame['shader_params'])
param_values = [[None]*4,[None]*4,[None]*4]
for layer,params in enumerate(current_frame.get('shader_params',[[None]*4]*3)):
#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))
param_values[layer][param] = p
if current_frame['feedback_active'] is not None and last_frame['feedback_active'] != current_frame['feedback_active']:
feedback_active = current_frame['feedback_active']
else:
feedback_active = None
if current_frame['x3_as_speed'] is not None and last_frame['x3_as_speed'] != current_frame['x3_as_speed']:
x3_as_speed = current_frame['x3_as_speed']
else:
x3_as_speed = None
speed_values = [None]*3
for layer,param in enumerate(current_frame.get('shader_speeds',[None]*3)):
if param is not None and param != last_frame['shader_speeds'][layer]:
speed_values[layer] = param
if current_frame['strobe_amount'] is not None and last_frame['strobe_amount'] != current_frame['strobe_amount']:
strobe_amount = current_frame['strobe_amount']
else:
strobe_amount = None
if self.DEBUG_FRAMES:
print("param_values is\t%s" % param_values)
print("speed_values is\t%s" % speed_values)
diff = {
'shader_params': param_values,
'feedback_active': feedback_active,
'x3_as_speed': x3_as_speed,
'shader_speeds': speed_values,
'strobe_amount': strobe_amount,
}
if self.DEBUG_FRAMES: print("returning\t%s\n^^^^" % diff['shader_params'])
return Frame(self.pc).store_copy(diff)
class FrameManager:
pc = None
def __init__(self, pc):
self.pc = pc
def get_live_frame(self):
return Frame(self.pc).store_live()
def recall_frame_params(self, preset):
if preset is None:
return
preset.recall_frame_params()
def recall_frame(self, preset):
if preset is None:
return
preset.recall_frame()
# overlay frame2 on frame1
def merge_frames(self, frame1, frame2):
return frame1.merge(frame2)
def get_frame_ignored(self, frame, ignored):
return frame.get_ignored(ignored)
def is_frame_empty(self, frame):
return frame.is_empty()
def get_frame_diff(self, last_frame, current_frame):
return last_frame.get_diff(current_frame)

View File

@@ -20,6 +20,8 @@ class Shaders(object):
self.selected_modulation_slot = 0 self.selected_modulation_slot = 0
self.selected_status_list = ['-','-','-'] ## going to try using symbols for this : '-' means empty, '▶' means running, '■' means not running, '!' means error self.selected_status_list = ['-','-','-'] ## going to try using symbols for this : '-' means empty, '▶' means running, '■' means not running, '!' means error
self.selected_modulation_level = [[[0.0,0.0,0.0,0.0] for i in range(4)] for i in range(3)]
self.modulation_value = [0.0,0.0,0.0,0.0]
self.selected_param_list = [[0.0,0.0,0.0,0.0] for i in range(3)] self.selected_param_list = [[0.0,0.0,0.0,0.0] for i in range(3)]
self.selected_speed_list = [1.0, 1.0, 1.0] self.selected_speed_list = [1.0, 1.0, 1.0]