WIP: TextMods-Module #58
2 changed files with 414 additions and 3 deletions
|
@ -13,6 +13,7 @@ pub use crate::core::botmodules::ModulesManager;
|
|||
|
||||
// mod experiments;
|
||||
mod experimental;
|
||||
mod text_mods;
|
||||
|
||||
// [ ] init() function that accepts bot instance - this is passed to init() on submodules
|
||||
|
||||
|
@ -20,6 +21,7 @@ pub async fn init(mgr: Arc<ModulesManager>) {
|
|||
// Modules initializer loads modules into the bot
|
||||
// this is achieved by calling submodules that also have fn init() defined
|
||||
|
||||
// experiments::init(mgr).await
|
||||
experimental::init(mgr).await;
|
||||
}
|
||||
experimental::init(mgr.clone()).await;
|
||||
text_mods::init(Arc::clone(&mgr)).await;
|
||||
|
||||
}
|
409
src/custom/text_mods.rs
Normal file
409
src/custom/text_mods.rs
Normal file
|
@ -0,0 +1,409 @@
|
|||
//! A module about editing and messing around with user text
|
||||
//!
|
||||
use std::collections::HashMap;
|
||||
use std::sync::Arc;
|
||||
use rand::{thread_rng, Rng};
|
||||
use rand::seq::SliceRandom;
|
||||
use twitch_irc::message::ReplyToMessage;
|
||||
|
||||
use crate::core::bot_actions::{actions_util, ExecBodyParams};
|
||||
use crate::core::botinstance::Channel;
|
||||
use crate::core::botmodules::{BotActionTrait, BotCommand, BotModule, Listener, ModulesManager};
|
||||
use crate::core::identity::UserRole::*;
|
||||
const OF_CMD_CHANNEL:Channel = Channel(String::new());
|
||||
|
||||
pub async fn init(mgr: Arc<ModulesManager>) {
|
||||
|
||||
let replyer = BotCommand {
|
||||
module: BotModule(String::from("Replyer")),
|
||||
command: String::from("Reply"),
|
||||
alias: vec![
|
||||
String::from("reply")
|
||||
],
|
||||
exec_body: actions_util::asyncbox(thereplyer),
|
||||
help: String::from("txt mods help"),
|
||||
required_roles: vec![
|
||||
BotAdmin,
|
||||
Broadcaster,
|
||||
Mod(OF_CMD_CHANNEL),
|
||||
VIP(OF_CMD_CHANNEL),
|
||||
Chatter
|
||||
],
|
||||
};
|
||||
|
||||
replyer.add_to_modmgr(Arc::clone(&mgr)).await;
|
||||
|
||||
|
||||
let forsen_listener = Listener{
|
||||
module:BotModule(String::from("TextMods")),
|
||||
name:String::from("Forsen Listener"),
|
||||
exec_body:actions_util::asyncbox(forsenforsen),
|
||||
help:String::from("Forsen helper"),
|
||||
};
|
||||
forsen_listener.add_to_modmgr(Arc::clone(&mgr)).await;
|
||||
|
||||
|
||||
let butt = BotCommand{
|
||||
module:BotModule(String::from("ButtModule")),
|
||||
command:String::from("butt"),
|
||||
alias:vec![],
|
||||
exec_body:actions_util::asyncbox(butt),
|
||||
help:String::from("butt helper"),
|
||||
required_roles:vec![
|
||||
BotAdmin,
|
||||
Broadcaster,
|
||||
Mod(OF_CMD_CHANNEL),
|
||||
Chatter,
|
||||
]
|
||||
};
|
||||
butt.add_to_modmgr(Arc::clone(&mgr)).await;
|
||||
|
||||
let shuffler = BotCommand{
|
||||
module:BotModule(String::from("Shuffler")),
|
||||
command:String::from("Shuffle"),
|
||||
alias: vec![
|
||||
String::from("shuffle")
|
||||
],
|
||||
exec_body: actions_util::asyncbox(shuffle),
|
||||
help:String::from("Shuffle Help"),
|
||||
required_roles:vec![
|
||||
BotAdmin,
|
||||
Broadcaster,
|
||||
Mod(OF_CMD_CHANNEL),
|
||||
VIP(OF_CMD_CHANNEL),
|
||||
Chatter
|
||||
]
|
||||
};
|
||||
shuffler.add_to_modmgr(Arc::clone(&mgr)).await;
|
||||
|
||||
|
||||
let the8ball: BotCommand = BotCommand {
|
||||
module:BotModule(String::from("8ball")),
|
||||
command:String::from("8ball"),
|
||||
alias: vec![String::from("8b")],
|
||||
exec_body: actions_util::asyncbox(the8ball),
|
||||
help:String::from("8ball Help"),
|
||||
required_roles:vec![
|
||||
BotAdmin,
|
||||
Broadcaster,
|
||||
Mod(OF_CMD_CHANNEL),
|
||||
VIP(OF_CMD_CHANNEL),
|
||||
Chatter
|
||||
]
|
||||
};
|
||||
the8ball.add_to_modmgr(Arc::clone(&mgr)).await;
|
||||
|
||||
let percent:BotCommand = BotCommand{
|
||||
module:BotModule(String::from("percent")),
|
||||
command:String::from("%"),
|
||||
alias:vec![],
|
||||
exec_body: actions_util::asyncbox(percentage),
|
||||
help: String::from("Percent Help"),
|
||||
required_roles: vec![
|
||||
BotAdmin,
|
||||
Broadcaster,
|
||||
Mod(OF_CMD_CHANNEL),
|
||||
VIP(OF_CMD_CHANNEL),
|
||||
Chatter
|
||||
]
|
||||
};
|
||||
percent.add_to_modmgr(Arc::clone(&mgr)).await;
|
||||
|
||||
let filler: BotCommand = BotCommand{
|
||||
module:BotModule(String::from("filler")),
|
||||
command:String::from("fill"),
|
||||
alias:vec![String::from("Fill")],
|
||||
exec_body:actions_util::asyncbox(fill),
|
||||
help:String::from("fill Help"),
|
||||
required_roles: vec![
|
||||
BotAdmin,
|
||||
Broadcaster,
|
||||
Mod(OF_CMD_CHANNEL),
|
||||
VIP(OF_CMD_CHANNEL)
|
||||
]
|
||||
};
|
||||
filler.add_to_modmgr(Arc::clone(&mgr)).await;
|
||||
|
||||
}
|
||||
|
||||
///Fill command, can be used to make the bot reply with a certain quantity of the same message
|
||||
///
|
||||
/// only works with `(prefix)fill` `word` `quantity`
|
||||
///
|
||||
///
|
||||
async fn fill(params : ExecBodyParams)
|
||||
{
|
||||
let usermessage = usermsg(¶ms);
|
||||
let quantity = usermessage.get(&2).unwrap();
|
||||
let mut botreply = String::new();
|
||||
|
||||
for _i in 0..quantity.parse::<i32>().unwrap(){
|
||||
botreply.push_str(usermessage.get(&1).unwrap().trim());
|
||||
botreply.push(' ');
|
||||
}
|
||||
|
||||
let bot = Arc::clone(¶ms.bot);
|
||||
let botlock = bot.read().await;
|
||||
botlock
|
||||
.botmgrs
|
||||
.chat
|
||||
.say_in_reply(
|
||||
Channel(params.clone().msg.channel_login().to_string()),
|
||||
botreply.clone(),
|
||||
params.clone()
|
||||
).await;
|
||||
}
|
||||
|
||||
|
||||
///Percentage is a function that returns a ramdom %
|
||||
///
|
||||
async fn percentage (params : ExecBodyParams)
|
||||
{
|
||||
let mut _botreply = String::new();
|
||||
let rng = thread_rng().gen_range(0..100);
|
||||
let rng_string = rng.to_string();
|
||||
_botreply = rng_string + "%";
|
||||
|
||||
let bot = Arc::clone(¶ms.bot);
|
||||
let botlock = bot.read().await;
|
||||
botlock
|
||||
.botmgrs
|
||||
.chat
|
||||
.say_in_reply(
|
||||
Channel(params.clone().msg.channel_login().to_string()),
|
||||
_botreply.clone(),
|
||||
params.clone()
|
||||
).await;
|
||||
}
|
||||
|
||||
|
||||
///The 8 ball function
|
||||
/// it returns a answear to the user message based on random
|
||||
///
|
||||
async fn the8ball(params : ExecBodyParams)
|
||||
{
|
||||
|
||||
let mut vecanswears = Vec::new();
|
||||
vecanswears.push(String::from("It is certain"));
|
||||
vecanswears.push(String::from("It is decidedly so"));
|
||||
vecanswears.push(String::from("Without a doubt"));
|
||||
vecanswears.push(String::from("Yes definitely"));
|
||||
vecanswears.push(String::from("You may rely on it"));
|
||||
|
||||
vecanswears.push(String::from("As I see it, yes"));
|
||||
vecanswears.push(String::from("Most likely"));
|
||||
vecanswears.push(String::from("Outlook good"));
|
||||
vecanswears.push(String::from("Yes"));
|
||||
vecanswears.push(String::from("Signs point to yes"));
|
||||
|
||||
vecanswears.push(String::from("Reply hazy, try again"));
|
||||
vecanswears.push(String::from("Ask again later"));
|
||||
vecanswears.push(String::from("Better not tell you now"));
|
||||
vecanswears.push(String::from("Cannot predict now"));
|
||||
vecanswears.push(String::from("Concentrate and ask again"));
|
||||
|
||||
vecanswears.push(String::from("Don't count on it"));
|
||||
vecanswears.push(String::from("My reply is no"));
|
||||
vecanswears.push(String::from("My sources say no"));
|
||||
vecanswears.push(String::from("Outlook not so good"));
|
||||
vecanswears.push(String::from("Very doubtful"));
|
||||
|
||||
|
||||
let randchoice = thread_rng().gen_range(0..vecanswears.len());
|
||||
let ballmessage = &vecanswears[randchoice];
|
||||
|
||||
let bot = Arc::clone(¶ms.bot);
|
||||
let botlock = bot.read().await;
|
||||
botlock
|
||||
.botmgrs
|
||||
.chat
|
||||
.say_in_reply(
|
||||
Channel(params.clone().msg.channel_login().to_string()),
|
||||
ballmessage.clone(),
|
||||
params.clone()
|
||||
).await;
|
||||
}
|
||||
|
||||
|
||||
/// Shuffle Function
|
||||
///
|
||||
/// Grabs The user message and checks how many words it has
|
||||
///
|
||||
/// If the user message constains more the one word, it shuffles the words
|
||||
///
|
||||
/// If its only One word, it shuffles the letters in the word
|
||||
async fn shuffle(params : ExecBodyParams)
|
||||
{
|
||||
let usermessage = usermsg(¶ms);
|
||||
|
||||
if usermessage.len() > 2
|
||||
{
|
||||
|
||||
let mut indexes: Vec<usize> = (1..usermessage.len()).collect();
|
||||
indexes.shuffle(&mut thread_rng());
|
||||
|
||||
let mut new_reply: HashMap<usize, String> = HashMap::new();
|
||||
for (index, &new_index) in indexes.iter().enumerate() {
|
||||
new_reply.insert(index, usermessage[&new_index].clone());
|
||||
}
|
||||
let mut botreply = String::new();
|
||||
for value in new_reply.values(){
|
||||
botreply.push_str(value);
|
||||
botreply.push(' ');
|
||||
}
|
||||
|
||||
|
||||
let bot = Arc::clone(¶ms.bot);
|
||||
let botlock = bot.read().await;
|
||||
botlock
|
||||
.botmgrs
|
||||
.chat
|
||||
.say_in_reply(
|
||||
Channel(params.clone().msg.channel_login().to_string()),
|
||||
botreply,
|
||||
params.clone()
|
||||
).await;
|
||||
|
||||
}
|
||||
else {
|
||||
//if it only has one word, shuffle its chars
|
||||
let word = usermessage.get(&1).unwrap();
|
||||
|
||||
let shuffle_word: String =
|
||||
word.chars()
|
||||
.collect::<Vec<char>>()
|
||||
.choose_multiple(&mut thread_rng(), word.len())
|
||||
.collect();
|
||||
|
||||
let bot = Arc::clone(¶ms.bot);
|
||||
let botlock = bot.read().await;
|
||||
botlock
|
||||
.botmgrs
|
||||
.chat
|
||||
.say_in_reply(
|
||||
Channel(params.clone().msg.channel_login().to_string()),
|
||||
shuffle_word,
|
||||
params.clone()
|
||||
).await;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
///butt command hehe
|
||||
///
|
||||
/// All this function does is grab the user message, and randomly pick one of the words
|
||||
/// in the phrase to change the random word for `butt`
|
||||
///
|
||||
async fn butt(params : ExecBodyParams)
|
||||
{
|
||||
//getting User message
|
||||
let mut userm = usermsg(¶ms);
|
||||
|
||||
//choose a random word from the user phrase
|
||||
let w = thread_rng().gen_range(1..userm.len());
|
||||
|
||||
//change the random word to butt :pepepains
|
||||
userm.insert(w, String::from("Butt"));
|
||||
|
||||
|
||||
let mut bot_reply = String::new();
|
||||
|
||||
for index in 1..userm.len()
|
||||
{
|
||||
if let Some(word) = userm.get(&index)
|
||||
{
|
||||
bot_reply.push_str(word);
|
||||
bot_reply.push(' ');
|
||||
}
|
||||
}
|
||||
|
||||
let bot = Arc::clone(¶ms.bot);
|
||||
let botlock = bot.read().await;
|
||||
botlock
|
||||
.botmgrs
|
||||
.chat
|
||||
.say_in_reply(
|
||||
Channel(params.clone().msg.channel_login().to_string()),
|
||||
bot_reply,
|
||||
params.clone()
|
||||
).await;
|
||||
|
||||
}
|
||||
|
||||
///Forsen.
|
||||
async fn forsenforsen(params : ExecBodyParams)
|
||||
{
|
||||
if params.msg.message_text == "forsen" || params.msg.message_text == "Forsen"
|
||||
{
|
||||
let bot = Arc::clone(¶ms.bot);
|
||||
let botlock = bot.read().await;
|
||||
botlock
|
||||
.botmgrs
|
||||
.chat
|
||||
.say_in_reply(
|
||||
Channel(params.clone().msg.channel_login().to_string()),
|
||||
String::from("Forsen!"),
|
||||
params.clone()
|
||||
).await;
|
||||
}
|
||||
}
|
||||
|
||||
///Thereplyer Function
|
||||
///
|
||||
/// This Function grabs the user message and reply the same message, without the command
|
||||
/// at the beginning
|
||||
///
|
||||
async fn thereplyer(params : ExecBodyParams)
|
||||
{
|
||||
let user_message: HashMap<usize,String> = usermsg(¶ms);
|
||||
let mut bot_reply = String::new();
|
||||
|
||||
for index in 1..user_message.len()
|
||||
{
|
||||
if let Some(word) = user_message.get(&index)
|
||||
{
|
||||
bot_reply.push_str(word);
|
||||
bot_reply.push(' ');
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
let bot = Arc::clone(¶ms.bot);
|
||||
let botlock = bot.read().await;
|
||||
botlock
|
||||
.botmgrs
|
||||
.chat
|
||||
.say_in_reply(
|
||||
Channel(params.clone().msg.channel_login().to_string()),
|
||||
bot_reply.clone(),
|
||||
params.clone()
|
||||
).await;
|
||||
|
||||
}
|
||||
|
||||
///Usermsg Function
|
||||
///
|
||||
/// Usage: this function grabs the user message, and indexate with a vector and hashmap
|
||||
///
|
||||
/// It returns the User message as a `Hashmap<usize,String>`, with indexs so you can utilize especific words
|
||||
///
|
||||
/// Where `Usize` is index and `String` is the word
|
||||
pub fn usermsg(params : &ExecBodyParams) -> HashMap<usize,String>
|
||||
{
|
||||
//getting the user message
|
||||
let sender_message = ¶ms.msg.message_text;
|
||||
|
||||
//vector to store the words
|
||||
let words: Vec<&str> = sender_message.split_whitespace().collect();
|
||||
|
||||
//using Hashmap to store the words
|
||||
let mut index_words:HashMap<usize,String> = HashMap::new();
|
||||
|
||||
//adding to the hashmap each word
|
||||
for(index,word) in words.iter().enumerate()
|
||||
{
|
||||
index_words.insert(index, String::from(*word));
|
||||
}
|
||||
index_words
|
||||
|
||||
}
|
Loading…
Reference in a new issue