1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
|
from __future__ import annotations
from adafruit_ticks import ticks_diff
from .util import hsv_to_rgb
class RGBEffect:
keyboard: Keyboard
prepared: list[Any]
def __init__(self, keyboard: Keyboard):
self.keyboard = keyboard
def prepare(self):
base = self.keyboard.modes["base"]
self.prepared = [self.prepare_key(key) for key in base.keys]
def prepare_key(self, key: Key) -> Any:
pass
def tick(self, ticks_ms: int):
pass
def get_color(self, i: int, key: Key):
pass
class ColorScale(RGBEffect):
def prepare_key(self, key: Key):
in_scale = self.keyboard.scale.is_in_scale(key.pitch)
if in_scale:
return (0.1, 0.9, 0.65)
else:
return (0.3, 0.8, 0.0)
def get_color(self, i: int, key: Key):
if key.pitch < 0 or key.pitch > 127:
return 0
hue, sat, key_val = self.prepared[i]
base = self.keyboard.modes["base"]
extra = base.extra_notes.get(key.pitch)
note_for_pitch = base.notes.get(key.pitch)
note_for_pitch = note_for_pitch or base.notes_expiring.get(key.pitch)
if extra:
return hsv_to_rgb(hue, 1.0, 1.0)
if key.note:
value = 1.0
elif note_for_pitch:
value = note_for_pitch.expiry * 0.3
else:
hue = 0.7
value = 0.0
rest = 1.0 - key_val
value = key_val + value * rest
return hsv_to_rgb(hue, sat, value)
class Rainbow(RGBEffect):
hue_shift: float = 0.0
last_ticks_ms: int
def tick(self, ticks_ms: int):
if hasattr(self, "last_ticks_ms"):
delta = ticks_diff(ticks_ms, self.last_ticks_ms)
self.hue_shift = (self.hue_shift + delta / 1000 / 6) % 1
self.last_ticks_ms = ticks_ms
def prepare(self):
self.hue_shift = 0.0
super().prepare()
def prepare_key(self, key: Key):
return (0, 0.9, 1.0)
def get_color(self, i: int, key: Key):
if key.pitch < 0 or key.pitch > 127:
return 0
x, y = key.pos
hue, sat, val = self.prepared[i]
hue += x / 50 + y / 40 + self.hue_shift
return hsv_to_rgb(hue, sat, val)
class RainbowScale(Rainbow):
def prepare_key(self, key: Key):
if self.keyboard.scale.is_in_scale(key.pitch):
return (0, 0.9, 1)
else:
return (0, 0.75, 0.1)
class RainbowScaleAlt(Rainbow):
def prepare_key(self, key: Key):
if self.keyboard.scale.is_in_scale(key.pitch):
return (0, 0.9, 1)
else:
return (0.2, 0.9, 0.5)
RGB_EFFECTS = {
"scale": ColorScale,
"rainbow": Rainbow,
"rainbow scale": RainbowScale,
"rainbow scale alt": RainbowScaleAlt,
}
|