SideFX Houdini customization package
git clone https://git.lucas.co/hou-control.git
python3.13libs/hc/hcbindings.py (2K)
1 import hou
2 import json
3 from pathlib import Path
4
5 """
6 KEY NAMES
7 uparrow, downarrow, leftarrow, rightarrow
8 alt, cmd, shift, ctrl, tab, del, backspace, enter, esc
9 f1...f12
10 pageup, pagedown, end, home, insert
11 /, \
12 pad0...pad9
13 padstar, padslash
14 pause
15 space
16 """
17
18
19 class HCBindings:
20 def __init__(self):
21 return
22
23 def load(self):
24 self.assign()
25
26 def assign(self):
27 path = Path(hou.getenv("HC_PATH")) / "hc_hotkeys.json"
28 data = json.loads(path.read_text())
29 assignments = data.get("assignments", {})
30 for symbol, key in assignments.items():
31 context = symbol.rpartition('.')[0]
32 self._clearConflicts(context, symbol, key)
33 ok = hou.hotkeys.addAssignment(context, symbol, key)
34 if not ok:
35 print(f"[HCBindings] failed to assign {symbol!r} -> {key!r} in context {context!r}")
36
37 def _clearConflicts(self, context, symbol, key):
38 try:
39 conflicts = hou.hotkeys.findConflicts(context, symbol, key)
40 except hou.OperationFailed as e:
41 print(f"[HCBindings] findConflicts error for {symbol!r} {key!r}: {e}")
42 return
43 for entry in conflicts:
44 if '?' in entry:
45 conflict_ctx, conflict_sym = entry.split('?', 1)
46 else:
47 conflict_ctx, conflict_sym = context, entry
48 if conflict_sym == symbol:
49 continue
50
51 # Allow Shift+k to exist globally as the keycam entry point
52 # alongside more-specific uses in the keycam state and
53 # network editor. Houdini resolves by context specificity.
54 if conflict_sym == 'h.hc_session_keycam':
55 continue
56
57 ok = hou.hotkeys.removeAssignment(conflict_ctx, conflict_sym, key)
58 if ok:
59 print(f"[HCBindings] unbound {key!r} from conflicting {conflict_sym!r}")
60 else:
61 print(f"[HCBindings] failed to unbind {key!r} from {conflict_sym!r}")