Skip to content

Commit

Permalink
addon dev and test
Browse files Browse the repository at this point in the history
  • Loading branch information
C-Loftus committed Jan 23, 2024
1 parent c057ca2 commit 8fd7287
Show file tree
Hide file tree
Showing 5 changed files with 68 additions and 44 deletions.
22 changes: 10 additions & 12 deletions core/addon_communication/ipc_client.py
Original file line number Diff line number Diff line change
@@ -1,17 +1,12 @@
from talon import Module, Context, actions
import os, ipaddress, json, socket
from .ipc_helpers import Mutex
import threading


mod = Module()
mutex = threading.Lock()

# We want to make sure only one connection is open at a time
mutex = Mutex(socket.socket(socket.AF_INET, socket.SOCK_STREAM))

# Lock the mutex for the scope of the `with` block
with mutex.lock() as value:
# value is typed as `list` here
value.append(1)
communication_socket = None

@mod.action_class
Expand Down Expand Up @@ -60,14 +55,17 @@ def send_ipc_command(command: str):
if command not in valid_commands:
raise ValueError(f"Invalid NVDA IPC command: '{command}'")

with mutex.lock() as socket:
socket.connect((ip, port))

with mutex:
sock = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
sock.connect((ip, int(port)))
try:
socket.sendall(command.encode("utf-8"))
except:
encoded = command.encode("utf-8")
sock.sendall(encoded)
except:
print("Error Communicating with NVDA extension")
finally:
socket.close()
sock.close()


ORCAContext = Context()
Expand Down
1 change: 1 addition & 0 deletions docs/src/ATTRIBUTIONS.md
Original file line number Diff line number Diff line change
Expand Up @@ -26,6 +26,7 @@
- NVDA Controller client `.dll` file can be found at: [https://www.nvaccess.org/files/nvda/releases/stable/](https://www.nvaccess.org/files/nvda/releases/stable/)
- Documentation for this controller client can be found at [https://github.com/nvaccess/nvda/blob/master/extras/controllerClient/readme.md](https://github.com/nvaccess/nvda/blob/master/extras/controllerClient/readme.md)
- [https://github.com/nvaccess/nvda/wiki/](https://github.com/nvaccess/nvda/wiki/)
- [https://github.com/nvda-es/devguides_translation/blob/master/original_docs/NVDA-Add-on-Development-Guide.md](https://github.com/nvda-es/devguides_translation/blob/master/original_docs/NVDA-Add-on-Development-Guide.md)
- [ https://addons.nvda-project.org/addons/AudioThemes.en.html](https://addons.nvda-project.org/addons/AudioThemes.en.html)
- [https://addons.nvda-project.org/addons/phoneticPunctuation.en.html](https://addons.nvda-project.org/addons/phoneticPunctuation.en.html)
- Helpful settings
Expand Down
63 changes: 40 additions & 23 deletions nvda/.addOn/nvda-addon.py
Original file line number Diff line number Diff line change
@@ -1,52 +1,69 @@
import globalPluginHandler
import speech
from scriptHandler import script
import config
import tones
import tones, nvwave, ui
import os, json, socket, threading

commands = ["disableSpeechInterruptForCharacters", "restoreSpeechInterruptForCharacters", "debug", "playWAV"]

commands = ["disableSpeechInterruptForCharacters", "restoreSpeechInterruptForCharacters"]

interrupt_value = False
def bind_to_available_port(server_socket, start_port, end_port):
for port in range(start_port, end_port):
try:
server_socket.bind(('127.0.0.1', port))
return port
except OSError:
continue
raise OSError(f"No available ports in the range {start_port}-{end_port}")

interrupt_value = False
def handle_command(command: str):
global interrupt_value
if command == "disableSpeechInterruptForCharacters":
interrupt = config.conf["keyboard"]["speechInterruptForCharacters"]
interrupt_value = interrupt
config.conf["keyboard"]["speechInterruptForCharacters"] = False
if command == "restoreSpeechInterruptForCharacters":
config.conf["keyboard"]["speechInterruptForCharacters"] = interrupt_value
else:
print("Invalid command: {command}")

tones.beep(440, 100)


global interrupt_value
if command == "disableSpeechInterruptForCharacters":
interrupt = config.conf["keyboard"]["speechInterruptForCharacters"]
interrupt_value = interrupt
config.conf["keyboard"]["speechInterruptForCharacters"] = False
if command == "restoreSpeechInterruptForCharacters":
config.conf["keyboard"]["speechInterruptForCharacters"] = interrupt_value
elif command == "debug":
tones.beep(640, 100)
else:
print(f"Invalid command: {command}")

class IPC_Server():
port = None

def handle_client(self, client_socket: socket.socket):
data = client_socket.recv(1024)
message = data.decode().strip()
handle_command(message)
print(f"Received {message}")
response = "HTTP/1.1 200 OK\r\nContent-Type: text/plain\r\n\r\nMessage received. Success".encode() # Create a HTTP response
client_socket.send(response)

def output_spec_file(self):
# write a json file to os.path.expanduser("~\\AppData\\Roaming\\nvda\\talon_server_spec.json")
# with ip address and port as well as commands
# write a json file to let clients know how to connect and what commands are available
PATH = os.path.expanduser("~\\AppData\\Roaming\\nvda\\talon_server_spec.json")
spec = {
"ip": "127.0.0.1",
"port": "8888",
"commands": commands
"address": "127.0.0.1",
"port": str(self.get_port()),
"valid_commands": commands
}
with open(PATH, "w") as f:
json.dump(spec, f)

def set_port(self, port):
self.port = port

def get_port(self):
return self.port

def create_server(self):
server_socket = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
server_socket.bind(('127.0.0.1', 8888))
port = bind_to_available_port(server_socket, 8888, 9000)
self.set_port(port)
self.output_spec_file()

server_socket.listen(1)
server_socket.settimeout(None) # Set the timeout to None
print(f'Serving on {server_socket.getsockname()}')
Expand Down
19 changes: 11 additions & 8 deletions nvda/nvda.py
Original file line number Diff line number Diff line change
Expand Up @@ -118,11 +118,14 @@ def braille(text: str):



# Not sure how to usually have speak words on
# since if we have it on all the time then it will mess
# def toggle_speak_typed_words(_):
# """Toggles the speak typed words setting"""
# actions.user.with_nvda_mod_press("3")

# speech_system.register("pre:phrase", toggle_speak_typed_words)
# speech_system.register("post:phrase", toggle_speak_typed_words)
def disable_interrupt(_):
if actions.user.is_nvda_running():
actions.user.send_ipc_command("disableSpeechInterruptForCharacters")

def restore_interrupt_setting(_):
if actions.user.is_nvda_running():
actions.user.send_ipc_command("restoreSpeechInterruptForCharacters")


speech_system.register("pre:phrase", disable_interrupt)
speech_system.register("post:phrase", restore_interrupt_setting)
7 changes: 6 additions & 1 deletion nvda/nvda.talon
Original file line number Diff line number Diff line change
Expand Up @@ -144,4 +144,9 @@ pass through next:
user.with_nvda_mod_press('f2')

restart reader:
user.restart_nvda()
user.restart_nvda()

test reader add on:
user.send_ipc_command("debug")


0 comments on commit 8fd7287

Please sign in to comment.