Merge branch 'develop' of https://github.com/bwmarrin/Discordgo into develop
This commit is contained in:
commit
40fce5bd1a
5 changed files with 231 additions and 2 deletions
|
@ -1,7 +1,8 @@
|
||||||
<img align="right" src="http://bwmarrin.github.io/discordgo/img/discordgo.png">
|
<img align="right" src="http://bwmarrin.github.io/discordgo/img/discordgo.png">
|
||||||
DiscordGo
|
DiscordGo
|
||||||
====
|
====
|
||||||
[](https://godoc.org/github.com/bwmarrin/discordgo) [](http://goreportcard.com/report/bwmarrin/discordgo) [](https://travis-ci.org/bwmarrin/discordgo) [][https://discord.gg/0f1SbxBZjYoCtNPP] [][https://discord.gg/0SBTUU1wZTWT6sqd]
|
[](https://godoc.org/github.com/bwmarrin/discordgo) [](http://goreportcard.com/report/bwmarrin/discordgo) [](https://travis-ci.org/bwmarrin/discordgo)
|
||||||
|
[](https://discord.gg/0f1SbxBZjYoCtNPP) [](https://discord.gg/0SBTUU1wZTWT6sqd)
|
||||||
|
|
||||||
DiscordGo is a [Go](https://golang.org/) package that provides low level
|
DiscordGo is a [Go](https://golang.org/) package that provides low level
|
||||||
bindings to the [Discord](https://discordapp.com/) chat client API. DiscordGo
|
bindings to the [Discord](https://discordapp.com/) chat client API. DiscordGo
|
||||||
|
@ -15,7 +16,7 @@ with additional voice helper functions and features.
|
||||||
tool that wraps `ffmpeg` to create opus encoded audio appropriate for use with
|
tool that wraps `ffmpeg` to create opus encoded audio appropriate for use with
|
||||||
Discord (and DiscordGo)
|
Discord (and DiscordGo)
|
||||||
|
|
||||||
Join [][https://discord.gg/0f1SbxBZjYoCtNPP]
|
Join [](https://discord.gg/0f1SbxBZjYoCtNPP)
|
||||||
Discord chat channel for support.
|
Discord chat channel for support.
|
||||||
|
|
||||||
## Getting Started
|
## Getting Started
|
||||||
|
|
41
examples/airhorn/README.md
Normal file
41
examples/airhorn/README.md
Normal file
|
@ -0,0 +1,41 @@
|
||||||
|
<img align="right" src="http://bwmarrin.github.io/discordgo/img/discordgo.png">
|
||||||
|
Airhorn Example
|
||||||
|
====
|
||||||
|
|
||||||
|
This example demonstrates how to utilize DiscordGo to listen to an !airhorn
|
||||||
|
command in a channel and play a sound to that users current voice channel.
|
||||||
|
|
||||||
|
### Build
|
||||||
|
|
||||||
|
This assumes you already have a working Go environment setup and that
|
||||||
|
DiscordGo is correctly installed on your system.
|
||||||
|
|
||||||
|
```sh
|
||||||
|
go install github.com/bwmarrin/discordgo/examples/airhorn
|
||||||
|
cd $GOPATH/bin
|
||||||
|
cp ../src/github.com/bwmarrin/discordgo/examples/airhorn/airhorn.dca .
|
||||||
|
```
|
||||||
|
|
||||||
|
### Usage
|
||||||
|
|
||||||
|
```
|
||||||
|
Usage of ./airhorn:
|
||||||
|
-t string
|
||||||
|
Account Token
|
||||||
|
```
|
||||||
|
|
||||||
|
The below example shows how to start the bot.
|
||||||
|
|
||||||
|
```sh
|
||||||
|
./airhorn -t <bot token>
|
||||||
|
```
|
||||||
|
|
||||||
|
### Creating sounds
|
||||||
|
|
||||||
|
Airhorn bot uses DCA files that are pre-computed files that are easy to send to Discord.
|
||||||
|
|
||||||
|
If you would like to create your own DCA files, please use [https://github.com/bwmarrin/dca/tree/master/cmd/dca](DCA).
|
||||||
|
|
||||||
|
```sh
|
||||||
|
./dca -i <input wav file> -raw > <output file>
|
||||||
|
```
|
BIN
examples/airhorn/airhorn.dca
Normal file
BIN
examples/airhorn/airhorn.dca
Normal file
Binary file not shown.
186
examples/airhorn/main.go
Normal file
186
examples/airhorn/main.go
Normal file
|
@ -0,0 +1,186 @@
|
||||||
|
package main
|
||||||
|
|
||||||
|
import (
|
||||||
|
"encoding/binary"
|
||||||
|
"flag"
|
||||||
|
"fmt"
|
||||||
|
"io"
|
||||||
|
"os"
|
||||||
|
"strings"
|
||||||
|
"time"
|
||||||
|
|
||||||
|
"github.com/bwmarrin/discordgo"
|
||||||
|
)
|
||||||
|
|
||||||
|
func init() {
|
||||||
|
flag.StringVar(&token, "t", "", "Account Token")
|
||||||
|
flag.Parse()
|
||||||
|
}
|
||||||
|
|
||||||
|
var token string
|
||||||
|
var buffer = make([][]byte, 0)
|
||||||
|
|
||||||
|
func main() {
|
||||||
|
if token == "" {
|
||||||
|
fmt.Println("No token provided. Please run: airhorn -t <bot token>")
|
||||||
|
return
|
||||||
|
}
|
||||||
|
|
||||||
|
// Load the sound file.
|
||||||
|
err := loadSound()
|
||||||
|
if err != nil {
|
||||||
|
fmt.Println("Error loading sound: ", err)
|
||||||
|
fmt.Println("Please copy $GOPATH/src/github.com/bwmarrin/examples/airhorn/airhorn.dca to this directory.")
|
||||||
|
return
|
||||||
|
}
|
||||||
|
|
||||||
|
// Create a new Discord session using the provided token.
|
||||||
|
dg, err := discordgo.New(token)
|
||||||
|
if err != nil {
|
||||||
|
fmt.Println("Error creating Discord session: ", err)
|
||||||
|
return
|
||||||
|
}
|
||||||
|
|
||||||
|
// Register ready as a callback for the ready events.
|
||||||
|
dg.AddHandler(ready)
|
||||||
|
|
||||||
|
// Register messageCreate as a callback for the messageCreate events.
|
||||||
|
dg.AddHandler(messageCreate)
|
||||||
|
|
||||||
|
// Register guildCreate as a callback for the guildCreate events.
|
||||||
|
dg.AddHandler(guildCreate)
|
||||||
|
|
||||||
|
// Open the websocket and begin listening.
|
||||||
|
err = dg.Open()
|
||||||
|
if err != nil {
|
||||||
|
fmt.Println("Error opening Discord session: ", err)
|
||||||
|
}
|
||||||
|
|
||||||
|
fmt.Println("Airhorn is now running. Press CTRL-C to exit.")
|
||||||
|
// Simple way to keep program running until CTRL-C is pressed.
|
||||||
|
<-make(chan struct{})
|
||||||
|
return
|
||||||
|
}
|
||||||
|
|
||||||
|
func ready(s *discordgo.Session, event *discordgo.Ready) {
|
||||||
|
// Set the playing status.
|
||||||
|
s.UpdateStatus(0, "!airhorn")
|
||||||
|
}
|
||||||
|
|
||||||
|
// This function will be called (due to AddHandler above) every time a new
|
||||||
|
// message is created on any channel that the autenticated bot has access to.
|
||||||
|
func messageCreate(s *discordgo.Session, m *discordgo.MessageCreate) {
|
||||||
|
if strings.HasPrefix(m.Content, "!airhorn") {
|
||||||
|
// Find the channel that the message came from.
|
||||||
|
c, err := s.State.Channel(m.ChannelID)
|
||||||
|
if err != nil {
|
||||||
|
// Could not find channel.
|
||||||
|
return
|
||||||
|
}
|
||||||
|
|
||||||
|
// Find the guild for that channel.
|
||||||
|
g, err := s.State.Guild(c.GuildID)
|
||||||
|
if err != nil {
|
||||||
|
// Could not find guild.
|
||||||
|
return
|
||||||
|
}
|
||||||
|
|
||||||
|
// Look for the message sender in that guilds current voice states.
|
||||||
|
for _, vs := range g.VoiceStates {
|
||||||
|
if vs.UserID == m.Author.ID {
|
||||||
|
err = playSound(s, g.ID, vs.ChannelID)
|
||||||
|
if err != nil {
|
||||||
|
fmt.Println("Error playing sound:", err)
|
||||||
|
}
|
||||||
|
|
||||||
|
return
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// This function will be called (due to AddHandler above) every time a new
|
||||||
|
// guild is joined.
|
||||||
|
func guildCreate(s *discordgo.Session, event *discordgo.GuildCreate) {
|
||||||
|
if event.Guild.Unavailable != nil {
|
||||||
|
return
|
||||||
|
}
|
||||||
|
|
||||||
|
for _, channel := range event.Guild.Channels {
|
||||||
|
if channel.ID == event.Guild.ID {
|
||||||
|
s.ChannelMessageSend(channel.ID, "Airhorn is ready! Type !airhorn while in a voice channel to play a sound.")
|
||||||
|
return
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// loadSound attempts to load an encoded sound file from disk.
|
||||||
|
func loadSound() error {
|
||||||
|
file, err := os.Open("airhorn.dca")
|
||||||
|
|
||||||
|
if err != nil {
|
||||||
|
fmt.Println("Error opening dca file :", err)
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
|
||||||
|
var opuslen int16
|
||||||
|
|
||||||
|
for {
|
||||||
|
// Read opus frame length from dca file.
|
||||||
|
err = binary.Read(file, binary.LittleEndian, &opuslen)
|
||||||
|
|
||||||
|
// If this is the end of the file, just return.
|
||||||
|
if err == io.EOF || err == io.ErrUnexpectedEOF {
|
||||||
|
return nil
|
||||||
|
}
|
||||||
|
|
||||||
|
if err != nil {
|
||||||
|
fmt.Println("Error reading from dca file :", err)
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
|
||||||
|
// Read encoded pcm from dca file.
|
||||||
|
InBuf := make([]byte, opuslen)
|
||||||
|
err = binary.Read(file, binary.LittleEndian, &InBuf)
|
||||||
|
|
||||||
|
// Should not be any end of file errors
|
||||||
|
if err != nil {
|
||||||
|
fmt.Println("Error reading from dca file :", err)
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
|
||||||
|
// Append encoded pcm data to the buffer.
|
||||||
|
buffer = append(buffer, InBuf)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// playSound plays the current buffer to the provided channel.
|
||||||
|
func playSound(s *discordgo.Session, guildID, channelID string) (err error) {
|
||||||
|
// Join the provided voice channel.
|
||||||
|
vc, err := s.ChannelVoiceJoin(guildID, channelID, false, false)
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
|
||||||
|
// Sleep for a specified amount of time before playing the sound
|
||||||
|
time.Sleep(250 * time.Millisecond)
|
||||||
|
|
||||||
|
// Start speaking.
|
||||||
|
vc.Speaking(true)
|
||||||
|
|
||||||
|
// Send the buffer data.
|
||||||
|
for _, buff := range buffer {
|
||||||
|
vc.OpusSend <- buff
|
||||||
|
}
|
||||||
|
|
||||||
|
// Stop speaking
|
||||||
|
vc.Speaking(false)
|
||||||
|
|
||||||
|
// Sleep for a specificed amount of time before ending.
|
||||||
|
time.Sleep(250 * time.Millisecond)
|
||||||
|
|
||||||
|
// Disconnect from the provided voice channel.
|
||||||
|
vc.Disconnect()
|
||||||
|
|
||||||
|
return nil
|
||||||
|
}
|
|
@ -26,6 +26,7 @@ func init() {
|
||||||
func main() {
|
func main() {
|
||||||
|
|
||||||
// Create a new Discord session using the provided login information.
|
// Create a new Discord session using the provided login information.
|
||||||
|
// Use discordgo.New(Token) to just use a token for login.
|
||||||
dg, err := discordgo.New(Email, Password, Token)
|
dg, err := discordgo.New(Email, Password, Token)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
fmt.Println("error creating Discord session,", err)
|
fmt.Println("error creating Discord session,", err)
|
||||||
|
|
Loading…
Reference in a new issue