diff --git a/build.gradle b/build.gradle new file mode 100644 index 0000000..75d7a70 --- /dev/null +++ b/build.gradle @@ -0,0 +1,53 @@ +/* + * This file was generated by the Gradle 'init' task. + * + * This generated file contains a sample Java project to get you started. + * For more details take a look at the Java Quickstart chapter in the Gradle + * User Manual available at https://docs.gradle.org/5.6/userguide/tutorial_java_projects.html + */ + +plugins { + // Apply the java plugin to add support for Java + id 'java' + + // Apply the application plugin to add support for building a CLI application + id 'application' + + // Shadow plugin to make uberJars + id 'com.github.johnrengelman.shadow' version '6.1.0' +} + +repositories { + // Use jcenter for resolving dependencies. + // You can declare any Maven/Ivy/file repository here. + jcenter() +} + +dependencies { + // This dependency is used by the application.// + implementation 'com.google.guava:guava:28.0-jre' + //implementation 'org.slf4j:slf4j-log4j12:2.0.0-alpha0' + implementation 'org.slf4j:slf4j-simple:2.0.0-alpha0' + + implementation 'net.lingala.zip4j:zip4j:2.5.2' + implementation 'club.minnced:opus-java:1.0.4' + + implementation 'ws.schild:jave-all-deps:2.7.3' + implementation 'org.apache.commons:commons-lang3:3.0' + implementation 'com.sedmelluq:lavaplayer:1.3.67' + implementation 'net.dv8tion:JDA:4.2.0_227' + + // Use JUnit test framework + testImplementation 'junit:junit:4.12' +} + +application { + // Define the main class for the application + mainClassName = 'fr.Skydust.JdrBot.JdrBot' +} + +jar { + manifest { + attributes('Manifest-Version': '1.0', 'Main-Class': 'fr.Skydust.JdrBot.JdrBot'); + } +} \ No newline at end of file diff --git a/gradle/wrapper/gradle-wrapper.jar b/gradle/wrapper/gradle-wrapper.jar new file mode 100644 index 0000000..e708b1c Binary files /dev/null and b/gradle/wrapper/gradle-wrapper.jar differ diff --git a/gradle/wrapper/gradle-wrapper.properties b/gradle/wrapper/gradle-wrapper.properties new file mode 100644 index 0000000..be52383 --- /dev/null +++ b/gradle/wrapper/gradle-wrapper.properties @@ -0,0 +1,5 @@ +distributionBase=GRADLE_USER_HOME +distributionPath=wrapper/dists +distributionUrl=https\://services.gradle.org/distributions/gradle-6.7-bin.zip +zipStoreBase=GRADLE_USER_HOME +zipStorePath=wrapper/dists diff --git a/gradlew b/gradlew new file mode 100755 index 0000000..4f906e0 --- /dev/null +++ b/gradlew @@ -0,0 +1,185 @@ +#!/usr/bin/env sh + +# +# Copyright 2015 the original author or authors. +# +# Licensed under the Apache License, Version 2.0 (the "License"); +# you may not use this file except in compliance with the License. +# You may obtain a copy of the License at +# +# https://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, +# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +# See the License for the specific language governing permissions and +# limitations under the License. +# + +############################################################################## +## +## Gradle start up script for UN*X +## +############################################################################## + +# Attempt to set APP_HOME +# Resolve links: $0 may be a link +PRG="$0" +# Need this for relative symlinks. +while [ -h "$PRG" ] ; do + ls=`ls -ld "$PRG"` + link=`expr "$ls" : '.*-> \(.*\)$'` + if expr "$link" : '/.*' > /dev/null; then + PRG="$link" + else + PRG=`dirname "$PRG"`"/$link" + fi +done +SAVED="`pwd`" +cd "`dirname \"$PRG\"`/" >/dev/null +APP_HOME="`pwd -P`" +cd "$SAVED" >/dev/null + +APP_NAME="Gradle" +APP_BASE_NAME=`basename "$0"` + +# Add default JVM options here. You can also use JAVA_OPTS and GRADLE_OPTS to pass JVM options to this script. +DEFAULT_JVM_OPTS='"-Xmx64m" "-Xms64m"' + +# Use the maximum available, or set MAX_FD != -1 to use that value. +MAX_FD="maximum" + +warn () { + echo "$*" +} + +die () { + echo + echo "$*" + echo + exit 1 +} + +# OS specific support (must be 'true' or 'false'). +cygwin=false +msys=false +darwin=false +nonstop=false +case "`uname`" in + CYGWIN* ) + cygwin=true + ;; + Darwin* ) + darwin=true + ;; + MINGW* ) + msys=true + ;; + NONSTOP* ) + nonstop=true + ;; +esac + +CLASSPATH=$APP_HOME/gradle/wrapper/gradle-wrapper.jar + + +# Determine the Java command to use to start the JVM. +if [ -n "$JAVA_HOME" ] ; then + if [ -x "$JAVA_HOME/jre/sh/java" ] ; then + # IBM's JDK on AIX uses strange locations for the executables + JAVACMD="$JAVA_HOME/jre/sh/java" + else + JAVACMD="$JAVA_HOME/bin/java" + fi + if [ ! -x "$JAVACMD" ] ; then + die "ERROR: JAVA_HOME is set to an invalid directory: $JAVA_HOME + +Please set the JAVA_HOME variable in your environment to match the +location of your Java installation." + fi +else + JAVACMD="java" + which java >/dev/null 2>&1 || die "ERROR: JAVA_HOME is not set and no 'java' command could be found in your PATH. + +Please set the JAVA_HOME variable in your environment to match the +location of your Java installation." +fi + +# Increase the maximum file descriptors if we can. +if [ "$cygwin" = "false" -a "$darwin" = "false" -a "$nonstop" = "false" ] ; then + MAX_FD_LIMIT=`ulimit -H -n` + if [ $? -eq 0 ] ; then + if [ "$MAX_FD" = "maximum" -o "$MAX_FD" = "max" ] ; then + MAX_FD="$MAX_FD_LIMIT" + fi + ulimit -n $MAX_FD + if [ $? -ne 0 ] ; then + warn "Could not set maximum file descriptor limit: $MAX_FD" + fi + else + warn "Could not query maximum file descriptor limit: $MAX_FD_LIMIT" + fi +fi + +# For Darwin, add options to specify how the application appears in the dock +if $darwin; then + GRADLE_OPTS="$GRADLE_OPTS \"-Xdock:name=$APP_NAME\" \"-Xdock:icon=$APP_HOME/media/gradle.icns\"" +fi + +# For Cygwin or MSYS, switch paths to Windows format before running java +if [ "$cygwin" = "true" -o "$msys" = "true" ] ; then + APP_HOME=`cygpath --path --mixed "$APP_HOME"` + CLASSPATH=`cygpath --path --mixed "$CLASSPATH"` + + JAVACMD=`cygpath --unix "$JAVACMD"` + + # We build the pattern for arguments to be converted via cygpath + ROOTDIRSRAW=`find -L / -maxdepth 1 -mindepth 1 -type d 2>/dev/null` + SEP="" + for dir in $ROOTDIRSRAW ; do + ROOTDIRS="$ROOTDIRS$SEP$dir" + SEP="|" + done + OURCYGPATTERN="(^($ROOTDIRS))" + # Add a user-defined pattern to the cygpath arguments + if [ "$GRADLE_CYGPATTERN" != "" ] ; then + OURCYGPATTERN="$OURCYGPATTERN|($GRADLE_CYGPATTERN)" + fi + # Now convert the arguments - kludge to limit ourselves to /bin/sh + i=0 + for arg in "$@" ; do + CHECK=`echo "$arg"|egrep -c "$OURCYGPATTERN" -` + CHECK2=`echo "$arg"|egrep -c "^-"` ### Determine if an option + + if [ $CHECK -ne 0 ] && [ $CHECK2 -eq 0 ] ; then ### Added a condition + eval `echo args$i`=`cygpath --path --ignore --mixed "$arg"` + else + eval `echo args$i`="\"$arg\"" + fi + i=`expr $i + 1` + done + case $i in + 0) set -- ;; + 1) set -- "$args0" ;; + 2) set -- "$args0" "$args1" ;; + 3) set -- "$args0" "$args1" "$args2" ;; + 4) set -- "$args0" "$args1" "$args2" "$args3" ;; + 5) set -- "$args0" "$args1" "$args2" "$args3" "$args4" ;; + 6) set -- "$args0" "$args1" "$args2" "$args3" "$args4" "$args5" ;; + 7) set -- "$args0" "$args1" "$args2" "$args3" "$args4" "$args5" "$args6" ;; + 8) set -- "$args0" "$args1" "$args2" "$args3" "$args4" "$args5" "$args6" "$args7" ;; + 9) set -- "$args0" "$args1" "$args2" "$args3" "$args4" "$args5" "$args6" "$args7" "$args8" ;; + esac +fi + +# Escape application args +save () { + for i do printf %s\\n "$i" | sed "s/'/'\\\\''/g;1s/^/'/;\$s/\$/' \\\\/" ; done + echo " " +} +APP_ARGS=`save "$@"` + +# Collect all arguments for the java command, following the shell quoting and substitution rules +eval set -- $DEFAULT_JVM_OPTS $JAVA_OPTS $GRADLE_OPTS "\"-Dorg.gradle.appname=$APP_BASE_NAME\"" -classpath "\"$CLASSPATH\"" org.gradle.wrapper.GradleWrapperMain "$APP_ARGS" + +exec "$JAVACMD" "$@" diff --git a/gradlew.bat b/gradlew.bat new file mode 100644 index 0000000..ac1b06f --- /dev/null +++ b/gradlew.bat @@ -0,0 +1,89 @@ +@rem +@rem Copyright 2015 the original author or authors. +@rem +@rem Licensed under the Apache License, Version 2.0 (the "License"); +@rem you may not use this file except in compliance with the License. +@rem You may obtain a copy of the License at +@rem +@rem https://www.apache.org/licenses/LICENSE-2.0 +@rem +@rem Unless required by applicable law or agreed to in writing, software +@rem distributed under the License is distributed on an "AS IS" BASIS, +@rem WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +@rem See the License for the specific language governing permissions and +@rem limitations under the License. +@rem + +@if "%DEBUG%" == "" @echo off +@rem ########################################################################## +@rem +@rem Gradle startup script for Windows +@rem +@rem ########################################################################## + +@rem Set local scope for the variables with windows NT shell +if "%OS%"=="Windows_NT" setlocal + +set DIRNAME=%~dp0 +if "%DIRNAME%" == "" set DIRNAME=. +set APP_BASE_NAME=%~n0 +set APP_HOME=%DIRNAME% + +@rem Resolve any "." and ".." in APP_HOME to make it shorter. +for %%i in ("%APP_HOME%") do set APP_HOME=%%~fi + +@rem Add default JVM options here. You can also use JAVA_OPTS and GRADLE_OPTS to pass JVM options to this script. +set DEFAULT_JVM_OPTS="-Xmx64m" "-Xms64m" + +@rem Find java.exe +if defined JAVA_HOME goto findJavaFromJavaHome + +set JAVA_EXE=java.exe +%JAVA_EXE% -version >NUL 2>&1 +if "%ERRORLEVEL%" == "0" goto execute + +echo. +echo ERROR: JAVA_HOME is not set and no 'java' command could be found in your PATH. +echo. +echo Please set the JAVA_HOME variable in your environment to match the +echo location of your Java installation. + +goto fail + +:findJavaFromJavaHome +set JAVA_HOME=%JAVA_HOME:"=% +set JAVA_EXE=%JAVA_HOME%/bin/java.exe + +if exist "%JAVA_EXE%" goto execute + +echo. +echo ERROR: JAVA_HOME is set to an invalid directory: %JAVA_HOME% +echo. +echo Please set the JAVA_HOME variable in your environment to match the +echo location of your Java installation. + +goto fail + +:execute +@rem Setup the command line + +set CLASSPATH=%APP_HOME%\gradle\wrapper\gradle-wrapper.jar + + +@rem Execute Gradle +"%JAVA_EXE%" %DEFAULT_JVM_OPTS% %JAVA_OPTS% %GRADLE_OPTS% "-Dorg.gradle.appname=%APP_BASE_NAME%" -classpath "%CLASSPATH%" org.gradle.wrapper.GradleWrapperMain %* + +:end +@rem End local scope for the variables with windows NT shell +if "%ERRORLEVEL%"=="0" goto mainEnd + +:fail +rem Set variable GRADLE_EXIT_CONSOLE if you need the _script_ return code instead of +rem the _cmd.exe /c_ return code! +if not "" == "%GRADLE_EXIT_CONSOLE%" exit 1 +exit /b 1 + +:mainEnd +if "%OS%"=="Windows_NT" endlocal + +:omega diff --git a/out/production/resources/META-INF/MANIFEST.MF b/out/production/resources/META-INF/MANIFEST.MF new file mode 100644 index 0000000..862686b --- /dev/null +++ b/out/production/resources/META-INF/MANIFEST.MF @@ -0,0 +1,3 @@ +Manifest-Version: 1.0 +Main-Class: fr.Skydust.JdrBot.JdrBot + diff --git a/settings.gradle b/settings.gradle new file mode 100644 index 0000000..8512e14 --- /dev/null +++ b/settings.gradle @@ -0,0 +1,2 @@ +rootProject.name = 'JdrBot' + diff --git a/src/main/java/.idea/workspace.xml b/src/main/java/.idea/workspace.xml new file mode 100644 index 0000000..9b1009f --- /dev/null +++ b/src/main/java/.idea/workspace.xml @@ -0,0 +1,54 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + 1616004344851 + + + + + + + \ No newline at end of file diff --git a/src/main/java/fr/Skydust/JdrBot/JdrBot.java b/src/main/java/fr/Skydust/JdrBot/JdrBot.java new file mode 100755 index 0000000..97d7c34 --- /dev/null +++ b/src/main/java/fr/Skydust/JdrBot/JdrBot.java @@ -0,0 +1,55 @@ +package fr.Skydust.JdrBot; + +import java.time.LocalDateTime; +import java.util.ArrayList; +import java.util.List; +import javax.security.auth.login.LoginException; + +import fr.Skydust.JdrBot.cmds.*; +import fr.Skydust.JdrBot.cmds.playmusic.*; +import fr.Skydust.JdrBot.stock.Command; +import net.dv8tion.jda.api.JDA; +import net.dv8tion.jda.api.JDABuilder; +import net.dv8tion.jda.api.entities.Activity; + +public class JdrBot { + public static String Version = "2.4"; + + static JDA jda; + public static LocalDateTime basedate; + public static List commandList; + + public static String startcmdchar = "!|:"; + + public static void main(String args[]) { + try { + basedate = LocalDateTime.now(); + jda = JDABuilder.createDefault("MTY5OTMzMzgxMDMzOTE4NDY0.DerlJg.m7BdNv_OMHlYa-f4T3O0jJ9LldM").build(); + jda.awaitReady(); + jda.getPresence().setActivity(Activity.playing("un jeu de rôle")); + + commandList = new ArrayList(); + + registerCommand(new Aide()); + registerCommand(new Etat()); + registerCommand(new Roll()); + //registerCommand(new Record()); + //registerCommand(new StopRecord()); + registerCommand(new Emote()); + registerCommand(new PlayMusic()); + registerCommand(new StopMusic()); + registerCommand(new FLoad()); + registerCommand(new FLoadLoop()); + + jda.addEventListener(new JdrBotListener()); + } catch (LoginException e) { + System.out.println("The login token is wrong"); + } catch (Exception e) { + e.printStackTrace(); + } + } + + public static void registerCommand(Command cmd) { + commandList.add(cmd); + } +} diff --git a/src/main/java/fr/Skydust/JdrBot/JdrBotListener.java b/src/main/java/fr/Skydust/JdrBot/JdrBotListener.java new file mode 100755 index 0000000..d0a9a1a --- /dev/null +++ b/src/main/java/fr/Skydust/JdrBot/JdrBotListener.java @@ -0,0 +1,60 @@ +package fr.Skydust.JdrBot; + +import java.util.Random; + +import fr.Skydust.JdrBot.cmds.LastTimeOnline; +import fr.Skydust.JdrBot.cmds.playmusic.PlayMusic; +import fr.Skydust.JdrBot.jukebox.JukeboxGUISystem; +import fr.Skydust.JdrBot.stock.Command; +import net.dv8tion.jda.api.events.guild.voice.GuildVoiceLeaveEvent; +import net.dv8tion.jda.api.events.guild.voice.GuildVoiceMoveEvent; +import net.dv8tion.jda.api.events.message.guild.GuildMessageReceivedEvent; +import net.dv8tion.jda.api.events.message.react.MessageReactionAddEvent; +import net.dv8tion.jda.api.events.user.update.UserUpdateOnlineStatusEvent; +import net.dv8tion.jda.api.hooks.ListenerAdapter; + +public class JdrBotListener extends ListenerAdapter { + + Random r = new Random(); + + @Override + public void onGuildMessageReceived(GuildMessageReceivedEvent e) { + System.out.println(e.getMessage().getAuthor().getName() + ": " + e.getMessage().getContentRaw()); + + // IF it doesn't start with the startcmdchar, ignore for optimization + if (!e.getMessage().getContentRaw().matches("^("+ JdrBot.startcmdchar+").*$") || e.getMessage().getAuthor().isBot()) + return; + + // Go through all cmds and call the one corresponding + for (Command cmd : JdrBot.commandList) { + if (isACommand(e.getMessage().getContentRaw(), cmd.cmdName)) { + cmd.call(e); + return; + } + } + + if (isACommand(e.getMessage().getContentRaw(), "yay")) + { + e.getChannel().sendMessage("Bien joue! Tu as su surpasse toutes les epreuves pour en arriver la! Je suis fier de toi!").queue(); + } + } + + @Override + public void onUserUpdateOnlineStatus(UserUpdateOnlineStatusEvent e) { + LastTimeOnline.onUserUpdateOnlineStatus(e); + } + @Override + public void onGuildVoiceMove(GuildVoiceMoveEvent e) { + PlayMusic.onGuildVoiceMove(e); + } + @Override + public void onGuildVoiceLeave(GuildVoiceLeaveEvent e) { + PlayMusic.onGuildVoiceLeave(e); + } + @Override + public void onMessageReactionAdd(MessageReactionAddEvent e) { JukeboxGUISystem.onMessageReactionAdd(e); } + + public boolean isACommand(String message, String cmd) { + return message.matches("^("+ JdrBot.startcmdchar+")("+cmd+").*$"); + } +} \ No newline at end of file diff --git a/src/main/java/fr/Skydust/JdrBot/audio/GuildMusicManager.java b/src/main/java/fr/Skydust/JdrBot/audio/GuildMusicManager.java new file mode 100755 index 0000000..c33d29c --- /dev/null +++ b/src/main/java/fr/Skydust/JdrBot/audio/GuildMusicManager.java @@ -0,0 +1,35 @@ +package fr.Skydust.JdrBot.audio; + +import com.sedmelluq.discord.lavaplayer.player.AudioPlayer; +import com.sedmelluq.discord.lavaplayer.player.AudioPlayerManager; + +import fr.Skydust.JdrBot.audio.handler.JdrBotASH; +import net.dv8tion.jda.api.managers.AudioManager; + +public class GuildMusicManager { + /** + * Audio player for the guild. + */ + public final AudioPlayer player; + /** + * Track scheduler for the player. + */ + public final TrackScheduler scheduler; + + /** + * Creates a player and a track scheduler. + * @param manager Audio player manager to use for creating the player. + */ + public GuildMusicManager(AudioPlayerManager manager, AudioManager am) { + player = manager.createPlayer(); + scheduler = new TrackScheduler(player, am); + player.addListener(scheduler); + } + + /** + * @return Wrapper around AudioPlayer to use it as an AudioSendHandler. + */ + public JdrBotASH getSendHandler() { + return new JdrBotASH(player); + } +} \ No newline at end of file diff --git a/src/main/java/fr/Skydust/JdrBot/audio/TrackScheduler.java b/src/main/java/fr/Skydust/JdrBot/audio/TrackScheduler.java new file mode 100755 index 0000000..4f78b3c --- /dev/null +++ b/src/main/java/fr/Skydust/JdrBot/audio/TrackScheduler.java @@ -0,0 +1,42 @@ +package fr.Skydust.JdrBot.audio; + +import com.sedmelluq.discord.lavaplayer.player.AudioPlayer; +import com.sedmelluq.discord.lavaplayer.player.event.AudioEventAdapter; +import com.sedmelluq.discord.lavaplayer.track.AudioTrack; +import com.sedmelluq.discord.lavaplayer.track.AudioTrackEndReason; + +import net.dv8tion.jda.api.managers.AudioManager; + +public class TrackScheduler extends AudioEventAdapter { + private final AudioPlayer player; + private boolean loop; + private AudioManager am; + + public TrackScheduler(AudioPlayer player, AudioManager am) { + this.player = player; + loop = true; + this.am = am; + } + + public void play(AudioTrack track, boolean loop) { + player.startTrack(track, false); + this.loop = loop; + } + + public void stop() { + player.stopTrack(); + } + + @Override + public void onTrackEnd(AudioPlayer player, AudioTrack track, AudioTrackEndReason endReason) { + if (endReason.mayStartNext) { + if(loop) { + player.startTrack(track.makeClone(), false); + System.out.println("Launching track:"+track.getInfo().title); + } else { + stop(); + //am.closeAudioConnection(); + } + } + } +} \ No newline at end of file diff --git a/src/main/java/fr/Skydust/JdrBot/audio/handler/JdrBotARH.java b/src/main/java/fr/Skydust/JdrBot/audio/handler/JdrBotARH.java new file mode 100755 index 0000000..b7ae13f --- /dev/null +++ b/src/main/java/fr/Skydust/JdrBot/audio/handler/JdrBotARH.java @@ -0,0 +1,36 @@ +package fr.Skydust.JdrBot.audio.handler; + +import fr.Skydust.JdrBot.cmds.record.Record; +import net.dv8tion.jda.api.audio.AudioReceiveHandler; +import net.dv8tion.jda.api.audio.CombinedAudio; +import net.dv8tion.jda.api.audio.UserAudio; + +public class JdrBotARH implements AudioReceiveHandler { + String guild; + public JdrBotARH(String guild) { + this.guild = guild; + } + + @Override + public boolean canReceiveCombined() { + return true; + } + + @Override + public boolean canReceiveUser() { + return false; + } + + @Override + public void handleCombinedAudio(CombinedAudio arg0) { + if(Record.rbs.get(guild) != null) { + Record.rbs.get(guild).addBytes(arg0.getAudioData(1.0)); + } + } + + @Override + public void handleUserAudio(UserAudio arg0) { + + } + +} diff --git a/src/main/java/fr/Skydust/JdrBot/audio/handler/JdrBotASH.java b/src/main/java/fr/Skydust/JdrBot/audio/handler/JdrBotASH.java new file mode 100755 index 0000000..9b47e9d --- /dev/null +++ b/src/main/java/fr/Skydust/JdrBot/audio/handler/JdrBotASH.java @@ -0,0 +1,35 @@ +package fr.Skydust.JdrBot.audio.handler; + +import com.sedmelluq.discord.lavaplayer.player.AudioPlayer; +import com.sedmelluq.discord.lavaplayer.track.playback.AudioFrame; + +import net.dv8tion.jda.api.audio.AudioSendHandler; + +import java.nio.ByteBuffer; + +public class JdrBotASH implements AudioSendHandler { + + private final AudioPlayer audioPlayer; + private AudioFrame lastFrame; + + public JdrBotASH(AudioPlayer audioPlayer) { + this.audioPlayer = audioPlayer; + } + + @Override + public boolean canProvide() { + lastFrame = audioPlayer.provide(); + return lastFrame != null; + } + + @Override + public ByteBuffer provide20MsAudio() { + return ByteBuffer.wrap(lastFrame.getData()); + } + + @Override + public boolean isOpus() { + return true; + } + +} diff --git a/src/main/java/fr/Skydust/JdrBot/cmds/Aide.java b/src/main/java/fr/Skydust/JdrBot/cmds/Aide.java new file mode 100755 index 0000000..ba1c405 --- /dev/null +++ b/src/main/java/fr/Skydust/JdrBot/cmds/Aide.java @@ -0,0 +1,36 @@ +package fr.Skydust.JdrBot.cmds; + +import fr.Skydust.JdrBot.JdrBot; +import fr.Skydust.JdrBot.stock.Command; +import net.dv8tion.jda.api.EmbedBuilder; +import net.dv8tion.jda.api.MessageBuilder; +import net.dv8tion.jda.api.events.message.guild.GuildMessageReceivedEvent; + +import java.awt.*; +import java.time.LocalDateTime; +import java.time.format.DateTimeFormatter; + +public class Aide extends Command { + public Aide() { + SetName("aide"); + SetDesc("Pour avoir de l'aide !"); + } + + @Override + public void call(GuildMessageReceivedEvent e) { + StringBuilder sb = new StringBuilder(); + + for (int i = 0; i< JdrBot.commandList.size(); i++) + { + Command cmd = JdrBot.commandList.get(i); + sb.append("`"+cmd.cmdName+"` - *"+cmd.cmdDesc+"*"+ ((i != JdrBot.commandList.size()-1) ? "\n" : "")); + } + + e.getChannel().sendMessage(new MessageBuilder().setEmbed(new EmbedBuilder() + .setDescription(sb.toString()) + .setTitle("Aide", null) + .setFooter("Fait le " + LocalDateTime.now().format(DateTimeFormatter.ofPattern("dd/MM/yyyy 'a' HH:mm:ss")), e.getJDA().getSelfUser().getAvatarUrl()) + .setColor(Color.red) + .build()).build()).queue(); + } +} diff --git a/src/main/java/fr/Skydust/JdrBot/cmds/Emote.java b/src/main/java/fr/Skydust/JdrBot/cmds/Emote.java new file mode 100755 index 0000000..86b58e8 --- /dev/null +++ b/src/main/java/fr/Skydust/JdrBot/cmds/Emote.java @@ -0,0 +1,60 @@ +package fr.Skydust.JdrBot.cmds; + +import java.util.Arrays; + +import fr.Skydust.JdrBot.stock.Command; +import net.dv8tion.jda.api.events.message.guild.GuildMessageReceivedEvent; + +public class Emote extends Command { + public Emote() { + SetName("emote"); + SetDesc("Donne les informations techniques d'une emote"); + } + + @Override + public void call(GuildMessageReceivedEvent e) { + String[] args = Arrays.copyOfRange(e.getMessage().getContentRaw().split(" "), 1, e.getMessage().getContentRaw().split(" ").length); + + String str = (String)args[0]; + if(str.matches("<:.*:\\d+>")) + { + String id = str.replaceAll("<:.*:(\\d+)>", "$1"); + net.dv8tion.jda.api.entities.Emote emote = e.getJDA().getEmoteById(id); + if(emote==null) + { + e.getChannel().sendMessage("Unknown emote:\n" + +"ID: **"+id+"**\n" + +"Guild: Unknown\n" + +"URL: https://discordcdn.com/emojis/"+id+".png").queue(); + return; + } + e.getChannel().sendMessage("Emote **"+emote.getName()+"**:\n"+"ID: **"+emote.getId()+"**\n"+"Guild: "+(emote.getGuild()==null ? "Unknown" : "**"+emote.getGuild().getName()+"**")+"\n"+"URL: "+emote.getImageUrl()); + return; + } + if(str.codePoints().count()>10) + { + e.getChannel().sendMessage("Invalid emote, or input is too long").queue();; + return; + } + StringBuilder builder = new StringBuilder("Emoji/Character info:"); + str.codePoints().forEachOrdered(code -> { + char[] chars = Character.toChars(code); + String hex = Integer.toHexString(code).toUpperCase(); + while(hex.length()<4) + hex = "0"+hex; + builder.append("\n`\\u").append(hex).append("` "); + if(chars.length>1) + { + String hex0 = Integer.toHexString(chars[0]).toUpperCase(); + String hex1 = Integer.toHexString(chars[1]).toUpperCase(); + while(hex0.length()<4) + hex0 = "0"+hex0; + while(hex1.length()<4) + hex1 = "0"+hex1; + builder.append("[`\\u").append(hex0).append("\\u").append(hex1).append("`] "); + } + builder.append(String.valueOf(chars)).append(" _").append(Character.getName(code)).append("_"); + }); + e.getChannel().sendMessage(builder.toString()).queue();; + } +} diff --git a/src/main/java/fr/Skydust/JdrBot/cmds/Etat.java b/src/main/java/fr/Skydust/JdrBot/cmds/Etat.java new file mode 100755 index 0000000..9805907 --- /dev/null +++ b/src/main/java/fr/Skydust/JdrBot/cmds/Etat.java @@ -0,0 +1,69 @@ +package fr.Skydust.JdrBot.cmds; + +import java.awt.Color; +import java.lang.management.ManagementFactory; +import java.text.DecimalFormat; +import java.time.Duration; +import java.time.LocalDateTime; +import java.time.format.DateTimeFormatter; + +import com.sedmelluq.discord.lavaplayer.tools.PlayerLibrary; +import fr.Skydust.JdrBot.JdrBot; +import fr.Skydust.JdrBot.stock.Command; +import fr.Skydust.JdrBot.utils.Utils; +import net.dv8tion.jda.api.EmbedBuilder; +import net.dv8tion.jda.api.JDAInfo; +import net.dv8tion.jda.api.MessageBuilder; +import net.dv8tion.jda.api.events.message.guild.GuildMessageReceivedEvent; + +public class Etat extends Command { + public Etat() { + SetName("status"); + SetDesc("Donne le status du bot"); + } + + @Override + public void call(GuildMessageReceivedEvent e) { + + //StringBuilder sb = new StringBuilder(); + //SystemInfo si = new SystemInfo(); + //HardwareAbstractionLayer hal = si.getHardware(); + Runtime rt = Runtime.getRuntime(); + DecimalFormat df = new DecimalFormat("#.##"); + /*sb.append("------------------------------------\n"); + sb.append("**CPU** (Current/Average): "+ + "\n**Threads**: "++ "\n"); + sb.append("**Memory** (Used/Total):" + + "\n Principal: "+(df.format((hal.getMemory().getTotal()-hal.getMemory().getAvailable())/1024/1024))+"Mb/"+df.format(hal.getMemory().getTotal()/1024/1024)+"Mb" + + "\n JVM: "+((rt.totalMemory()-rt.freeMemory())/1024/1024)+"Mb/"+(rt.totalMemory()/1024/1024)+"Mb" + + "\n Swap: "+df.format(hal.getMemory().getSwapUsed()/1024/1024)+"Mb/"+df.format(hal.getMemory().getSwapTotal()/1024/1024)+"Mb\n" + + "\n"); + sb.append("**Servers**: "+e.getJDA().getGuilds().size()+"\n"); + sb.append("**Servers w/ Music Started**: "+PlayMusic.musicManagers.size()+"\n"); + sb.append("**Servers w/ Recording Started**: "+Record.rbs.size()+"\n");*/ + LocalDateTime currentDate = LocalDateTime.now(); + Duration difference = Duration.between(JdrBot.basedate, currentDate); + //sb.append("**Uptime**: "+Utils.formatDuration(difference)); + + + e.getChannel().sendMessage(new MessageBuilder().setEmbed(new EmbedBuilder() + .setAuthor("Etat de "+ e.getGuild().getSelfMember().getEffectiveName()) + .addBlankField(false) + //.addField("CPU","-----", false) + //.addField("Load (Current/Average)",df.format(hal.getProcessor().getSystemCpuLoad()*100)+"%/"+df.format(hal.getProcessor().getSystemLoadAverage()*100)+"%",false) + //.addField("CPU Temperature", String.format("%.1f°C", hal.getSensors().getCpuTemperature()), true) + //.addField("Fan Speed", Arrays.toString(hal.getSensors().getFanSpeeds()), true) + .addField("Threads", ManagementFactory.getThreadMXBean().getThreadCount()+"", true) + .addBlankField(false) + .addField("Memory (Used/Total)", "-----",false) + //.addField("Principal",(df.format((hal.getMemory().getTotal()-hal.getMemory().getAvailable())/1024/1024))+"Mb/"+df.format(hal.getMemory().getTotal()/1024/1024)+"Mb", true) + .addField("JVM",((rt.totalMemory()-rt.freeMemory())/1024/1024)+"Mb/"+(rt.totalMemory()/1024/1024)+"Mb", true) + //.addField("Swap",df.format(hal.getMemory().getSwapUsed()/1024/1024)+"Mb/"+df.format(hal.getMemory().getSwapTotal()/1024/1024)+"Mb", true) + .addBlankField(false) + .addField("Servers",e.getJDA().getGuilds().size()+"",true) + .addField("Versions", "JdrBot: "+JdrBot.Version+ " - JDA: " + JDAInfo.VERSION + " - Lavaplayer: "+ PlayerLibrary.VERSION, true) + .addField("Uptime", Utils.formatDuration(difference), true) + .setFooter("*Fait le "+currentDate.format(DateTimeFormatter.ofPattern("dd/MM/yyyy à HH:mm:ss"))+"*", e.getJDA().getSelfUser().getAvatarUrl()) + .setColor(Color.BLUE) + .build()).build()).queue(); + } +} diff --git a/src/main/java/fr/Skydust/JdrBot/cmds/LastTimeOnline.java b/src/main/java/fr/Skydust/JdrBot/cmds/LastTimeOnline.java new file mode 100755 index 0000000..3cbebb6 --- /dev/null +++ b/src/main/java/fr/Skydust/JdrBot/cmds/LastTimeOnline.java @@ -0,0 +1,56 @@ +package fr.Skydust.JdrBot.cmds; + +import java.time.Duration; +import java.time.LocalDateTime; +import java.util.HashMap; + +import fr.Skydust.JdrBot.stock.Command; +import fr.Skydust.JdrBot.utils.Utils; +import net.dv8tion.jda.api.OnlineStatus; +import net.dv8tion.jda.api.entities.User; +import net.dv8tion.jda.api.events.message.guild.GuildMessageReceivedEvent; +import net.dv8tion.jda.api.events.user.update.UserUpdateOnlineStatusEvent; + +public class LastTimeOnline extends Command { + static HashMap AllUsers = new HashMap(); + + public LastTimeOnline() { + SetName("lasttimeonline|lto"); + SetDesc("Dis depuis combien de temps un utilisateur est en ligne/hors-ligne"); + } + + @Override + public void call(GuildMessageReceivedEvent e) { + if(e.getMessage().getMentionedUsers().size() < 1) { + e.getChannel().sendMessage("Vous n'avez pas mentionne d'utilisateur !").queue(); + return; + } + User u = e.getMessage().getMentionedUsers().get(0); + if(AllUsers.get(u.getId()) == null) { + e.getChannel().sendMessage(u.getAsMention()+" n'a pas change d'etat entre le demarrage du bot et maintenant").queue(); + return; + } + OnlineStatus status = e.getGuild().getMember(u).getOnlineStatus(); + LocalDateTime UserDate = AllUsers.get(e.getMessage().getMentionedUsers().get(0).getId()); + StringBuilder sb = new StringBuilder(); + if(status.equals(OnlineStatus.INVISIBLE) || status.equals(OnlineStatus.OFFLINE)) { + sb.append(u.getAsMention()+" est en hors-ligne depuis "); + } else { + sb.append(u.getAsMention()+" est en ligne depuis "); + } + sb.append(Utils.formatDurationSmooth(Duration.between(UserDate, LocalDateTime.now()))); + e.getChannel().sendMessage(sb.toString()).queue(); + } + + /** Called from the main Listener */ + public static void onUserUpdateOnlineStatus(UserUpdateOnlineStatusEvent e) { + if(e.getOldOnlineStatus().equals(OnlineStatus.OFFLINE)) { + //Si il est en ligne + AllUsers.put(e.getUser().getId(), LocalDateTime.now()); + } else if(!e.getOldOnlineStatus().equals(OnlineStatus.ONLINE) && !e.getOldOnlineStatus().equals(OnlineStatus.DO_NOT_DISTURB) && !e.getOldOnlineStatus().equals(OnlineStatus.IDLE)) { + //Si il est hors-ligne + AllUsers.put(e.getUser().getId(), LocalDateTime.now()); + } + } + +} diff --git a/src/main/java/fr/Skydust/JdrBot/cmds/Roll.java b/src/main/java/fr/Skydust/JdrBot/cmds/Roll.java new file mode 100755 index 0000000..10c2fa2 --- /dev/null +++ b/src/main/java/fr/Skydust/JdrBot/cmds/Roll.java @@ -0,0 +1,79 @@ +package fr.Skydust.JdrBot.cmds; + +import java.util.*; + +import fr.Skydust.JdrBot.stock.Command; +import fr.Skydust.JdrBot.utils.Utils; +import net.dv8tion.jda.api.events.message.guild.GuildMessageReceivedEvent; + +public class Roll extends Command { + static Random r = new Random(); + + public Roll() { + SetName("r|roll"); + SetDesc("Lance un dé (USAGE:roll [NombreDés]d[NombreFaces] OU roll [NombreFaces]"); + } + + public void call(GuildMessageReceivedEvent e) { + if (e.getMessage().getContentRaw().split(" ").length != 1) + { + String[] args = e.getMessage().getContentRaw().split(" "); + + if (Utils.IsInt(args[1])) + { + e.getChannel().sendMessage(e.getMember().getAsMention() + " rolled **" + (1 + r.nextInt((Integer.parseInt(args[1])+1) - 1)) + "**").queue(); + } else if (args[1].contains("d")) { + if (Utils.IsInt(args[1].split("d")[0]) && Utils.IsInt(args[1].split("d")[1])) + { + int number = Integer.parseInt(args[1].split("d")[0]); + int number1 = Integer.parseInt(args[1].split("d")[1]); + if (number <= 100) + { + if (number1 <= 1000) + { + if (number1 != 1) + { + String finale = "Les nombres sortis sont les suivants : "; + + int finalcount = 0; + + //List list = new ArrayList(); + for (int i = 0; i < number; i++) + { + int CurrentNumber = (1 + r.nextInt((number1+1) - 1)); + //list.add(CurrentNumber); + finalcount += CurrentNumber; + + if(i == number-1) { + finale = finale + "**" + CurrentNumber + "**"; + } else { + finale = finale + "**" + CurrentNumber + "**, "; + } + } + + //Ranger par ordre decroissant + //Collections.sort(list, Comparator.reverseOrder()); + + e.getChannel().sendMessage(e.getMember().getAsMention() + " " + finale + " pour un total de " + finalcount).queue(); + } else { + e.getChannel().sendMessage("Comment as-tu obtenu un dé avec un seul côté !").queue(); + } + } + else + { + e.getChannel().sendMessage("Le nombre de faces doit être en dessous de 1000 !").queue(); + } + } + else + { + e.getChannel().sendMessage("Le nombre de dés doit être en dessous de 100 !").queue(); + } + } else { + e.getChannel().sendMessage("Il faut un nombre valide !").queue(); + } + } else { + e.getChannel().sendMessage("Il faut un nombre valide !").queue(); + } + } + } +} diff --git a/src/main/java/fr/Skydust/JdrBot/cmds/playmusic/FLoad.java b/src/main/java/fr/Skydust/JdrBot/cmds/playmusic/FLoad.java new file mode 100755 index 0000000..32f69a6 --- /dev/null +++ b/src/main/java/fr/Skydust/JdrBot/cmds/playmusic/FLoad.java @@ -0,0 +1,24 @@ +package fr.Skydust.JdrBot.cmds.playmusic; + +import fr.Skydust.JdrBot.stock.Command; +import net.dv8tion.jda.api.events.message.guild.GuildMessageReceivedEvent; +import org.apache.commons.lang3.StringUtils; + +import java.util.Arrays; + +public class FLoad extends Command { + public FLoad() { + SetName("fload"); + SetDesc("/!\\ Commande test /!\\ Permet de charger une musique de force"); + } + + @Override + public void call(GuildMessageReceivedEvent e) { + String args = StringUtils.join(Arrays.copyOfRange(e.getMessage().getContentRaw().split(" "), 1, e.getMessage().getContentRaw().split(" ").length)," "); + + e.getGuild().getAudioManager().openAudioConnection(e.getMember().getVoiceState().getChannel()); + //ytsearch:query + + PlayMusic.loadAndPlay(e.getChannel(), args, false, false); + } +} diff --git a/src/main/java/fr/Skydust/JdrBot/cmds/playmusic/FLoadLoop.java b/src/main/java/fr/Skydust/JdrBot/cmds/playmusic/FLoadLoop.java new file mode 100755 index 0000000..e37ec89 --- /dev/null +++ b/src/main/java/fr/Skydust/JdrBot/cmds/playmusic/FLoadLoop.java @@ -0,0 +1,26 @@ +package fr.Skydust.JdrBot.cmds.playmusic; + +import fr.Skydust.JdrBot.stock.Command; +import net.dv8tion.jda.api.events.message.guild.GuildMessageReceivedEvent; +import org.apache.commons.lang3.StringUtils; + +import java.util.Arrays; + +public class FLoadLoop extends Command { + public FLoadLoop() { + SetName("floadloop"); + SetDesc("/!\\ Commande test /!\\ Permet de charger une musique de force"); + } + + @Override + public void call(GuildMessageReceivedEvent e) { + String args = StringUtils.join(Arrays.copyOfRange(e.getMessage().getContentRaw().split(" "), 1, e.getMessage().getContentRaw().split(" ").length)," "); + + e.getGuild().getAudioManager().openAudioConnection(e.getMember().getVoiceState().getChannel()); + + if(!args.matches(".*(https?)://.*")) { + args = "ytsearch:"+args; + } + PlayMusic.loadAndPlay(e.getChannel(), StringUtils.join(args," "), true, false); + } +} \ No newline at end of file diff --git a/src/main/java/fr/Skydust/JdrBot/cmds/playmusic/PlayMusic.java b/src/main/java/fr/Skydust/JdrBot/cmds/playmusic/PlayMusic.java new file mode 100755 index 0000000..2b406bf --- /dev/null +++ b/src/main/java/fr/Skydust/JdrBot/cmds/playmusic/PlayMusic.java @@ -0,0 +1,146 @@ +package fr.Skydust.JdrBot.cmds.playmusic; + +import java.util.HashMap; +import java.util.Map; + +import fr.Skydust.JdrBot.jukebox.JukeboxGUISystem; +import fr.Skydust.JdrBot.cmds.record.Record; +import fr.Skydust.JdrBot.stock.Command; +import net.dv8tion.jda.api.Permission; +import net.dv8tion.jda.api.entities.Guild; +import net.dv8tion.jda.api.entities.TextChannel; +import net.dv8tion.jda.api.events.guild.voice.GuildVoiceLeaveEvent; +import net.dv8tion.jda.api.events.guild.voice.GuildVoiceMoveEvent; +import net.dv8tion.jda.api.events.message.guild.GuildMessageReceivedEvent; + +import com.sedmelluq.discord.lavaplayer.player.AudioLoadResultHandler; +import com.sedmelluq.discord.lavaplayer.player.AudioPlayerManager; +import com.sedmelluq.discord.lavaplayer.player.DefaultAudioPlayerManager; +import com.sedmelluq.discord.lavaplayer.source.AudioSourceManagers; +import com.sedmelluq.discord.lavaplayer.tools.FriendlyException; +import com.sedmelluq.discord.lavaplayer.track.AudioPlaylist; +import com.sedmelluq.discord.lavaplayer.track.AudioTrack; + +import fr.Skydust.JdrBot.audio.GuildMusicManager; +import fr.Skydust.JdrBot.jukebox.JukeboxGUI; + +public class PlayMusic extends Command { + private static final AudioPlayerManager playerManager = new DefaultAudioPlayerManager(); + static Map musicManagers; + + public PlayMusic() { + musicManagers = new HashMap<>(); + AudioSourceManagers.registerRemoteSources(playerManager); + AudioSourceManagers.registerLocalSource(playerManager); + + SetName("playmusic|pm"); + SetDesc("Demarre le jukebox"); + } + + @Override + public void call(GuildMessageReceivedEvent e) { + if(!e.getMember().hasPermission(Permission.ADMINISTRATOR)) { + return; + } + + if(JukeboxGUISystem.getGuildsJukebox(e.getGuild()) != null) { + e.getChannel().sendMessage("/!\\ Le lecteur audio est deja present ici ! Pour l'arreter, tapez \"!stopmusic\" !").queue(); + return; + } + + String[] args = e.getMessage().getContentRaw().split(" "); + if (args.length != 1) + { + JukeboxGUISystem.createJukebox(e.getChannel(), args[1]); + } else { + JukeboxGUISystem.createJukebox(e.getChannel()); + } + + } + + public static void onGuildVoiceLeave(GuildVoiceLeaveEvent e) { + if(e.getGuild().getAudioManager().isConnected() && e.getChannelLeft().getName().equals(e.getGuild().getAudioManager().getConnectedChannel().getName()) && e.getChannelLeft().getMembers().size() == 1) { + JukeboxGUI gui = JukeboxGUISystem.getGuildsJukebox(e.getGuild()); + if(gui != null) { + e.getGuild().getTextChannelById(gui.TextChannelID).deleteMessageById(gui.MessageID) + .queue(msg -> { + JukeboxGUISystem.setGuildsJukebox(e.getGuild(), null); + }); + } + getGuildAudioPlayer(e.getGuild()).scheduler.stop(); + if(Record.rbs.get(e.getGuild().getId()) == null) { + e.getGuild().getAudioManager().closeAudioConnection(); + } + } + } + + public static void onGuildVoiceMove(GuildVoiceMoveEvent e) { + if(e.getGuild().getAudioManager().isConnected() && e.getChannelLeft().getName().equals(e.getGuild().getAudioManager().getConnectedChannel().getName()) && e.getChannelLeft().getMembers().size() == 1) { + JukeboxGUI gui = JukeboxGUISystem.getGuildsJukebox(e.getGuild()); + if(gui != null) { + e.getGuild().getTextChannelById(gui.TextChannelID).deleteMessageById(gui.MessageID) + .queue(msg -> { + JukeboxGUISystem.setGuildsJukebox(e.getGuild(), null); + }); + } + getGuildAudioPlayer(e.getGuild()).scheduler.stop(); + //if(Record.rbs.get(e.getGuild().getId()) == null) { + e.getGuild().getAudioManager().closeAudioConnection(); + //} + } + } + + public static void loadAndPlay(final TextChannel channel, final String trackUrl, boolean loop, boolean nomsg) { + System.out.println(trackUrl); + GuildMusicManager musicManager = getGuildAudioPlayer(channel.getGuild()); + playerManager.loadItemOrdered(musicManager, trackUrl, new AudioLoadResultHandler() { + @Override + public void trackLoaded(AudioTrack track) { + if(!nomsg) { + channel.sendMessage("**Now Playing**: "+track.getInfo().title).queue(); + } + System.out.println("Launching track pre:"+track.getInfo().title); + musicManager.scheduler.play(track, loop); + } + + @Override + public void playlistLoaded(AudioPlaylist playlist) { + AudioTrack firstTrack = playlist.getSelectedTrack(); + + if (firstTrack == null) { + firstTrack = playlist.getTracks().get(0); + } + + if(!nomsg) { + channel.sendMessage("**Now Playing**: "+firstTrack.getInfo().title).queue(); + } + System.out.println("Launching track pre:"+firstTrack.getInfo().title); + musicManager.scheduler.play(firstTrack, loop); + } + + @Override + public void noMatches() { + } + + @Override + public void loadFailed(FriendlyException exception) { + channel.sendMessage(exception.getMessage()).queue(); + } + }); + } + + public static synchronized GuildMusicManager getGuildAudioPlayer(Guild guild) { + long guildId = Long.parseLong(guild.getId()); + GuildMusicManager musicManager = musicManagers.get(guildId); + + if (musicManager == null) { + musicManager = new GuildMusicManager(playerManager, guild.getAudioManager()); + musicManagers.put(guildId, musicManager); + } + + guild.getAudioManager().setSendingHandler(musicManager.getSendHandler()); + + return musicManager; + } + +} diff --git a/src/main/java/fr/Skydust/JdrBot/cmds/playmusic/StopMusic.java b/src/main/java/fr/Skydust/JdrBot/cmds/playmusic/StopMusic.java new file mode 100755 index 0000000..f139f0e --- /dev/null +++ b/src/main/java/fr/Skydust/JdrBot/cmds/playmusic/StopMusic.java @@ -0,0 +1,35 @@ +package fr.Skydust.JdrBot.cmds.playmusic; + +import fr.Skydust.JdrBot.cmds.record.Record; +import fr.Skydust.JdrBot.jukebox.JukeboxGUI; +import fr.Skydust.JdrBot.jukebox.JukeboxGUISystem; +import fr.Skydust.JdrBot.stock.Command; +import net.dv8tion.jda.api.Permission; +import net.dv8tion.jda.api.events.message.guild.GuildMessageReceivedEvent; + +public class StopMusic extends Command { + public StopMusic() { + SetName("stopmusic|sm"); + SetDesc("Arrete le jukebox et supprime son message"); + } + + @Override + public void call(GuildMessageReceivedEvent e) { + if(!e.getGuild().getAudioManager().isConnected() && e.getMember().hasPermission(Permission.ADMINISTRATOR)) { + return; + } + + JukeboxGUI gui = JukeboxGUISystem.getGuildsJukebox(e.getGuild()); + + if(gui != null) { + e.getGuild().getTextChannelById(gui.TextChannelID).deleteMessageById(gui.MessageID) + .queue(msg -> { + JukeboxGUISystem.setGuildsJukebox(e.getGuild(), null); + }); + } + PlayMusic.getGuildAudioPlayer(e.getGuild()).scheduler.stop(); + if(Record.rbs.get(e.getGuild().getId()) == null) { + e.getGuild().getAudioManager().closeAudioConnection(); + } + } +} diff --git a/src/main/java/fr/Skydust/JdrBot/cmds/record/Record.java b/src/main/java/fr/Skydust/JdrBot/cmds/record/Record.java new file mode 100755 index 0000000..b19cfa0 --- /dev/null +++ b/src/main/java/fr/Skydust/JdrBot/cmds/record/Record.java @@ -0,0 +1,38 @@ +package fr.Skydust.JdrBot.cmds.record; + +import java.util.Date; +import java.util.HashMap; + +import fr.Skydust.JdrBot.audio.handler.JdrBotARH; +import fr.Skydust.JdrBot.stock.RecordState; +import fr.Skydust.JdrBot.stock.Command; +import net.dv8tion.jda.api.events.message.guild.GuildMessageReceivedEvent; + +public class Record extends Command { + public static HashMap rbs = new HashMap(); + + public Record() { + SetName("record"); + SetDesc("Enregistre le chat vocal"); + } + + public void call(GuildMessageReceivedEvent e) + { + if(rbs.get(e.getGuild().getId()) == null) { + rbs.put(e.getGuild().getId(), new RecordState()); + } + + if(e.getGuild().getMember(e.getAuthor()).getVoiceState().getChannel() != null && !rbs.get(e.getGuild().getId()).isRecording() && !rbs.get(e.getGuild().getId()).isProcessing()) { + if(rbs.get(e.getGuild().getId()).isProcessing()) { + e.getChannel().sendMessage(e.getAuthor().getAsMention()+" Un enregistrement est en train d'etre sauvegarde envoye"); + return; + } + e.getChannel().sendMessage(e.getAuthor().getAsMention()+" Lancement du record").queue(); + System.out.println("["+new Date().toString()+"] Le serveur ID "+e.getGuild().getId()+"("+e.getGuild().getName()+") vient de lancer un enregistrement"); + e.getGuild().getAudioManager().openAudioConnection(e.getGuild().getMember(e.getAuthor()).getVoiceState().getChannel()); + rbs.get(e.getGuild().getId()).setRecording(true);e.getGuild().getAudioManager().setReceivingHandler(new JdrBotARH(e.getGuild().getId())); + } else { + e.getChannel().sendMessage(e.getAuthor().getAsMention()+" n'est pas dans la channel vocal et ou a deja demarre un enregistrement!"); + } + } +} \ No newline at end of file diff --git a/src/main/java/fr/Skydust/JdrBot/cmds/record/StopRecord.java b/src/main/java/fr/Skydust/JdrBot/cmds/record/StopRecord.java new file mode 100755 index 0000000..47e466c --- /dev/null +++ b/src/main/java/fr/Skydust/JdrBot/cmds/record/StopRecord.java @@ -0,0 +1,21 @@ +package fr.Skydust.JdrBot.cmds.record; + +import fr.Skydust.JdrBot.stock.Command; +import net.dv8tion.jda.api.events.message.guild.GuildMessageReceivedEvent; + +public class StopRecord extends Command { + public StopRecord() { + SetName("stoprecord|sr"); + SetDesc("Arrete l'enregistrement"); + } + + @Override + public void call(GuildMessageReceivedEvent e) { + if(Record.rbs.get(e.getGuild().getId()) != null && Record.rbs.get(e.getGuild().getId()).isRecording()) { + Record.rbs.get(e.getGuild().getId()).endRecord(e.getGuild(), e.getChannel()); + Record.rbs.put(e.getGuild().getId(), null); + } else { + e.getChannel().sendMessage("PERSONNE N'ENREGISTRE <3").queue(); + } + } +} diff --git a/src/main/java/fr/Skydust/JdrBot/jukebox/JukeboxGUI.java b/src/main/java/fr/Skydust/JdrBot/jukebox/JukeboxGUI.java new file mode 100755 index 0000000..1e66ed8 --- /dev/null +++ b/src/main/java/fr/Skydust/JdrBot/jukebox/JukeboxGUI.java @@ -0,0 +1,14 @@ +package fr.Skydust.JdrBot.jukebox; + +public class JukeboxGUI { + public String MessageID = ""; + public int prevSong = -1; + public String TextChannelID = ""; + public String Menu = "mainMenu"; + + public JukeboxGUI(String textChannelID, String MessageID, String Menu) { + this.MessageID = MessageID; + this.TextChannelID = textChannelID; + this.Menu = Menu; + } +} diff --git a/src/main/java/fr/Skydust/JdrBot/jukebox/JukeboxGUISystem.java b/src/main/java/fr/Skydust/JdrBot/jukebox/JukeboxGUISystem.java new file mode 100755 index 0000000..1dd0a47 --- /dev/null +++ b/src/main/java/fr/Skydust/JdrBot/jukebox/JukeboxGUISystem.java @@ -0,0 +1,175 @@ +package fr.Skydust.JdrBot.jukebox; + +import fr.Skydust.JdrBot.cmds.playmusic.PlayMusic; +import net.dv8tion.jda.api.EmbedBuilder; +import net.dv8tion.jda.api.MessageBuilder; +import net.dv8tion.jda.api.entities.Guild; +import net.dv8tion.jda.api.entities.TextChannel; +import net.dv8tion.jda.api.events.message.react.MessageReactionAddEvent; + +import java.awt.*; +import java.io.File; +import java.util.HashMap; + +public class JukeboxGUISystem { + /*0to10*/ + public static final String[] AllChars = {"\u0030\u20E3","\u0031\u20E3","\u0032\u20E3","\u0033\u20E3","\u0034\u20E3","\u0035\u20E3","\u0036\u20E3","\u0037\u20E3","\u0038\u20E3","\u0039\u20E3","\uD83D\uDD1F", + /*Alphabet*/ "\uD83C\uDDE6","\uD83C\uDDE7","\uD83C\uDDE8","\uD83C\uDDE9","\uD83C\uDDEA","\uD83C\uDDEB","\uD83C\uDDEC","\uD83C\uDDED","\uD83C\uDDEE","\uD83C\uDDEF","\uD83C\uDDF0","\uD83C\uDDF1","\uD83C\uDDF2","\uD83C\uDDF3","\uD83C\uDDF4","\uD83C\uDDF5","\uD83C\uDDF6","\uD83C\uDDF7","\uD83C\uDDF8","\uD83C\uDDF9","\uD83C\uDDFA","\uD83C\uDDFB","\uD83C\uDDFC","\uD83C\uDDFD","\uD83C\uDDFE","\uD83C\uDDFF"}; + + public static final String UP = "\uD83D\uDD3C"; + public static final String DOWN = "\uD83D\uDD3D"; + public static final String SELECT = "\u2705"; + public static final String CANCEL = "\u274E"; + + private static String songsLocation = "Songs"; + + public static HashMap JukeboxGUIs = new HashMap(); + + public static void createJukebox(TextChannel tc) { + createJukebox(tc, "mainMenu"); + } + + public static void createJukebox(TextChannel tc, String menu) { + File path = new File(songsLocation + ((menu.equals("mainMenu") ? "" : "/"+menu))); + + if(!path.exists()) + return; + + String[] filePaths = path.list(); + + StringBuilder str = new StringBuilder(); + int i = 0; + for (String s : filePaths) { + str.append(AllChars[i]+":"+s+"\n"); + i++; + } + + tc.sendMessage(new MessageBuilder().append("Music Player 3000").setEmbed(new EmbedBuilder().setThumbnail("https://cdn4.iconfinder.com/data/icons/miu/24/device-volume-loudspeaker-speaker-up-glyph-128.png").setTitle("Choisi un jdr:",null).setColor(Color.green).setDescription("\n"+str.toString()).build()).build()).queue(msg -> { + for(int i2=0;i2 { + StringBuilder sb = new StringBuilder(); + for (String s : msg.getEmbeds().get(0).getDescription().split("\n")) { + if (s.contains(AllChars[i2])) { + sb.append(s.replaceAll(AllChars[i2] + ":", "")); + } + } + + + if (cm.Menu.equals("mainMenu")) { + String[] filePaths = new File("Songs/" + sb.toString()).list(); + + // Si "i2", qui est le nombre du choix que tu viens de cliquer, est au dessus du nombre d'options du menu >> Annuler + // OU + // Si il essaye de mettre un menu avec + de 20 reactions >> Annuler + + if (i2 > new File("Songs/").list().length || filePaths.length > 20) { + return; + } + + StringBuilder str = new StringBuilder(); + int i3 = 0; + for (String s : filePaths) { + str.append(AllChars[i3] + ":" + s.replace(".mp3", "") + "\n"); + i3++; + } + + str.append(AllChars[i3] + ":Retour"); + + msg.editMessage(new MessageBuilder().append("Music Player 3000").setEmbed(new EmbedBuilder().setThumbnail("https://cdn4.iconfinder.com/data/icons/miu/24/device-volume-loudspeaker-speaker-up-glyph-128.png").setTitle("Choisi une musique:", null).setColor(Color.green).setDescription("\n" + str.toString()).build()).build()).queue(msg2 -> { + //msg2.clearReactions().queue(msg3 -> { + try { + for (int i4 = 0; i4 < filePaths.length + 1; i4++) { + msg2.addReaction(AllChars[i4]).queue(); + } + + cm.Menu = sb.toString(); + } catch (Exception e5) { + e5.printStackTrace(); + } + //}); + }); + } else { + if (sb.toString().equals("Retour") || sb.toString().equals("")) { + String[] filePaths = new File("Songs").list(); + + if (i2 > new File("Songs/" + cm.Menu + "/").list().length || filePaths.length > 20) { + return; + } + + StringBuilder str = new StringBuilder(); + int i9 = 0; + for (String s : filePaths) { + str.append(AllChars[i9] + ":" + s + "\n"); + i9++; + } + msg.editMessage(new MessageBuilder().append("Music Player 3000").setEmbed(new EmbedBuilder().setThumbnail("https://cdn4.iconfinder.com/data/icons/miu/24/device-volume-loudspeaker-speaker-up-glyph-128.png").setTitle("Choisi un jdr:", null).setColor(Color.green).setDescription("\n" + str.toString()).build()).build()).queue(msg1 -> { + for (int y = filePaths.length; y < msg1.getReactions().size(); y++) { + msg1.getReactions().get(y).removeReaction().queue(); + } + try { + for (int i8 = 0; i8 < filePaths.length; i8++) { + msg1.addReaction(AllChars[i8]).queue(); + } + JukeboxGUIs.get(e.getGuild().getId()).Menu = "mainMenu"; + + } catch (Exception e5) { + e5.printStackTrace(); + } + //}); + }); + return; + } + tc.getGuild().getAudioManager().openAudioConnection(tc.getGuild().getMember(e.getUser()).getVoiceState().getChannel()); + if (cm.prevSong == -1) { + msg.editMessage(new MessageBuilder().append("Music Player 3000").setEmbed(new EmbedBuilder().setThumbnail("https://cdn4.iconfinder.com/data/icons/miu/24/device-volume-loudspeaker-speaker-up-glyph-128.png").setTitle("Choisi une musique:", null).setColor(Color.green).setDescription(msg.getEmbeds().get(0).getDescription().replace(AllChars[i2], "\u25B6" + AllChars[i2])).build()).build()).queue(); + } else { + msg.editMessage(new MessageBuilder().append("Music Player 3000").setEmbed(new EmbedBuilder().setThumbnail("https://cdn4.iconfinder.com/data/icons/miu/24/device-volume-loudspeaker-speaker-up-glyph-128.png").setTitle("Choisi une musique:", null).setColor(Color.green).setDescription(msg.getEmbeds().get(0).getDescription().replace("\u25B6", "").replace(AllChars[i2], "\u25B6" + AllChars[i2])).build()).build()).queue(); + } + cm.prevSong = i2; + PlayMusic.loadAndPlay(tc, "Songs/" + cm.Menu + "/" + sb.toString() + ".mp3", true, true); + } + }); + } + } + } + + public static synchronized JukeboxGUI getGuildsJukebox(Guild guild) { + return JukeboxGUIs.get(guild.getId()); + } + + public static void setGuildsJukebox(Guild guild, JukeboxGUI gui) { + JukeboxGUIs.put(guild.getId(), gui); + } +} diff --git a/src/main/java/fr/Skydust/JdrBot/stock/Command.java b/src/main/java/fr/Skydust/JdrBot/stock/Command.java new file mode 100755 index 0000000..56f8b4b --- /dev/null +++ b/src/main/java/fr/Skydust/JdrBot/stock/Command.java @@ -0,0 +1,18 @@ +package fr.Skydust.JdrBot.stock; + +import net.dv8tion.jda.api.events.message.guild.GuildMessageReceivedEvent; + +public abstract class Command { + public String cmdName; + public String cmdDesc; + + public abstract void call(GuildMessageReceivedEvent e); + + public void SetName(String name) { + this.cmdName = name; + } + + public void SetDesc(String desc) { + this.cmdDesc = desc; + } +} diff --git a/src/main/java/fr/Skydust/JdrBot/stock/RecordState.java b/src/main/java/fr/Skydust/JdrBot/stock/RecordState.java new file mode 100755 index 0000000..ca0e261 --- /dev/null +++ b/src/main/java/fr/Skydust/JdrBot/stock/RecordState.java @@ -0,0 +1,154 @@ +package fr.Skydust.JdrBot.stock; + +import java.io.*; +import java.nio.ByteBuffer; +import java.nio.ByteOrder; +import java.util.ArrayList; +import java.util.Date; +import java.util.List; +import java.util.zip.ZipException; + +import fr.Skydust.JdrBot.jukebox.JukeboxGUISystem; +import fr.Skydust.JdrBot.utils.ByteArrayOutputStreamT; +import net.dv8tion.jda.api.entities.Guild; +import net.dv8tion.jda.api.entities.TextChannel; +import net.lingala.zip4j.ZipFile; +import net.lingala.zip4j.model.ZipParameters; +import net.lingala.zip4j.model.enums.CompressionLevel; +import net.lingala.zip4j.model.enums.CompressionMethod; +import org.apache.commons.codec.EncoderException; +import ws.schild.jave.AudioAttributes; +import ws.schild.jave.Encoder; +import ws.schild.jave.EncodingAttributes; +import ws.schild.jave.MultimediaObject; + +public class RecordState { + private boolean isRecording; + private final ByteArrayOutputStreamT bytes; + private boolean isProcessing; + + public RecordState() { + isRecording = false; + isProcessing = false; + bytes = new ByteArrayOutputStreamT(); + } + + public void setRecording(boolean Record) { + isRecording = Record; + } + + public boolean isRecording() { + return isRecording; + } + + public void setProcessing(boolean Process) { + isProcessing = Process; + } + + public boolean isProcessing() { + return isProcessing; + } + + public void addBytes(byte[] bytes) { + if(!isProcessing && isRecording) { + try { + this.bytes.write(bytes); + } catch (IOException e) { + e.printStackTrace(); + } + } + } + + public ByteArrayOutputStreamT getBytes() { + return bytes; + } + + public void endRecord(Guild g, TextChannel tc) { + setRecording(false); + setProcessing(true); + if(JukeboxGUISystem.getGuildsJukebox(g) == null) { + g.getAudioManager().closeAudioConnection(); + } + + System.out.println("["+new Date().toString()+"] Le serveur ID "+g.getId()+"("+g.getName()+") vient de terminer un enregistrement"); + new Thread(() -> { + try { + recordFinish(tc); + setProcessing(false); + } catch (Exception e1) { + e1.printStackTrace(); + tc.sendMessage("["+new Date().toString()+"] Une erreur est survenue pendant l'enregistrement sur le serveur ID "+g.getId()+"("+g.getName()+")").queue(); + try { + bytes.close(); + } catch (IOException e) { + e.printStackTrace(); + } + setProcessing(false); + } + }).start(); + } + + public void recordFinish(TextChannel tc) throws ZipException, IOException, IllegalArgumentException, EncoderException, ws.schild.jave.EncoderException { + //Bytes to Wav + + + FileOutputStream out = new FileOutputStream("test.pcm"); + out.write(bytes.toByteArray()); + out.close(); + + + String OriginalName = new Date().toString().replaceAll(":", "-"); + + File wavFile = new File(OriginalName+".wav"); + File mp3File = new File(OriginalName+".mp3"); + + //AudioSystem.write(ais, AudioFileFormat.Type.WAVE, wavFile); + //rawToWave(bytes.toByteArray(), wavFile); + + //bais.close(); + bytes.close(); + + //ais.close(); + + //Wav to MP3 + Encoder encoder = new Encoder(); + AudioAttributes audio = new AudioAttributes(); + audio.setCodec("libmp3lame"); + audio.setBitRate(128000); + audio.setChannels(2); + EncodingAttributes ea = new EncodingAttributes(); + ea.setAudioAttributes(audio); + ea.setFormat("mp3"); + + encoder.encode(new MultimediaObject(wavFile),mp3File,ea); + //wavFile.delete(); + + //MP3 to Zip + ZipParameters parameters = new ZipParameters(); + parameters.setCompressionMethod(CompressionMethod.DEFLATE); + parameters.setCompressionLevel(CompressionLevel.NORMAL); + ZipFile zipFile; + zipFile = new ZipFile(OriginalName+".zip"); + + //List filesToAdd = new ArrayList(); + //filesToAdd.add(mp3File); + + //zipFile.createSplitZipFile(filesToAdd, parameters, true, 8283750); + //mp3File.delete(); + + //Send Files through Discord + if(zipFile.getSplitZipFiles().size() > 1) { + tc.sendMessage("Envoi du fichier audio(Via plusieurs fichiers zip)...").queue(); + for(Object file : zipFile.getSplitZipFiles()) { + File currentFile = new File(file+""); + tc.sendFile(currentFile, "").queue(msg -> currentFile.delete()); + } + } else { + tc.sendMessage("Envoi du fichier audio(Via un fichier zip)...").queue(); + File currentFile = new File(zipFile.getSplitZipFiles().get(0)+""); + tc.sendFile(currentFile, currentFile.getName()).queue(msg -> currentFile.delete()); + } + } + + +} diff --git a/src/main/java/fr/Skydust/JdrBot/utils/ByteArrayOutputStreamT.java b/src/main/java/fr/Skydust/JdrBot/utils/ByteArrayOutputStreamT.java new file mode 100755 index 0000000..6cbf19a --- /dev/null +++ b/src/main/java/fr/Skydust/JdrBot/utils/ByteArrayOutputStreamT.java @@ -0,0 +1,10 @@ +package fr.Skydust.JdrBot.utils; + +import java.io.ByteArrayOutputStream; + +public class ByteArrayOutputStreamT extends ByteArrayOutputStream { + @Override + public byte toByteArray()[] { + return buf; + } +} diff --git a/src/main/java/fr/Skydust/JdrBot/utils/Utils.java b/src/main/java/fr/Skydust/JdrBot/utils/Utils.java new file mode 100755 index 0000000..c94806a --- /dev/null +++ b/src/main/java/fr/Skydust/JdrBot/utils/Utils.java @@ -0,0 +1,37 @@ +package fr.Skydust.JdrBot.utils; + +import java.time.Duration; + +public class Utils { + public static boolean IsInt(String info) { + try { + Integer.parseInt(info); + return true; + } catch(Exception e) { + return false; + } + } + public static String formatDuration(Duration duration) { + long seconds = duration.getSeconds(); + long absSeconds = Math.abs(seconds); + String positive = String.format( + "%d:%02d:%02d", + absSeconds / 3600, + (absSeconds % 3600) / 60, + absSeconds % 60); + return seconds < 0 ? "-" + positive : positive; + } + + public static String formatDurationSmooth(Duration duration) { + long absSeconds = Math.abs(duration.getSeconds()); + + if((absSeconds/3600) == 0) {//Hours + if(((absSeconds%3600)/60) == 0) + {//Minutes + return String.format("%d secondes", absSeconds % 60); + } + return String.format("%d minutes", (absSeconds % 3600) / 60); + } + return String.format("%d heures", (absSeconds /3600)); + } +} diff --git a/src/main/resources/META-INF/MANIFEST.MF b/src/main/resources/META-INF/MANIFEST.MF new file mode 100644 index 0000000..862686b --- /dev/null +++ b/src/main/resources/META-INF/MANIFEST.MF @@ -0,0 +1,3 @@ +Manifest-Version: 1.0 +Main-Class: fr.Skydust.JdrBot.JdrBot +