PTT for whisplay

This commit is contained in:
Gabby Pelton
2026-05-30 01:40:34 -05:00
parent 3415b6bb59
commit c5f3cf54f5
2 changed files with 61 additions and 7 deletions
+15 -2
View File
@@ -28,14 +28,27 @@ Single-file Python application for managing LXST Channel connections via Reticul
## Whisplay GUI Controls
### Channel list (STATE_READY)
Short press (<1s) Cycle to next channel in list
Long press (>=1s) Call the selected channel
Press (while in call) Hang up
RGB LED indicates state:
### In call (STATE_IN_CALL) — Push-to-Talk mode (default)
Press & hold Talk (unmute microphone)
Release Stop talking (mute microphone)
Double-press Toggle to always-on mode
### In call — Always-on mode (toggled)
Press Hang up
Double-press Toggle to push-to-talk mode
### RGB LED indicates state:
Blue = ready, showing channels
Orange = calling
Green = in call
Yellow = transmitting (PTT mode, mic active)
## Initial Setup Order
+46 -5
View File
@@ -36,6 +36,7 @@ if _WHISPLAY_AVAILABLE:
pass
LONG_PRESS_THRESHOLD = 1.0
DOUBLE_PRESS_THRESHOLD = 0.4
class Terminal:
@@ -71,6 +72,10 @@ class ChannelClient:
self.selected_index = 0
self._press_time = 0.0
self._wm8960_device = None
self._ptt_enabled = True
self._ptt_active = False
self._last_release_time = 0.0
self._double_pressed = False
if use_whisplay and _WHISPLAY_AVAILABLE and _HAS_PIL:
try:
self._init_whisplay()
@@ -304,8 +309,13 @@ class ChannelClient:
lines = [f"Channel {self.selected_index + 1}"]
if ch:
lines.append(ch["hash"][:16] + "..")
lines += ["", "Press to hang up"]
fb = self._render("In Call", lines, accent=(60, 220, 120), footer="Press button to end")
if self._ptt_enabled:
lines += ["", "PTT: hold to talk", "Release to mute"]
footer = "Double-press: toggle"
else:
lines += ["", "Mic always-on", "Press to hang up"]
footer = "Double-press: toggle"
fb = self._render("In Call", lines, accent=(60, 220, 120), footer=footer)
self.board.draw_image(0, 0, self.board.LCD_WIDTH, self.board.LCD_HEIGHT, fb)
def _show_status(self, title, detail="", accent=(255, 180, 60)):
@@ -317,14 +327,41 @@ class ChannelClient:
def _on_button_press(self):
self._press_time = time.time()
if self.state == self.STATE_IN_CALL:
if time.time() - self._last_release_time < DOUBLE_PRESS_THRESHOLD:
self._double_pressed = True
self._ptt_enabled = not self._ptt_enabled
if self._ptt_enabled:
self.telephone.mute_transmit()
else:
self.telephone.unmute_transmit()
if self.board:
self._show_in_call()
return
if self._ptt_enabled:
self._ptt_active = True
self.telephone.unmute_transmit()
if self.board:
self.board.set_rgb(255, 255, 0)
def _on_button_release(self):
elapsed = time.time() - self._press_time
self._last_release_time = time.time()
if self.state == self.STATE_IN_CALL:
self.telephone.hangup()
return
if self._double_pressed:
self._double_pressed = False
return
if self._ptt_enabled:
self._ptt_active = False
self.telephone.mute_transmit()
if self.board:
self.board.set_rgb(0, 255, 80)
return
else:
self.telephone.hangup()
return
if self.state != self.STATE_READY:
return
elapsed = time.time() - self._press_time
if elapsed >= LONG_PRESS_THRESHOLD:
if self.channels:
self.board.set_rgb(255, 180, 0)
@@ -457,6 +494,8 @@ class ChannelClient:
f"\nCall established with "
f"{RNS.prettyhexrep(remote_identity.hash)}"
)
if self._ptt_enabled:
self.telephone.mute_transmit()
if self.board:
self.board.set_rgb(0, 255, 80)
self._show_in_call()
@@ -465,6 +504,8 @@ class ChannelClient:
was_in_call = self.state == self.STATE_IN_CALL
was_calling = self.state == self.STATE_CALLING
self.state = self.STATE_READY
self._ptt_active = False
self._double_pressed = False
if was_in_call:
print(f"\nCall ended")
elif was_calling: