added support for pitch= and tempo= to yt yts and sayen
This commit is contained in:
parent
2fbe20740f
commit
4b658e90d5
@ -10,106 +10,110 @@ from importlib import reload
|
|||||||
from . import Commands
|
from . import Commands
|
||||||
|
|
||||||
class CommandHandler():
|
class CommandHandler():
|
||||||
def __init__(self, Torchlight):
|
def __init__(self, Torchlight):
|
||||||
self.Logger = logging.getLogger(__class__.__name__)
|
self.Logger = logging.getLogger(__class__.__name__)
|
||||||
self.Torchlight = Torchlight
|
self.Torchlight = Torchlight
|
||||||
self.Commands = []
|
self.Commands = []
|
||||||
self.NeedsReload = False
|
self.NeedsReload = False
|
||||||
|
|
||||||
def Setup(self):
|
def Setup(self):
|
||||||
Counter = len(self.Commands)
|
Counter = len(self.Commands)
|
||||||
self.Commands.clear()
|
self.Commands.clear()
|
||||||
if Counter:
|
if Counter:
|
||||||
self.Logger.info(sys._getframe().f_code.co_name + " Unloaded {0} commands!".format(Counter))
|
self.Logger.info(sys._getframe().f_code.co_name + " Unloaded {0} commands!".format(Counter))
|
||||||
|
|
||||||
Counter = 0
|
Counter = 0
|
||||||
for subklass in sorted(Commands.BaseCommand.__subclasses__(), key = lambda x: x.Order, reverse = True):
|
for subklass in sorted(Commands.BaseCommand.__subclasses__(), key = lambda x: x.Order, reverse = True):
|
||||||
try:
|
try:
|
||||||
Command = subklass(self.Torchlight)
|
Command = subklass(self.Torchlight)
|
||||||
if hasattr(Command, "_setup"):
|
if hasattr(Command, "_setup"):
|
||||||
Command._setup()
|
Command._setup()
|
||||||
except Exception as e:
|
except Exception as e:
|
||||||
self.Logger.error(traceback.format_exc())
|
self.Logger.error(traceback.format_exc())
|
||||||
else:
|
else:
|
||||||
self.Commands.append(Command)
|
self.Commands.append(Command)
|
||||||
Counter += 1
|
Counter += 1
|
||||||
|
|
||||||
self.Logger.info(sys._getframe().f_code.co_name + " Loaded {0} commands!".format(Counter))
|
self.Logger.info(sys._getframe().f_code.co_name + " Loaded {0} commands!".format(Counter))
|
||||||
|
|
||||||
def Reload(self):
|
def Reload(self):
|
||||||
try:
|
try:
|
||||||
reload(Commands)
|
reload(Commands)
|
||||||
except Exception as e:
|
except Exception as e:
|
||||||
self.Logger.error(traceback.format_exc())
|
self.Logger.error(traceback.format_exc())
|
||||||
else:
|
else:
|
||||||
self.Setup()
|
self.Setup()
|
||||||
|
|
||||||
async def HandleCommand(self, line, player):
|
async def HandleCommand(self, line, player):
|
||||||
Message = line.split(sep = ' ', maxsplit = 1)
|
Message = line.split(sep = ' ', maxsplit = 1)
|
||||||
if len(Message) < 2:
|
if len(Message) < 2:
|
||||||
Message.append("")
|
Message.append("")
|
||||||
Message[1] = Message[1].strip()
|
Message[1] = Message[1].strip()
|
||||||
|
|
||||||
if Message[1] and self.Torchlight().LastUrl:
|
if Message[1] and self.Torchlight().LastUrl:
|
||||||
Message[1] = Message[1].replace("!last", self.Torchlight().LastUrl)
|
Message[1] = Message[1].replace("!last", self.Torchlight().LastUrl)
|
||||||
line = Message[0] + ' ' + Message[1]
|
line = Message[0] + ' ' + Message[1]
|
||||||
|
|
||||||
Level = 0
|
Level = 0
|
||||||
if player.Access:
|
if player.Access:
|
||||||
Level = player.Access["level"]
|
Level = player.Access["level"]
|
||||||
|
|
||||||
RetMessage = None
|
RetMessage = None
|
||||||
Ret = None
|
Ret = None
|
||||||
for Command in self.Commands:
|
for Command in self.Commands:
|
||||||
for Trigger in Command.Triggers:
|
for Trigger in Command.Triggers:
|
||||||
Match = False
|
Match = False
|
||||||
RMatch = None
|
RMatch = None
|
||||||
if isinstance(Trigger, tuple):
|
if isinstance(Trigger, tuple):
|
||||||
if Message[0].lower().startswith(Trigger[0], 0, Trigger[1]):
|
if Message[0].lower().startswith(Trigger[0], 0, Trigger[1]):
|
||||||
Match = True
|
Match = True
|
||||||
elif isinstance(Trigger, str):
|
elif isinstance(Trigger, str):
|
||||||
if Message[0].lower() == Trigger.lower():
|
if Message[0].lower() == Trigger.lower():
|
||||||
Match = True
|
Match = True
|
||||||
else: # compiled regex
|
else: # compiled regex
|
||||||
RMatch = Trigger.search(line)
|
RMatch = Trigger.search(line)
|
||||||
if RMatch:
|
if RMatch:
|
||||||
Match = True
|
Match = True
|
||||||
|
|
||||||
if not Match:
|
if not Match:
|
||||||
continue
|
continue
|
||||||
|
|
||||||
self.Logger.debug(sys._getframe().f_code.co_name + " \"{0}\" Match -> {1} | {2}".format(player.Name, Command.__class__.__name__, Trigger))
|
self.Logger.debug(sys._getframe().f_code.co_name + " \"{0}\" Match -> {1} | {2}".format(player.Name, Command.__class__.__name__, Trigger))
|
||||||
|
|
||||||
if Level < Command.Level:
|
if Level < Command.Level:
|
||||||
RetMessage = "You do not have access to this command! (You: {0} | Required: {1})".format(Level, Command.Level)
|
RetMessage = "You do not have access to this command! (You: {0} | Required: {1})".format(Level, Command.Level)
|
||||||
continue
|
continue
|
||||||
|
|
||||||
try:
|
try:
|
||||||
if RMatch:
|
if RMatch:
|
||||||
Ret = await Command._rfunc(line, RMatch, player)
|
Ret = await Command._rfunc(line, RMatch, player)
|
||||||
else:
|
else:
|
||||||
Ret = await Command._func(Message, player)
|
#self.Logger.debug(f"_rfunc line: {line}")
|
||||||
except Exception as e:
|
if line.startswith("!yt"): #transfering the line if its !yt or !yts in case people want to include pitch or tempo.
|
||||||
self.Logger.error(traceback.format_exc())
|
Ret = await Command._func(Message, player, line)
|
||||||
self.Torchlight().SayChat("Error: {0}".format(str(e)))
|
else:
|
||||||
|
Ret = await Command._func(Message, player)
|
||||||
|
except Exception as e:
|
||||||
|
self.Logger.error(traceback.format_exc())
|
||||||
|
self.Torchlight().SayChat("Error: {0}".format(str(e)))
|
||||||
|
|
||||||
RetMessage = None
|
RetMessage = None
|
||||||
|
|
||||||
if isinstance(Ret, str):
|
if isinstance(Ret, str):
|
||||||
Message = Ret.split(sep = ' ', maxsplit = 1)
|
Message = Ret.split(sep = ' ', maxsplit = 1)
|
||||||
Ret = None
|
Ret = None
|
||||||
|
|
||||||
if Ret != None and Ret > 0:
|
if Ret != None and Ret > 0:
|
||||||
break
|
break
|
||||||
|
|
||||||
if Ret != None and Ret >= 0:
|
if Ret != None and Ret >= 0:
|
||||||
break
|
break
|
||||||
|
|
||||||
if RetMessage:
|
if RetMessage:
|
||||||
self.Torchlight().SayPrivate(player, RetMessage)
|
self.Torchlight().SayPrivate(player, RetMessage)
|
||||||
|
|
||||||
if self.NeedsReload:
|
if self.NeedsReload:
|
||||||
self.NeedsReload = False
|
self.NeedsReload = False
|
||||||
self.Reload()
|
self.Reload()
|
||||||
|
|
||||||
return Ret
|
return Ret
|
||||||
|
@ -8,6 +8,28 @@ import math
|
|||||||
from .Utils import Utils, DataHolder
|
from .Utils import Utils, DataHolder
|
||||||
import traceback
|
import traceback
|
||||||
|
|
||||||
|
def get_rubberBand(message):
|
||||||
|
rubberband = []
|
||||||
|
try:
|
||||||
|
for msg in message[1].split(" "): #checking if pitch= or tempo= is specified
|
||||||
|
if "tempo=" in msg:
|
||||||
|
tempo = float(msg.split("tempo=",1)[1])
|
||||||
|
if tempo < 0.0:
|
||||||
|
tempo = 0.01
|
||||||
|
if tempo > 20:
|
||||||
|
tempo = 20
|
||||||
|
rubberband.append(f"rubberband=tempo={tempo}")
|
||||||
|
elif "pitch=" in msg:
|
||||||
|
pitch = float(msg.split("pitch=",1)[1])
|
||||||
|
if pitch < 0.0:
|
||||||
|
pitch = 0.1
|
||||||
|
if pitch > 5.0:
|
||||||
|
pitch = 5.0
|
||||||
|
rubberband.append(f"rubberband=pitch={pitch}")
|
||||||
|
except Exception:
|
||||||
|
pass
|
||||||
|
return rubberband
|
||||||
|
|
||||||
class BaseCommand():
|
class BaseCommand():
|
||||||
Order = 0
|
Order = 0
|
||||||
def __init__(self, torchlight):
|
def __init__(self, torchlight):
|
||||||
@ -525,25 +547,8 @@ class VoiceCommands(BaseCommand):
|
|||||||
elif Level < 2:
|
elif Level < 2:
|
||||||
return 0
|
return 0
|
||||||
|
|
||||||
rubberband = []
|
rubberband = get_rubberBand(message)
|
||||||
try:
|
|
||||||
for msg in message[1].split(" "): #checking if pitch= or tempo= is specified
|
|
||||||
if "tempo=" in msg:
|
|
||||||
tempo = float(msg.split("tempo=",1)[1])
|
|
||||||
if tempo < 0.0:
|
|
||||||
tempo = 0.01
|
|
||||||
if tempo > 20:
|
|
||||||
tempo = 20
|
|
||||||
rubberband.append(f"rubberband=tempo={tempo}")
|
|
||||||
elif "pitch=" in msg:
|
|
||||||
pitch = float(msg.split("pitch=",1)[1])
|
|
||||||
if pitch < 0.0:
|
|
||||||
pitch = 0.1
|
|
||||||
if pitch > 99:
|
|
||||||
pitch = 99
|
|
||||||
rubberband.append(f"rubberband=pitch={pitch}")
|
|
||||||
except Exception:
|
|
||||||
pass
|
|
||||||
if message[0] == "!random":
|
if message[0] == "!random":
|
||||||
Trigger = self.random.choice(list(self.VoiceTriggers.values()))
|
Trigger = self.random.choice(list(self.VoiceTriggers.values()))
|
||||||
if isinstance(Trigger, list):
|
if isinstance(Trigger, list):
|
||||||
@ -561,6 +566,7 @@ class VoiceCommands(BaseCommand):
|
|||||||
if isinstance(Sounds, list):
|
if isinstance(Sounds, list):
|
||||||
if Num and Num > 0 and Num <= len(Sounds):
|
if Num and Num > 0 and Num <= len(Sounds):
|
||||||
Sound = Sounds[Num - 1]
|
Sound = Sounds[Num - 1]
|
||||||
|
|
||||||
elif message[1] and not message[1].startswith("tempo=") and not message[1].startswith("pitch="): #it does not start with pitch or with tempo, so must be a number or alias.
|
elif message[1] and not message[1].startswith("tempo=") and not message[1].startswith("pitch="): #it does not start with pitch or with tempo, so must be a number or alias.
|
||||||
searching = message[1].startswith('?')
|
searching = message[1].startswith('?')
|
||||||
search = message[1][1:] if searching else message[1].split(" ")[0]
|
search = message[1][1:] if searching else message[1].split(" ")[0]
|
||||||
@ -617,7 +623,7 @@ class YouTube(BaseCommand):
|
|||||||
self.Triggers = ["!yt"]
|
self.Triggers = ["!yt"]
|
||||||
self.Level = 6
|
self.Level = 6
|
||||||
|
|
||||||
async def _func(self, message, player):
|
async def _func(self, message, player, line = None):
|
||||||
self.Logger.debug(sys._getframe().f_code.co_name + ' ' + str(message))
|
self.Logger.debug(sys._getframe().f_code.co_name + ' ' + str(message))
|
||||||
|
|
||||||
if self.check_disabled(player):
|
if self.check_disabled(player):
|
||||||
@ -637,8 +643,11 @@ class YouTube(BaseCommand):
|
|||||||
AudioClip = self.Torchlight().AudioManager.AudioClip(player, message[1])
|
AudioClip = self.Torchlight().AudioManager.AudioClip(player, message[1])
|
||||||
if not AudioClip:
|
if not AudioClip:
|
||||||
return 1
|
return 1
|
||||||
|
|
||||||
return AudioClip.Play(Time)
|
#turning the string into a list where get_rubberband just picks the second element to search in
|
||||||
|
dline = ['', line.split(" ", 1)[1]]
|
||||||
|
rubberband = get_rubberBand(dline)
|
||||||
|
return AudioClip.Play(Time, rubberband = rubberband)
|
||||||
|
|
||||||
class YouTubeSearch(BaseCommand):
|
class YouTubeSearch(BaseCommand):
|
||||||
import json
|
import json
|
||||||
@ -648,7 +657,7 @@ class YouTubeSearch(BaseCommand):
|
|||||||
self.Triggers = ["!yts"]
|
self.Triggers = ["!yts"]
|
||||||
self.Level = 6 #adjusting to new levels
|
self.Level = 6 #adjusting to new levels
|
||||||
|
|
||||||
async def _func(self, message, player):
|
async def _func(self, message, player, line = None):
|
||||||
self.Logger.debug(sys._getframe().f_code.co_name + ' ' + str(message))
|
self.Logger.debug(sys._getframe().f_code.co_name + ' ' + str(message))
|
||||||
|
|
||||||
if self.check_disabled(player):
|
if self.check_disabled(player):
|
||||||
@ -663,7 +672,8 @@ class YouTubeSearch(BaseCommand):
|
|||||||
Time = Utils.ParseTime(TimeStr)
|
Time = Utils.ParseTime(TimeStr)
|
||||||
message[1] = message[1][:Temp.value]
|
message[1] = message[1][:Temp.value]
|
||||||
|
|
||||||
Proc = await asyncio.create_subprocess_exec("yt-dlp", "--dump-json", "--username", "oauth2", "--password", "''", "-xg", "ytsearch:" + message[1],
|
search_term = message[1].split("pitch=")[0].split("tempo=")[0]
|
||||||
|
Proc = await asyncio.create_subprocess_exec("yt-dlp", "--dump-json", "--username", "oauth2", "--password", "''", "-xg", "ytsearch:" + search_term,
|
||||||
stdout = asyncio.subprocess.PIPE)
|
stdout = asyncio.subprocess.PIPE)
|
||||||
Out, _ = await Proc.communicate()
|
Out, _ = await Proc.communicate()
|
||||||
|
|
||||||
@ -679,7 +689,11 @@ class YouTubeSearch(BaseCommand):
|
|||||||
if not AudioClip:
|
if not AudioClip:
|
||||||
return 1
|
return 1
|
||||||
self.Torchlight().LastUrl = url
|
self.Torchlight().LastUrl = url
|
||||||
return AudioClip.Play(Time)
|
|
||||||
|
#turning the string into a list where get_rubberband just picks the second element to search in
|
||||||
|
dline = ['', line.split(" ", 1)[1]]
|
||||||
|
rubberband = get_rubberBand(dline)
|
||||||
|
return AudioClip.Play(Time, rubberband = rubberband)
|
||||||
|
|
||||||
|
|
||||||
class Say(BaseCommand):
|
class Say(BaseCommand):
|
||||||
@ -692,7 +706,8 @@ class Say(BaseCommand):
|
|||||||
self.Level = 2
|
self.Level = 2
|
||||||
|
|
||||||
async def Say(self, player, language, message):
|
async def Say(self, player, language, message):
|
||||||
GTTS = self.gtts.gTTS(text = message, lang = language)
|
actual_message = message.split("pitch=")[0].split("tempo=")[0]
|
||||||
|
GTTS = self.gtts.gTTS(text = actual_message, lang = language)
|
||||||
|
|
||||||
TempFile = self.tempfile.NamedTemporaryFile(delete = False)
|
TempFile = self.tempfile.NamedTemporaryFile(delete = False)
|
||||||
GTTS.write_to_fp(TempFile)
|
GTTS.write_to_fp(TempFile)
|
||||||
@ -702,8 +717,11 @@ class Say(BaseCommand):
|
|||||||
if not AudioClip:
|
if not AudioClip:
|
||||||
os.unlink(TempFile.name)
|
os.unlink(TempFile.name)
|
||||||
return 1
|
return 1
|
||||||
|
#turning the string into a list where get_rubberband just picks the second element to search in
|
||||||
|
dline = ['', message.split(" ", 1)[1]]
|
||||||
|
rubberband = get_rubberBand(dline)
|
||||||
|
|
||||||
if AudioClip.Play():
|
if AudioClip.Play(rubberband = rubberband):
|
||||||
AudioClip.AudioPlayer.AddCallback("Stop", lambda: os.unlink(TempFile.name))
|
AudioClip.AudioPlayer.AddCallback("Stop", lambda: os.unlink(TempFile.name))
|
||||||
return 0
|
return 0
|
||||||
else:
|
else:
|
||||||
|
Loading…
Reference in New Issue
Block a user