diff --git a/vRuffle.py b/vRuffle.py index a23648f..ba2d1be 100644 --- a/vRuffle.py +++ b/vRuffle.py @@ -4,6 +4,7 @@ import random import time import itertools +from perlin_noise import PerlinNoise ############### ### GLOBALS ### @@ -16,9 +17,11 @@ MIN_SAND = 0.1 MAX_SAND = 0.3 +SAND_RANGE = (MIN_SAND, MAX_SAND) MIN_COLOR = np.array([245, 225, 160]) MAX_COLOR = np.array([255, 255, 255]) +COLOR_RANGE = (MIN_COLOR, MAX_COLOR) MAX_VEL = 150 @@ -52,9 +55,31 @@ def blur(a): return arraylist_sum def transformRange(val, r1, r2): - perc = np.linalg.norm(val - r1[0]) / np.linalg.norm(r1[1] - r1[0]) + normalize = np.vectorize(np.linalg.norm) + perc = normalize(val - r1[0]) / normalize(r1[1] - r1[0]) + if len(np.shape(r2[0])) > 0: perc = np.expand_dims(perc, axis=-1) return r2[0] + perc * (r2[1] - r2[0]) +def generateNoise(baseOctaves, numComponents, decayRate): + # baseOctave increases the zoom, numComponents increases the detail + noises, coeffs = [], [] + for i in range(numComponents): + + coeff = decayRate**i + noises.append(PerlinNoise(octaves=baseOctaves / coeff)) + coeffs.append(coeff) + + def getNoise(pnt): + val = 0 + for i in range(numComponents): + noise, coeff = noises[i], coeffs[i] + val += coeff * noise(pnt) + return val + + absThresh = np.sqrt(0.5) * sum(coeffs) + + return getNoise, absThresh + class PlayingField: def __init__(self,left1,left2,left3,left4,right1,right2,right3,right4): self.left1 = left1 @@ -67,27 +92,29 @@ def __init__(self,left1,left2,left3,left4,right1,right2,right3,right4): self.right4 = right4 self.sandBoard = np.ones((tableWidth, tableHeight)) * MIN_SAND self.colorGradient = np.ones((tableWidth, tableHeight, 3)) * MIN_COLOR - choice = random.randint(0,2) + choice = 3#random.randint(0,3) # if choice == 0: # print("constant sanding") # self.fill_board(self.const_sand) if choice == 0: print('slow mid sanding') - self.fill_board(self.slow_mid) + filler = self.slow_mid elif choice == 1: print("slow outer sanding") - self.fill_board(self.slow_outer) + filler = self.slow_outer elif choice == 2: print("staggered sanding") - self.fill_board(self.staggered) + filler = self.staggered + elif choice == 3: + print("noisy sanding") + filler = self.build_noisy_filler(24, numComponents=3, decayRate=0.7) + self.fill_board(filler) def __setitem__(self, idx, val): self.sandBoard[idx] = val - self.colorGradient[idx] = transformRange( - self.sandBoard[idx], - (MIN_SAND, MAX_SAND), - (MIN_COLOR, MAX_COLOR) - ) + self.colorGradient[idx] = transformRange(self.sandBoard[idx], + SAND_RANGE, + COLOR_RANGE) def __getitem__(self, idx): return self.sandBoard[idx] @@ -155,6 +182,15 @@ def staggered(self, i, j): else: return random.uniform(third_qtl_sand, MAX_SAND) + def build_noisy_filler(self, octaves, numComponents=1, decayRate=0.5): + noise, absThresh = generateNoise(octaves, numComponents, decayRate) + noiseRange = (-absThresh, absThresh) + windowSize = max(tableWidth, tableHeight) + def noisy_filler(i, j): + noiseVal = noise([i/windowSize, j/windowSize]) + return transformRange(noiseVal, noiseRange, SAND_RANGE) + return noisy_filler + class Puck: def __init__(self,num,pos,vel=np.array([0,0])): self.radius = 15