Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
18 changes: 18 additions & 0 deletions phoenix/composition/colors.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,18 @@
def merge_colors(color_1, color2, method='average'):
if method == 'average':
return (
(color_1[0] + color2[0]) / 2,
(color_1[1] + color2[1]) / 2,
(color_1[2] + color2[2]) / 2
)

color_patterns = {
'psychedelic': [
(255, 235, 0),
(252, 0, 25),
(1, 255, 79),
(255, 1, 215),
(86, 0, 204),
(0, 237, 245)
]
}
81 changes: 81 additions & 0 deletions phoenix/composition/pattern.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,81 @@
import math
from .triangle_patterns import triangle_patterns
from .colors import merge_colors

TRIANGLE = 0
GRID = 1

class Pattern:
def __init__(
self,
type = TRIANGLE,
pattern = 'outer_edge',
tail_length = 6,
colors = [(35, 76, 130)],
tail_colors = [(0, 0, 0)],
children = []
):
self.pattern = pattern
if type == TRIANGLE:
self.pattern_array = triangle_patterns[pattern]
else:
self.pattern_array = None
self.length = len(self.pattern_array)
self.current = 0
self.tail_length = tail_length
self.colors = colors
self.colors_length = len(colors)
self.tail_colors = tail_colors
self.tail_colors_length = len(tail_colors)
self.children = children
self.epochs_elapsed = 0

def next_epoch(self):
self.epochs_elapsed += 1

if self.epochs_elapsed > self.length:
self.epochs_elapsed = 0

return self.epochs_elapsed

def get_next_color(self, colors, colors_length):
first_color = colors[math.floor((self.epochs_elapsed / self.length) * colors_length)]
second_color = colors[math.ceil((self.epochs_elapsed / self.length) * colors_length)]

return merge_colors(first_color, second_color)

def get_next(self, inner_step = 1):
next = self.pattern_array[self.current]
self.current = (self.current+1) % self.length
changes = [(next, self.get_next_color(self.colors, self.colors_length))]

# Get next for children and append to changes
if self.children is not None:
for child_pattern in self.children:
changes.extend(child_pattern.get_next())

self.next_epoch()

return changes

def get_tail(self):
tail = (self.current-self.tail_length) % self.length
tails = [(self.pattern_array[tail], self.get_next_color(self.tail_colors, self.tail_colors_length))]

# Get tail for children
if self.children is not None:
for child_pattern in self.children:
tails.extend(child_pattern.get_tail())

self.next_epoch()
return tails

## not needed?
# def get_range(self):
# range = []
# for i in range(0, self.tail_length):
# address = self.pattern_array[(self.current-i) % self.length]
# range.append(address)
#
# self.current = (self.current+1) % self.length
# return range
File renamed without changes.
114 changes: 114 additions & 0 deletions phoenix/composition/triangle_patterns.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,114 @@
from phoenix.composition.pattern import Pattern
from phoenix.coordinates.triangles import get_addresses_from_edge

def reverse(pattern):
return pattern[::-1]


def cross_pattern_1():
pattern = []
pattern.extend(get_addresses_from_edge(1, 1))
pattern.extend(get_addresses_from_edge(5, 2))
pattern.extend(get_addresses_from_edge(4, 3))
return pattern

def cross_pattern_2():
pattern = []
pattern.extend(get_addresses_from_edge(2, 1))
pattern.extend(get_addresses_from_edge(6, 1))
pattern.extend(get_addresses_from_edge(4, 1))
return pattern

def cross_pattern_3():
pattern = []
pattern.extend(get_addresses_from_edge(3, 2))
pattern.extend(get_addresses_from_edge(7, 2))
pattern.extend(get_addresses_from_edge(4, 2))
return pattern

def cross_pattern_4():
pattern = []
pattern.extend(get_addresses_from_edge(1, 3))
pattern.extend(get_addresses_from_edge(5, 3))
pattern.extend(get_addresses_from_edge(8, 1))
return pattern

def cross_pattern_5():
pattern = []
pattern.extend(get_addresses_from_edge(2, 2))
pattern.extend(get_addresses_from_edge(6, 2))
pattern.extend(get_addresses_from_edge(8, 2))
return pattern

def cross_pattern_6():
pattern = []
pattern.extend(get_addresses_from_edge(3, 3))
pattern.extend(get_addresses_from_edge(7, 2))
pattern.extend(get_addresses_from_edge(8, 3))
return pattern


def flower_right():
pattern = []
pattern.extend(get_addresses_from_edge(3, 2))
pattern.extend(get_addresses_from_edge(7, 1))
pattern.extend(get_addresses_from_edge(8, 2))
pattern.extend(get_addresses_from_edge(4, 1))
pattern.extend(get_addresses_from_edge(6, 2))
pattern.extend(get_addresses_from_edge(2, 1))
return pattern

def flower_left():
pattern = []
pattern.extend(get_addresses_from_edge(3, 3))
pattern.extend(get_addresses_from_edge(7, 3))
pattern.extend(get_addresses_from_edge(8, 3))
pattern.extend(get_addresses_from_edge(4, 3))
pattern.extend(get_addresses_from_edge(5, 3))
pattern.extend(get_addresses_from_edge(1, 1))
return pattern

def outer_edge():
pattern = []
pattern.extend(get_addresses_from_edge(1, 1))
pattern.extend(get_addresses_from_edge(2, 1))
pattern.extend(get_addresses_from_edge(2, 2))
pattern.extend(get_addresses_from_edge(3, 2))
pattern.extend(get_addresses_from_edge(3, 3))
pattern.extend(get_addresses_from_edge(1, 3))
return pattern

def outer_counter_clockwise():
pattern = []
pattern.extend(get_addresses_from_edge(1, 1))
pattern.extend(get_addresses_from_edge(2, 1))
pattern.extend(get_addresses_from_edge(2, 2))
pattern.extend(get_addresses_from_edge(4, 2))
pattern.extend(get_addresses_from_edge(4, 3))
pattern.extend(get_addresses_from_edge(4, 1))
pattern.extend(get_addresses_from_edge(3, 2))
pattern.extend(get_addresses_from_edge(3, 3))
pattern.extend(get_addresses_from_edge(1, 3))
return pattern

def inner_clockwise():
pattern = []
pattern.extend(reverse(get_addresses_from_edge(5, 1)))
pattern.extend(reverse(get_addresses_from_edge(5, 3)))
pattern.extend(reverse(get_addresses_from_edge(5, 2)))
pattern.extend(get_addresses_from_edge(8, 1))
pattern.extend(reverse(get_addresses_from_edge(6, 2)))
pattern.extend(reverse(get_addresses_from_edge(6, 1)))
pattern.extend(reverse(get_addresses_from_edge(6, 3)))
pattern.extend(get_addresses_from_edge(8, 2))
pattern.extend(reverse(get_addresses_from_edge(7, 3)))
pattern.extend(reverse(get_addresses_from_edge(7, 2)))
pattern.extend(reverse(get_addresses_from_edge(7, 1)))
pattern.extend(get_addresses_from_edge(8, 3))
return pattern

triangle_patterns = {
'outer_edge': outer_edge(),
'outer_counter_clockwise': outer_counter_clockwise(),
'inner_clockwise': inner_clockwise()
}
68 changes: 68 additions & 0 deletions phoenix/coordinates/grid.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,68 @@
# Grid is for edge-neighbor based or pixel-neighbor based animations

# x axis is along base of triangle
# y axis is along left edge
# z axis is along right edge, it can be derived from x and y
from .triangles import get_addresses_from_edge

X = 0
Y = 1
Z = 2

class Pixel:
def __init__(
self,
edge,
address
):
self.edge = edge
self.address = address

class Edge:
def __init__(
self,
axis = X,
index = 1,
):
self.axis = axis
self.index = index
self.pixels = self.calc_pixel_addresses()

def calc_pixel_addresses():
pixels = []

return pixels

def get_x_neighbor(self, dir=1):

return self.edge_x_wrap(x, y)

def get_y_neighbor(self, dir=1):

return self.edge_y_wrap(x, y)

def get_z_neighbor(self, dir=1):

return self.edge_z_wrap(x, y)


class Grid:
def __init__(
self,
):
self.edges = []
for i in range(0, Z+1):
axis_edges = []
for j in range(0, 10):
axis_edges.append[Edge(i, j)]
self.edges.append(axis_edges)


class AutomataGrid(Grid):
def __init__(
self,
):
self.super.__init__()

def evolve():
pass
19 changes: 5 additions & 14 deletions phoenix/coordinates/triangles.py
Original file line number Diff line number Diff line change
@@ -1,18 +1,21 @@
# Triangles is for outer and inner triangle based patterns

# Triangle order:
## Outer: Left, right, top, center
## STRIP_INDEX_INNER: Left, right, top, center
## Inner: Left, right, top, center

# Edge order:
## Base down: Bottom, right, top
## Base up: Right, top, left

from phoenix.lights.strip import get_strip_index_from_address, get_address_from_strip_index

STRIP_INDEX_OUTER_LEFT = 1
STRIP_INDEX_OUTER_RIGHT = 2
STRIP_INDEX_INNER = 0

LEDS_PER_OUTER_EDGE = 12
LEDS_PER_INNER_EDGE = 6
LEDS_PER_STRIP = 72

triangles = {
1: {
Expand Down Expand Up @@ -67,18 +70,6 @@ def get_strip_index_from_edge(triangle, edge, index):
strip_index = tri['index'][(edge-1)*tri['edge_length']+index]
return {'strip': strip, 'index': strip_index}

def get_address_from_strip_index(strip, index):
return strip*LEDS_PER_STRIP+index

def get_strip_index_from_address(address):
index = address % LEDS_PER_STRIP
strip = (address - index) / LEDS_PER_STRIP
address = {
'strip': int(strip),
'index': index
}
return address

def get_addresses_from_edge(triangle, edge):
addresses = []
edge_length = triangles[triangle]['edge_length']
Expand Down
2 changes: 1 addition & 1 deletion phoenix/interface/knobs.py
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,7 @@
import board
from rainbowio import colorwheel
from adafruit_seesaw import seesaw, neopixel, rotaryio, digitalio
from phoenix.lights.lights import Strip
from phoenix.lights.strip import Strip

addresses = [0x37, 0x36, 0x3A]

Expand Down
Empty file added phoenix/lights/dimmer.py
Empty file.
Loading