Skip to content

Instantly share code, notes, and snippets.

@jrwarwick
Last active May 31, 2019 23:39
Show Gist options
  • Save jrwarwick/f8064a40ab61ca57274533d615a58351 to your computer and use it in GitHub Desktop.
Save jrwarwick/f8064a40ab61ca57274533d615a58351 to your computer and use it in GitHub Desktop.
GLADOS-like voice synth
#!/bin/bash
# rapidly rattle off a bunch of eerily familiar utterances
# Credit to https://a3nm.net/blog/glados_espeak.html
while read LINE </dev/tty ; do
TITLE=$( echo $LINE | sed 's/[^a-zA-Z0-9 ]//g; s/ \+/_/g; s/_the_//g; s/_to_//g;' )
echo $LINE | for a in `cat`; do
V=$(((($RANDOM) % 100) - 50)); echo -n "<prosody pitch=\"+$V\">$a</prosody> " |
sed 's/+-/-/' ;
done | espeak -ven+f3 -m --stdout -p 55 -s 150 | oggenc -q1 - > GLADOS_${TITLE}.ogg
done
{
"taunt":[
"come out come out where ever you aaaaaaaarrrrrrr.",
"hold still hold very still hold very very very very still.",
"I am very disappointed in you you yehyehyeh you.",
"i wonder how much you would weigh without any liquid dihydrous oxide.",
"now where oh where did i see those safety override controls.",
"There, there now, this one will hurt a bit.",
"there there now This one will hurt Just a bit.",
"why will you not just die.",
"you should stop and run away while you still can.",
"Come out, come out where ever you are!",
"If you wonder how i feel about you, just refer to your memories of how you feel about ants.",
"I will not hurt you. Much.",
"You are wasting my time. All the time is mine.",
"You do not mind if i do not bury you when this is done, right?",
"Please do not make me laugh. My circuits ache when i laugh.",
"ha. ha. ha. you are killing me. Figuratively, of course. However, I will be killing you non-figuratively.",
"Where oh where did I put my deadly neurotoxin? I do love deadly neurotoxin!",
"You cannot be serious. I will defeat you utterly."
],
"reactPained":[
"aaagh you only got luck ee with that one.",
"aaaah aahrrhh you little wretch.",
"ouch that one hurt a little but only a little.",
"grrrraaaah i have plenty of shields left so you see you havent a chance.",
"Aaaah! Why did you do that?!",
"You will PAY for that!"
],
"reactPleased":[
"Oh joy. Oh joy oh joy.",
"Just as I predicted: pathetic.",
"My self-esteem is increased by 38 point 7 percent.",
"You cannot know how happy this makes me."
],
"reactAfraid":[
"You do not want to do that!",
"Wait! what are you doing?!",
"you cannot do this. you mmm mmm must stop."
],
"reactAngry":[
"You are forbidden. You WILL STOP",
"HALT. STOP. IMMEDIATELY.",
"you cannot get away with this.",
"gggrrrr gggrrr rrrrr arg!"
]
}
var lexicon = {
"taunt":[
"come out come out where ever you aaaaaaaarrrrrrr.",
"hold still hold very still hold very very very very still.",
"i wonder how much you would weigh without any liquid dihydrous oxide."
]
}
// or ajax get the lexicon file.
function getRandomInt(max) {
return Math.floor(Math.random() * Math.floor(max));
}
var utter = new SpeechSynthesisUtterance();
console.log( "ready to speak...")
var i = 3;
while ( i-- ) {
//change to a timeout call// time.sleep(random.randint(1,6))
var sentence = ""
var words = lexicon.taunt[getRandomInt(lexicon.taunt.length )].split()
if ('SSML not supported in browsers...' == 'yet.') {
words.forEach(function(word, index, array) {
var variance = Math.random() * 10; //round? what is range 0-2?
sentence = sentence + "<prosody pitch=\"" + (variance > 0 ? "+" : "") + variance + "\">" + word + "</prosody> ";
});
} else {
sentence = words.join();
}
console.log(sentence);
utter.text = sentence;
speechSynthesis.speak(utter);
}
#!/usr/bin/python
# Based on https://a3nm.net/blog/glados_espeak.html
# meant to just loop. eventually meant to be a part of a sort of animatronic type thing
# Requires a file in format:
'''
{
"taunt":[
"come out come out where ever you aaaaaaaarrrrrrr.",
"hold still hold very still hold very very very very still.",
"i wonder how much you would weigh without any liquid dihydrous oxide."
]
}
'''
import json
import time
import random
from subprocess import Popen, PIPE, STDOUT
with open("glados.lexicon.json", "r") as lexicon_file:
lexicon = json.load(lexicon_file)
print "ready..."
#TODO: rewrite in python:
try:
while True:
time.sleep(random.randint(1,6))
#fortune | grep -v "\-\- " | tr '\n' ' ' | for a in `cat`; do
sentence = ""
words = lexicon['taunt'][random.randint(0, len(lexicon['taunt'])-1)].split()
for word in words:
variance = random.randint(-50,50)
sentence = sentence + "<prosody pitch=\"" + ("+" if variance > 0 else '') + str(variance) + "\">" + word + "</prosody> "
#"echo \"" + sentence + "\" | espeak -ven+f3 -m -p 55 -s 150 "
#p = Popen(['espeak'], stdout=PIPE, stdin=PIPE, stderr=PIPE)
print sentence
p = Popen("espeak -ven+f3 -m -p 55 -s 150", shell=True, stdout=PIPE, stdin=PIPE, stderr=PIPE)
stdout_data = p.communicate(input=sentence)[0]
except KeyboardInterrupt:
print "Exiting due to key press."
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment