Always-on computer music
Du kan inte välja fler än 25 ämnen Ämnen måste starta med en bokstav eller siffra, kan innehålla bindestreck ('-') och vara max 35 tecken långa.

64 lines
1.6KB

  1. import math
  2. import time
  3. import itertools as it
  4. import cv2
  5. import colorsys
  6. from pythonosc import udp_client
  7. import numpy as np
  8. DENSITY = 4
  9. RED = [0, 0, 255]
  10. N_COLORS = 3
  11. LAST_MESSAGE_TIME = 0
  12. LAST_SNAPSHOT_TIME = 0
  13. def analyze_block(frame, osc, index, sp, ep, send=False):
  14. """ Analyze a block """
  15. block = frame[sp[1]:ep[1], sp[0]:ep[0], 0:3]
  16. average_color = np.average(block, (0, 1)) / 255
  17. h, s, v = colorsys.rgb_to_hsv(*average_color)
  18. # Configure the oscillator
  19. if send:
  20. osc.send_message(
  21. "/radio",
  22. [int(index), float(h),
  23. float(s), float(v), .5])
  24. return frame
  25. def analyze(frame, osc):
  26. """ Analyze the full frame """
  27. global LAST_MESSAGE_TIME, LAST_SNAPSHOT_TIME
  28. height, width, d = frame.shape
  29. n = DENSITY
  30. m = math.ceil(n * (height / width))
  31. dx = width / n
  32. dy = height / m
  33. send = False
  34. if time.time() - LAST_MESSAGE_TIME > 0.1:
  35. LAST_MESSAGE_TIME = time.time()
  36. send = True
  37. if time.time() - LAST_SNAPSHOT_TIME > 2:
  38. LAST_SNAPSHOT_TIME = time.time()
  39. cv2.imwrite("frame.png", frame)
  40. for index, (y, x) in enumerate(it.product(range(m), range(n))):
  41. sp = (int(x * dx), int(y * dy))
  42. ep = (int(x * dx + dx), int(y * dy + dy))
  43. frame = analyze_block(frame, osc, index, sp, ep, send)
  44. return frame
  45. if __name__ == '__main__':
  46. # camera = cv2.VideoCapture("/dev/video2")
  47. camera = cv2.VideoCapture(0)
  48. osc = udp_client.SimpleUDPClient("0.0.0.0", 5005)
  49. print("Radio is running...")
  50. while True:
  51. ret, frame = camera.read()
  52. frame = analyze(frame, osc)
  53. camera.release()