Files
@ 31612b323436
Branch filter:
Location: light9/bcf2000.py - annotation
31612b323436
4.1 KiB
text/x-python
pass packet creation time so collector can see how much lag there is
Ignore-this: aa3fae53817ad8f617822a558f2ae19e
Ignore-this: aa3fae53817ad8f617822a558f2ae19e
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 116 117 | c7478a778992 c7478a778992 c7478a778992 c7478a778992 c7478a778992 c7478a778992 c7478a778992 c7478a778992 c7478a778992 c7478a778992 c7478a778992 c7478a778992 c7478a778992 c7478a778992 c7478a778992 c7478a778992 c7478a778992 c7478a778992 c7478a778992 c7478a778992 c7478a778992 c7478a778992 c7478a778992 c7478a778992 c7478a778992 c7478a778992 c7478a778992 c7478a778992 c7478a778992 c7478a778992 c7478a778992 b2858c2d4a4d ff9c72cfb023 b2858c2d4a4d b2858c2d4a4d c7478a778992 c7478a778992 f5a75dbe96cd c7478a778992 c7478a778992 c7478a778992 bd8a89743226 c7478a778992 c7478a778992 c7478a778992 c7478a778992 551f06733559 c7478a778992 c7478a778992 c7478a778992 c7478a778992 c7478a778992 c7478a778992 c7478a778992 c7478a778992 c7478a778992 c7478a778992 c7478a778992 c7478a778992 c7478a778992 c7478a778992 c7478a778992 c7478a778992 c7478a778992 c7478a778992 c7478a778992 c7478a778992 c7478a778992 c7478a778992 c7478a778992 c7478a778992 c7478a778992 c7478a778992 c7478a778992 c7478a778992 c7478a778992 c7478a778992 c7478a778992 48af0ea86ff4 c7478a778992 c7478a778992 c7478a778992 c7478a778992 c7478a778992 c7478a778992 c7478a778992 c7478a778992 c7478a778992 c7478a778992 c7478a778992 c7478a778992 c7478a778992 c7478a778992 c7478a778992 c7478a778992 c7478a778992 551f06733559 551f06733559 551f06733559 c7478a778992 c7478a778992 c7478a778992 c7478a778992 c7478a778992 c7478a778992 68e1655eaa2c c7478a778992 fc87327e29c4 c7478a778992 551f06733559 551f06733559 551f06733559 551f06733559 c7478a778992 c7478a778992 c7478a778992 c7478a778992 | #!/usr/bin/python
from __future__ import division
import math
import twisted.internet.fdesc
from twisted.internet import reactor
from twisted.internet.task import LoopingCall
class BCF2000(object):
control = {81 : "slider1", 82 : "slider2", 83 : "slider3", 84 : "slider4",
85 : "slider5", 86 : "slider6", 87 : "slider7", 88 : "slider8",
1 : "knob1", 2 : "knob2", 3 : "knob3", 4 : "knob4",
5 : "knob5", 6 : "knob6", 7 : "knob7", 8 : "knob8",
33 : "button-knob1", 34 : "button-knob2",
35 : "button-knob3", 36 : "button-knob4",
37 : "button-knob5", 38 : "button-knob6",
39 : "button-knob7", 40 : "button-knob8",
65 : "button-upper1", 66 : "button-upper2",
67 : "button-upper3", 68 : "button-upper4",
69 : "button-upper5", 70 : "button-upper6",
71 : "button-upper7", 72 : "button-upper8",
73 : "button-lower1", 74 : "button-lower2",
75 : "button-lower3", 76 : "button-lower4",
77 : "button-lower5", 78 : "button-lower6",
79 : "button-lower7", 80 : "button-lower8",
89 : "button-corner1", 90 : "button-corner2",
91 : "button-corner3", 92 : "button-corner4",
}
def __init__(self, dev="/dev/snd/midiC2D0"):
"""device was usually /dev/snd/midiC1D0 but then it showed up
once as C0D0. It should be autodetected"""
self.devPath = dev
self.dev = None
self.lastValue = {} # control name : value
self.reopen()
self.packet = ""
loop = LoopingCall(self.poll)
loop.start(.01)
def poll(self):
try:
bytes = self.dev.read(3)
except (IOError, AttributeError):
return
if len(bytes) == 0:
print "midi stall, reopen slider device"
self.reopen()
return
self.packet += bytes
if len(self.packet) == 3:
p = self.packet
self.packet = ""
self.packetReceived(p)
def packetReceived(self, packet):
b0, which, value = [ord(b) for b in packet]
if b0 != 0xb0:
return
if which in self.control:
name = self.control[which]
if name.startswith("button-"):
value = value > 0
self.lastValue[name] = value
self.valueIn(name, value)
else:
print "unknown control %s to %s" % (which, value)
def reopen(self):
if self.dev is not None:
try:
self.dev.close()
except IOError:
pass
self.lastValue.clear()
self.dev = open(self.devPath, "r+")
twisted.internet.fdesc.setNonBlocking(self.dev)
def valueIn(self, name, value):
"""override this with your handler for when events come in
from the hardware"""
print "slider %s to %s" % (name, value)
if name == 'slider1':
for x in range(2,8+1):
v2 = int(64 + 64 * math.sin(x / 3 + value / 10))
self.valueOut('slider%d' % x, v2)
for x in range(1,8+1):
self.valueOut('button-upper%s' % x, value > x*15)
self.valueOut('button-lower%s' % x, value > (x*15+7))
def valueOut(self, name, value):
"""call this to send an event to the hardware"""
if self.dev is None:
return
value = int(value)
if self.lastValue.get(name) == value:
return
self.lastValue[name] = value
which = [k for k,v in self.control.items() if v == name]
assert len(which) == 1, "unknown control name %r" % name
if name.startswith('button-'):
value = value * 127
#print "bcf: write %s %s" % (name, value)
self.dev.write(chr(0xb0) + chr(which[0]) + chr(int(value)))
def close(self):
self.dev.close()
self.dev = None
if __name__ == '__main__':
b = BCF2000()
reactor.run()
|