Compare commits
35 Commits
105ca3a914
...
testing
Author | SHA1 | Date | |
---|---|---|---|
23441c8b28 | |||
6124419d29 | |||
b17f1c0672 | |||
432a55308f | |||
60ece5b489 | |||
9b8b21cc55 | |||
d10312c0d2 | |||
9e73910121 | |||
6a8f866943 | |||
21e933ab53 | |||
893f7bf455 | |||
5d8aae9386 | |||
4309fd8994 | |||
c2e5a8ee3d | |||
78f7ae506d | |||
a0e539d3ce | |||
db40032d3d | |||
c3c9da9403 | |||
a71bb0e608 | |||
02b598e987 | |||
6cd034c594 | |||
ad55390801 | |||
6e9aaa9751 | |||
1a9b8d5c03 | |||
d51b5fadd8 | |||
41f525f51b | |||
f94521bfb1 | |||
c83714866d | |||
18279b6e7b | |||
f82c4d2559 | |||
3ee8fd0098 | |||
2e5c14d5d6 | |||
fc53c8be24 | |||
9dd3d49174 | |||
c332370ba1 |
231
DoomTTS.ps1
Normal file
231
DoomTTS.ps1
Normal file
@ -0,0 +1,231 @@
|
|||||||
|
# Change the next line to $true to enable the script
|
||||||
|
$useTextToSpeech = $true
|
||||||
|
# Set this to $true to use SAPI, $false to use nvdaControllerClient or fall back to clipboard
|
||||||
|
$useSAPI = $false
|
||||||
|
# Set the speech rate. -10 to 10, default 0
|
||||||
|
$speechRate = 0
|
||||||
|
|
||||||
|
# Do not edit below this line.
|
||||||
|
######################################################################
|
||||||
|
|
||||||
|
# Exit if text-to-speech is disabled
|
||||||
|
if (-not $useTextToSpeech) {
|
||||||
|
exit
|
||||||
|
}
|
||||||
|
|
||||||
|
# Define antigrep, and sed patterns
|
||||||
|
$antigrepPatterns = @(
|
||||||
|
'^P_StartScript:',
|
||||||
|
'^[Ff]luidsynth:',
|
||||||
|
'^(Facing|INTRO|MAP[0-9]+|README)',
|
||||||
|
'^ *TITLEMAP',
|
||||||
|
'key card',
|
||||||
|
'^\[Toby Accessibility Mod\] (INTRO|READMe)([0-9]+).*',
|
||||||
|
"^(As |Computer Voice:|I |I've|Monorail|Ugh|What|Where)",
|
||||||
|
[regex]::Escape('Ugh... Huh? What the hell was that?! Better go check it out...')
|
||||||
|
)
|
||||||
|
|
||||||
|
$sedPatterns = @(
|
||||||
|
@("\[Toby Accessibility Mod\] M_", "[Toby Accessibility Mod] "),
|
||||||
|
@("^\[Toby Accessibility Mod\] ", ""),
|
||||||
|
@("^MessageBoxMenu$", "Confirmation menu: Press Y for yes or N for no"),
|
||||||
|
@("^Mainmenu$", "Main menu"),
|
||||||
|
@("^Playerclassmenu$", "Player class menu"),
|
||||||
|
@("^Skillmenu$", "Difficulty menu"),
|
||||||
|
@("^NGAME", "New game"),
|
||||||
|
@("^LOADG$", "Load game"),
|
||||||
|
@("^SAVEG$", "Save game"),
|
||||||
|
@("^QUITG$", "Quit game"),
|
||||||
|
@('"cl_run" = "true"', "Run"),
|
||||||
|
@('"cl_run" = "false"', "Walk"),
|
||||||
|
@('.*/:Game saved. \(', ""),
|
||||||
|
@('^\*\*\*', ""),
|
||||||
|
@('^\+', "")
|
||||||
|
)
|
||||||
|
|
||||||
|
# Check PowerShell version
|
||||||
|
$requiredPowershellVersion = [Version]"5.1"
|
||||||
|
$currentPowershellVersion = $PSVersionTable.PSVersion
|
||||||
|
|
||||||
|
$logFile = ".\DoomTTS.log"
|
||||||
|
Set-Content -Path $logFile -Value "Logging started $(Get-Date -Format 'dddd MMMM dd, yyyy') at $(Get-Date -Format 'hh:mmtt')"
|
||||||
|
Add-Content -Path $logFile -Value "Powershell $currentPowershellVersion"
|
||||||
|
if ($currentVersion -lt $requiredVersion) {
|
||||||
|
Add-Content -Path $logFile -Value "PowerShell version $requiredPowershellVersion or later is required. Exiting."
|
||||||
|
exit
|
||||||
|
}
|
||||||
|
|
||||||
|
# Function for logging
|
||||||
|
function Write-Log {
|
||||||
|
param (
|
||||||
|
[string]$Message,
|
||||||
|
[string]$Type = "INFO" # Can be INFO, ERROR, or SPEECH
|
||||||
|
)
|
||||||
|
|
||||||
|
$timestamp = Get-Date -Format "yyyy-MM-dd HH:mm:ss"
|
||||||
|
$logMessage = "$Message [$Type] [$timestamp]"
|
||||||
|
|
||||||
|
# Append the message to the log file
|
||||||
|
Add-Content -Path $logFile -Value $logMessage
|
||||||
|
|
||||||
|
# If it's an error, also write to the console
|
||||||
|
if ($Type -eq "ERROR") {
|
||||||
|
Write-Host $logMessage -ForegroundColor Red
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
# Function to load NVDA DLL and check if NVDA is running
|
||||||
|
function Initialize-NVDA {
|
||||||
|
try {
|
||||||
|
# Declare the P/Invoke signatures
|
||||||
|
$signature = @"
|
||||||
|
[DllImport("kernel32.dll")]
|
||||||
|
public static extern IntPtr LoadLibrary(string dllToLoad);
|
||||||
|
|
||||||
|
[DllImport("kernel32.dll")]
|
||||||
|
public static extern IntPtr GetProcAddress(IntPtr hModule, string procedureName);
|
||||||
|
|
||||||
|
[DllImport("kernel32.dll")]
|
||||||
|
public static extern bool FreeLibrary(IntPtr hModule);
|
||||||
|
|
||||||
|
[UnmanagedFunctionPointer(CallingConvention.StdCall)]
|
||||||
|
public delegate int NvdaTestIfRunning();
|
||||||
|
|
||||||
|
[UnmanagedFunctionPointer(CallingConvention.StdCall)]
|
||||||
|
public delegate void NvdaSpeakText([MarshalAs(UnmanagedType.LPWStr)] string text);
|
||||||
|
|
||||||
|
[UnmanagedFunctionPointer(CallingConvention.StdCall)]
|
||||||
|
public delegate void NvdaBrailleMessage([MarshalAs(UnmanagedType.LPWStr)] string message);
|
||||||
|
|
||||||
|
[UnmanagedFunctionPointer(CallingConvention.StdCall)]
|
||||||
|
public delegate void NvdaCancelSpeech();
|
||||||
|
"@
|
||||||
|
|
||||||
|
Add-Type -MemberDefinition $signature -Name "NvdaFunctions" -Namespace "Win32Functions"
|
||||||
|
|
||||||
|
# Load the NVDA client library
|
||||||
|
$dllPath = ".\nvdaControllerClient.dll"
|
||||||
|
$nvdaDll = [Win32Functions.NvdaFunctions]::LoadLibrary($dllPath)
|
||||||
|
if ($nvdaDll -eq [IntPtr]::Zero) {
|
||||||
|
throw "Failed to load nvdaControllerClient.dll"
|
||||||
|
}
|
||||||
|
|
||||||
|
# Define function pointers
|
||||||
|
$nvdaTestIfRunning = [System.Runtime.InteropServices.Marshal]::GetDelegateForFunctionPointer(
|
||||||
|
[Win32Functions.NvdaFunctions]::GetProcAddress($nvdaDll, "nvdaController_testIfRunning"),
|
||||||
|
[Type][Win32Functions.NvdaFunctions+NvdaTestIfRunning]
|
||||||
|
)
|
||||||
|
|
||||||
|
$nvdaSpeakText = [System.Runtime.InteropServices.Marshal]::GetDelegateForFunctionPointer(
|
||||||
|
[Win32Functions.NvdaFunctions]::GetProcAddress($nvdaDll, "nvdaController_speakText"),
|
||||||
|
[Type][Win32Functions.NvdaFunctions+NvdaSpeakText]
|
||||||
|
)
|
||||||
|
|
||||||
|
$nvdaBrailleMessage = [System.Runtime.InteropServices.Marshal]::GetDelegateForFunctionPointer(
|
||||||
|
[Win32Functions.NvdaFunctions]::GetProcAddress($nvdaDll, "nvdaController_brailleMessage"),
|
||||||
|
[Type][Win32Functions.NvdaFunctions+NvdaBrailleMessage]
|
||||||
|
)
|
||||||
|
|
||||||
|
$nvdaCancelSpeech = [System.Runtime.InteropServices.Marshal]::GetDelegateForFunctionPointer(
|
||||||
|
[Win32Functions.NvdaFunctions]::GetProcAddress($nvdaDll, "nvdaController_cancelSpeech"),
|
||||||
|
[Type][Win32Functions.NvdaFunctions+NvdaCancelSpeech]
|
||||||
|
)
|
||||||
|
|
||||||
|
# Test if NVDA is running
|
||||||
|
$res = $nvdaTestIfRunning.Invoke()
|
||||||
|
if ($res -ne 0) {
|
||||||
|
$errorMessage = [ComponentModel.Win32Exception]::new([System.Runtime.InteropServices.Marshal]::GetLastWin32Error()).Message
|
||||||
|
throw "NVDA is not running or communication failed. Error: $errorMessage"
|
||||||
|
}
|
||||||
|
|
||||||
|
return @{
|
||||||
|
SpeakText = $nvdaSpeakText
|
||||||
|
BrailleMessage = $nvdaBrailleMessage
|
||||||
|
CancelSpeech = $nvdaCancelSpeech
|
||||||
|
}
|
||||||
|
}
|
||||||
|
catch {
|
||||||
|
Write-Log -Message "Error initializing NVDA: $_" -Type "ERROR"
|
||||||
|
return $null
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
# Function to speak text using SAPI, NVDA, or copy to clipboard
|
||||||
|
function Speak-Text {
|
||||||
|
param (
|
||||||
|
[string]$text
|
||||||
|
)
|
||||||
|
|
||||||
|
Write-Log -Message "Speaking: $text" -Type "SPEECH"
|
||||||
|
|
||||||
|
if ($useSAPI) {
|
||||||
|
try {
|
||||||
|
$tts = New-Object -ComObject SAPI.SPVoice
|
||||||
|
$tts.Rate = $speechRate
|
||||||
|
$tts.Speak($text)
|
||||||
|
} catch {
|
||||||
|
Write-Log -Message "Error using SAPI: $_" -Type "ERROR"
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
$nvdaFunctions = Initialize-NVDA
|
||||||
|
if ($nvdaFunctions) {
|
||||||
|
try {
|
||||||
|
$nvdaFunctions.SpeakText.Invoke($text)
|
||||||
|
} catch {
|
||||||
|
Write-Log -Message "Error using nvdaControllerClient.dll: $_" -Type "ERROR"
|
||||||
|
Set-Clipboard -Value $text
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
Set-Clipboard -Value $text
|
||||||
|
Write-Log -Message "Failed to initialize NVDA, text copied to clipboard" -Type "INFO"
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
# Process the output with grep, antigrep, and sed-like functionality
|
||||||
|
function Process-Output {
|
||||||
|
param (
|
||||||
|
[string]$line,
|
||||||
|
[string[]]$antigrepPatterns,
|
||||||
|
[array]$sedPatterns
|
||||||
|
)
|
||||||
|
|
||||||
|
# Apply antigrep (exclude lines)
|
||||||
|
foreach ($pattern in $antigrepPatterns) {
|
||||||
|
if ($line -match $pattern) {
|
||||||
|
return # Skip this line
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
# Apply sed (modify lines)
|
||||||
|
foreach ($pattern in $sedPatterns) {
|
||||||
|
$line = $line -replace $pattern[0], $pattern[1]
|
||||||
|
}
|
||||||
|
|
||||||
|
return $line
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
# Start reading the piped output
|
||||||
|
$stream = [System.IO.StreamReader]::new([Console]::OpenStandardInput(), [System.Text.Encoding]::UTF8)
|
||||||
|
# Use the 40 - line to let us know when to start speaking.
|
||||||
|
$startProcessing = $false
|
||||||
|
|
||||||
|
while ($null -ne ($line = $stream.ReadLine())) {
|
||||||
|
Write-Log -Message "Raw input: $line" -Type "INFO"
|
||||||
|
|
||||||
|
# Check for the separator
|
||||||
|
if ($line -match '^-{5,}$') {
|
||||||
|
$startProcessing = $true
|
||||||
|
continue # Skip the separator
|
||||||
|
}
|
||||||
|
|
||||||
|
# Only process lines after we've seen the separator
|
||||||
|
if ($startProcessing) {
|
||||||
|
$processedLine = Process-Output -line $line -antigrepPatterns $antigrepPatterns -sedPatterns $sedPatterns
|
||||||
|
if ($processedLine) {
|
||||||
|
Write-Log -Message "Processed line: $processedLine" -Type "INFO"
|
||||||
|
Speak-Text -text $processedLine
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
File diff suppressed because it is too large
Load Diff
@ -10,7 +10,7 @@
|
|||||||
}
|
}
|
||||||
],
|
],
|
||||||
"files": [
|
"files": [
|
||||||
"Addons/MENU/TobyV{toby_base_version}_*",
|
"Addons/MENU/TobyV*_SimpleMenu.pk3",
|
||||||
"aoddoom1.wad"
|
"aoddoom1.wad"
|
||||||
],
|
],
|
||||||
"optional_files": [
|
"optional_files": [
|
||||||
|
24
TobyCustom/DoomGuyVersesTheDaleks.json
Normal file
24
TobyCustom/DoomGuyVersesTheDaleks.json
Normal file
@ -0,0 +1,24 @@
|
|||||||
|
{
|
||||||
|
"name": "DoomGuy Verses the Daleks",
|
||||||
|
"dependencies": [
|
||||||
|
{
|
||||||
|
"file": "DoomguyVsTheDaleks_V1.1.wad",
|
||||||
|
"url": "https://www.moddb.com/mods/doomguy-vs-the-daleks",
|
||||||
|
"messages": [
|
||||||
|
"Place \"DoomguyVsTheDaleks_V1.1.wad\" in the Toby Doom directory. On Linux/Mac this is ~/.local/games/doom"
|
||||||
|
]
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"files": [
|
||||||
|
"Addons/MENU/TobyV*_SimpleMenu.pk3",
|
||||||
|
"Addons/DOOM/TobyV*_Decorations.pk3",
|
||||||
|
"Addons/DOOM/TobyV*_Guns.pk3",
|
||||||
|
"Addons/DOOM/TobyV*_Pickups.pk3",
|
||||||
|
"DoomguyVsTheDaleks_V1.1.wad"
|
||||||
|
],
|
||||||
|
"optional_files": [
|
||||||
|
"DoomMetalVol7.wad",
|
||||||
|
"DoomMetalVol6.wad"
|
||||||
|
],
|
||||||
|
"use_map_menu": true
|
||||||
|
}
|
@ -10,8 +10,7 @@
|
|||||||
}
|
}
|
||||||
],
|
],
|
||||||
"files": [
|
"files": [
|
||||||
"Addons/MENU/TobyV{toby_base_version}_*",
|
"Addons/MENU/TobyV*_SimpleMenu.pk3",
|
||||||
"Addons/DOOM/TobyV{toby_base_version}_Proximity.pk3",
|
|
||||||
"GMOTA_V.1.5.2.pk3"
|
"GMOTA_V.1.5.2.pk3"
|
||||||
],
|
],
|
||||||
"flags": [
|
"flags": [
|
||||||
|
17
TobyCustom/ProjectMSX.json
Normal file
17
TobyCustom/ProjectMSX.json
Normal file
@ -0,0 +1,17 @@
|
|||||||
|
{
|
||||||
|
"name": "ProjectMSX",
|
||||||
|
"dependencies": [
|
||||||
|
{
|
||||||
|
"file": "projectmsx_v0.2a.pk3",
|
||||||
|
"url": "https://www.moddb.com/mods/project-msx",
|
||||||
|
"messages": [
|
||||||
|
"Place projectmsx_v0.2a.pk3 in the Toby Doom directory. On Linux/Mac this is ~/.local/games/doom."
|
||||||
|
]
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"files": [
|
||||||
|
"Addons/MENU/TobyV*_SimpleMenu.pk3",
|
||||||
|
"projectmsx_v0.2a.pk3"
|
||||||
|
],
|
||||||
|
"use_map_menu": true
|
||||||
|
}
|
@ -12,7 +12,7 @@
|
|||||||
}
|
}
|
||||||
],
|
],
|
||||||
"files": [
|
"files": [
|
||||||
"Addons/DOOM/TobyV{toby_base_version}_Proximity.pk3",
|
"Addons/MENU/TobyV*_SimpleMenu.pk3",
|
||||||
"PB-Toby-Compatibility-Addon.pk3",
|
"PB-Toby-Compatibility-Addon.pk3",
|
||||||
"Project_Brutality.pk3"
|
"Project_Brutality.pk3"
|
||||||
],
|
],
|
||||||
|
@ -11,7 +11,7 @@
|
|||||||
}
|
}
|
||||||
],
|
],
|
||||||
"files": [
|
"files": [
|
||||||
"Addons/DOOM/TobyV{toby_base_version}_Proximity.pk3",
|
"Addons/MENU/TobyV*_SimpleMenu.pk3",
|
||||||
"Project_Brutality-Latest.pk3"
|
"Project_Brutality-Latest.pk3"
|
||||||
],
|
],
|
||||||
"optional_files": [
|
"optional_files": [
|
||||||
|
@ -29,8 +29,7 @@
|
|||||||
]
|
]
|
||||||
},
|
},
|
||||||
"files": [
|
"files": [
|
||||||
"Addons/MENU/TobyV{toby_base_version}_*",
|
"Addons/MENU/TobyV*_SimpleMenu.pk3"
|
||||||
"Addons/DOOM/TobyV{toby_base_version}_Proximity.pk3"
|
|
||||||
],
|
],
|
||||||
"flags": [
|
"flags": [
|
||||||
"+bind", "Ctrl", "+attack",
|
"+bind", "Ctrl", "+attack",
|
||||||
|
@ -1,15 +1,16 @@
|
|||||||
{
|
{
|
||||||
"name": "Star Wars",
|
"name": "Xim Star Wars",
|
||||||
"dependencies": [
|
"dependencies": [
|
||||||
{
|
{
|
||||||
"file": "Xim-StarWars-v3.1.5.pk3",
|
"file": "Xim-StarWars-v3.1.5.pk3",
|
||||||
"url": "https://www.moddb.com/mods/xims-star-wars-doom",
|
"url": "https://www.moddb.com/mods/xims-star-wars-doom",
|
||||||
"messages": [
|
"messages": [
|
||||||
"Place Xim-StarWars-v3.1.5.pk3 in the Toby Doom directory, on Linux or Mac, ~/.local/games/doom"
|
"Extract Xim-StarWars-v3.1.5.6.zip to the Toby Doom directory, on Linux or Mac, ~/.local/games/doom"
|
||||||
]
|
]
|
||||||
}
|
}
|
||||||
],
|
],
|
||||||
"files": [
|
"files": [
|
||||||
|
"Addons/MENU/TobyV*_SimpleMenu.pk3",
|
||||||
"Xim-StarWars-v3.1.5.pk3",
|
"Xim-StarWars-v3.1.5.pk3",
|
||||||
"Addons/STARWARS/*.pk3"
|
"Addons/STARWARS/*.pk3"
|
||||||
],
|
],
|
Reference in New Issue
Block a user