| #!/usr/bin/python |
| # -*- coding: utf-8 -*- |
| # -*- Python -*- |
| |
| from pyalsa.alsahcontrol import HControl, Element as HElement, \ |
| Info as HInfo, Value as HValue, InterfaceId, \ |
| EventMask, EventMaskRemove |
| |
| MIXER = InterfaceId['Mixer'] |
| MIXERS = str(MIXER) |
| |
| class BaseElement(InternalMElement): |
| |
| def __init__(self, mixer, name, index, weight): |
| InternalMElement.__init__(self, mixer, name, index, weight) |
| self.channels = 0 |
| self.min = [0, 0] |
| self.max = [0, 0] |
| |
| def opsIsChannel(self, dir, chn): |
| return chn >= 0 and chn < self.channels |
| |
| def opsGetRange(self, dir): |
| return (0, self.min[dir], self.max[dir]) |
| |
| def opsSetRange(self, dir, min, max): |
| self.min[dir] = min |
| self.max[dir] = max |
| |
| def volumeToUser(self, info, dir, value): |
| min = info.min |
| max = info.max |
| if min == max: |
| return self.min[dir] |
| n = (value - min) * (self.max[dir] - self.min[dir]) |
| return self.min[dir] + (n + (max - min) / 2) / (max - min) |
| |
| def volumeFromUser(self, info, dir, value): |
| min = info.min |
| max = info.max |
| if self.max[dir] == self.min[dir]: |
| return min |
| n = (value - self.min[dir]) * (max - min) |
| return min + (n + (self.max[dir] - self.min[dir]) / 2) / (self.max[dir] - self.min[dir]) |
| |
| class StandardElement(BaseElement): |
| |
| def __init__(self, mixer, name, index, weight): |
| BaseElement.__init__(self, mixer, name, index, weight) |
| self.channels = 1 |
| self.volume = [None, None] |
| self.volumeinfo = [None, None] |
| self.volumearray = [None, None] |
| self.switch = [None, None] |
| self.switchinfo = [None, None] |
| self.switcharray = [None, None] |
| |
| def decideChannels(self): |
| max = 0 |
| for i in [0, 1]: |
| if self.volume[i]: |
| count = self.volumeinfo[i].count |
| if count > max: |
| max = count |
| if self.switch[i]: |
| count = self.switchinfo[i].count |
| if count > max: |
| max = count |
| self.channels = max |
| |
| def attachVolume(self, helem, dir): |
| self.volume[dir] = helem |
| self.volumeinfo[dir] = HInfo(helem) |
| self.min[dir] = self.volumeinfo[dir].min |
| self.max[dir] = self.volumeinfo[dir].max |
| self.volumearray[dir] = HValue(helem).getArray(self.volumeinfo[dir].type, self.volumeinfo[dir].count) |
| |
| def attachSwitch(self, helem, dir): |
| self.switch[dir] = helem |
| self.switchinfo[dir] = HInfo(helem) |
| self.switcharray[dir] = HValue(helem).getArray(self.switchinfo[dir].type, self.switchinfo[dir].count) |
| |
| def attach(self, helem): |
| BaseElement.attach(self, helem) |
| if helem.name.endswith('Playback Volume'): |
| self.attachVolume(helem, 0) |
| self.caps |= self.CAP_PVOLUME |
| elif helem.name.endswith('Capture Volume'): |
| self.attachVolume(helem, 1) |
| self.caps |= self.CAP_CVOLUME |
| elif helem.name.endswith('Playback Switch'): |
| self.attachSwitch(helem, 0) |
| self.caps |= self.CAP_PSWITCH |
| elif helem.name.endswith('Capture Switch'): |
| self.attachSwitch(helem, 1) |
| self.caps |= self.CAP_CSWITCH |
| self.decideChannels() |
| self.eventInfo() |
| |
| def opsGetVolume(self, dir, chn): |
| return (0, self.volumeToUser(self.volumeinfo[dir], dir, self.volumearray[dir][chn])) |
| |
| def opsSetVolume(self, dir, chn, value): |
| val = self.volumeFromUser(self.volumeinfo[dir], dir, value) |
| if self.volumearray[dir][chn] == val: |
| return |
| self.volumearray[dir][chn] = val |
| hv = HValue(self.volume[dir]) |
| hv.setArray(self.volumeinfo[dir].type, self.volumearray[dir]) |
| hv.write() |
| |
| def opsGetSwitch(self, dir, chn): |
| return (0, self.switcharray[dir][chn]) |
| |
| def opsSetSwitch(self, dir, chn, value): |
| if self.switcharray[dir][chn] and value: |
| return |
| if not self.switcharray[dir][chn] and not value: |
| return |
| self.switcharray[dir] = int(value) |
| hv = HValue(self.switch[dir]) |
| hv.setArray(self.switchinfo[dir].type, self.switcharray[dir]) |
| hv.write() |
| |
| def update(self, helem): |
| for i in [0, 1]: |
| if helem == self.volume[i]: |
| self.volumearray[i] = HValue(helem).getArray(self.volumeinfo[i].type, self.volumeinfo[i].count) |
| elif helem == self.switch[i]: |
| self.switcharray[i] = HValue(helem).getArray(self.switchinfo[i].type, self.switchinfo[i].count) |
| self.eventValue() |
| |
| class EnumElement(BaseElement): |
| |
| def __init__(self, mixer, name, index, weight): |
| BaseElement.__init__(self, mixer, name, index, weight) |
| self.mycaps = 0 |
| |
| def attach(self, helem): |
| BaseElement.attach(self, helem) |
| self.enum = helem |
| self.enuminfo = HInfo(helem) |
| self.enumarray = HValue(helem).getArray(self.enuminfo.type, self.enuminfo.count) |
| self.channels = self.enuminfo.count |
| self.texts = self.enuminfo.itemNames |
| self.caps |= self.mycaps |
| |
| def opsIsEnumerated(self, dir=-1): |
| if dir < 0: |
| return 1 |
| if dir == 0 and self.mycaps & self.CAP_PENUM: |
| return 1 |
| if dir == 1 and self.mycaps & self.CAP_CENUM: |
| return 1 |
| |
| def opsIsEnumCnt(self, dir): |
| return self.enuminfo.items |
| |
| def opsGetEnumItemName(self, item): |
| return (0, self.texts[item]) |
| |
| def opsGetEnumItem(self, chn): |
| if chn >= self.channels: |
| return -1 |
| return (0, self.enumarray[chn]) |
| |
| def opsSetEnumItem(self, chn, value): |
| if chn >= self.channels: |
| return -1 |
| if self.enumarray[chn] == value: |
| return |
| self.enumarray[chn] = int(value) |
| hv = HValue(self.enum) |
| hv.setArray(self.enuminfo.type, self.enumarray) |
| hv.write() |
| |
| def update(self, helem): |
| self.enumarray = HValue(helem).getArray(self.enuminfo.type, self.enuminfo.count) |
| self.eventValue() |
| |
| class EnumElementPlayback(EnumElement): |
| |
| def __init__(self, mixer, name, index, weight): |
| EnumElement.__init__(self, mixer, name, index, weight) |
| self.mycaps = self.CAP_PENUM |
| |
| class EnumElementCapture(EnumElement): |
| |
| def __init__(self, mixer, name, index, weight): |
| EnumElement.__init__(self, mixer, name, index, weight) |
| self.mycaps = self.CAP_CENUM |
| |
| ELEMS = [] |
| |
| def element_add(helem): |
| key = helem.name+'//'+str(helem.index)+'//'+str(helem.interface) |
| if not CONTROLS.has_key(key): |
| return |
| val = CONTROLS[key] |
| felem = None |
| for elem in ELEMS: |
| if elem.name == val[0] and elem.index == val[1]: |
| felem = elem |
| break |
| if not felem: |
| felem = mixer.newMElement(val[3], val[0], val[1], val[2]) |
| mixer.addMElement(felem) |
| ELEMS.append(felem) |
| felem.attach(helem) |
| |
| def eventHandler(evmask, helem, melem): |
| if evmask == EventMaskRemove: |
| return |
| if evmask & EventMask['Add']: |
| element_add(helem) |
| if evmask & EventMask['Value']: |
| melem.update(helem) |
| |
| def init(): |
| hctl = HControl(device, load=False) |
| mixer.attachHCtl(hctl) |
| mixer.register() |