-
Notifications
You must be signed in to change notification settings - Fork 42
/
Copy pathkeymapparser.py
125 lines (94 loc) · 3.66 KB
/
keymapparser.py
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
118
119
120
121
122
123
124
125
import enigma
import xml.etree.cElementTree
from keyids import KEYIDS
# these are only informational (for help)...
from Tools.KeyBindings import addKeyBinding
class KeymapError(Exception):
def __init__(self, message):
self.msg = message
def __str__(self):
return self.msg
def getKeyId(id):
if len(id) == 1:
keyid = ord(id) | 0x8000
elif id[0] == '\\':
if id[1] == 'x':
keyid = int(id[2:], 0x10) | 0x8000
elif id[1] == 'd':
keyid = int(id[2:]) | 0x8000
else:
raise KeymapError("[keymapparser] key id '" + str(id) + "' is neither hex nor dec")
else:
try:
keyid = KEYIDS[id]
except:
raise KeymapError("[keymapparser] key id '" + str(id) + "' is illegal")
return keyid
unmapDict = {}
def parseKeys(context, filename, actionmap, device, keys):
for x in keys.findall("key"):
get_attr = x.attrib.get
mapto = get_attr("mapto")
unmap = get_attr("unmap")
id = get_attr("id")
flags = get_attr("flags")
if unmap is not None:
assert id, "[keymapparser] %s: must specify id in context %s, unmap '%s'" % (filename, context, unmap)
keyid = getKeyId(id)
actionmap.unbindPythonKey(context, keyid, unmap)
unmapDict.update({(context, id, unmap): filename})
else:
assert mapto, "[keymapparser] %s: must specify mapto (or unmap) in context %s, id '%s'" % (filename, context, id)
assert id, "[keymapparser] %s: must specify id in context %s, mapto '%s'" % (filename, context, mapto)
keyid = getKeyId(id)
flag_ascii_to_id = lambda x: {'m': 1, 'b': 2, 'r': 4, 'l': 8}[x]
flags = sum(map(flag_ascii_to_id, flags))
assert flags, "[keymapparser] %s: must specify at least one flag in context %s, id '%s'" % (filename, context, id)
# if a key was unmapped, it can only be assigned a new function in the same keymap file (avoid file parsing sequence dependency)
if unmapDict.get((context, id, mapto)) in [filename, None]:
# print "[keymapparser] " + context + "::" + mapto + " -> " + device + "." + hex(keyid)
actionmap.bindKey(filename, device, keyid, flags, context, mapto)
addKeyBinding(filename, keyid, context, mapto, flags)
def parseTrans(filename, actionmap, device, keys):
for x in keys.findall("toggle"):
get_attr = x.attrib.get
toggle_key = get_attr("from")
toggle_key = getKeyId(toggle_key)
actionmap.bindToggle(filename, device, toggle_key)
for x in keys.findall("key"):
get_attr = x.attrib.get
keyin = get_attr("from")
keyout = get_attr("to")
toggle = get_attr("toggle") or "0"
assert keyin, "[keymapparser] %s: must specify key to translate from '%s'" % (filename, keyin)
assert keyout, "[keymapparser] %s: must specify key to translate to '%s'" % (filename, keyout)
keyin = getKeyId(keyin)
keyout = getKeyId(keyout)
toggle = int(toggle)
actionmap.bindTranslation(filename, device, keyin, keyout, toggle)
def readKeymap(filename):
p = enigma.eActionMap.getInstance()
assert p
try:
source = open(filename)
except:
print "[keymapparser] keymap file " + filename + " not found"
return
try:
dom = xml.etree.cElementTree.parse(source)
except:
raise KeymapError("[keymapparser] keymap %s not well-formed." % filename)
source.close()
keymap = dom.getroot()
for cmap in keymap.findall("map"):
context = cmap.attrib.get("context")
assert context, "[keymapparser] map must have context"
parseKeys(context, filename, p, "generic", cmap)
for device in cmap.findall("device"):
parseKeys(context, filename, p, device.attrib.get("name"), device)
for ctrans in keymap.findall("translate"):
for device in ctrans.findall("device"):
parseTrans(filename, p, device.attrib.get("name"), device)
def removeKeymap(filename):
p = enigma.eActionMap.getInstance()
p.unbindKeyDomain(filename)