all repos — disgord @ 6066ac97421f0b357b8b7348fc87e6d4b673442a

A simple Discord bot in Go.

src/music/audio.go (view raw)

 1package music
 2
 3import (
 4	"github.com/FoxeiZ/dca"
 5	"github.com/bwmarrin/discordgo"
 6)
 7
 8type Audio struct {
 9	session  *dca.EncodeSession
10	stream   *dca.StreamingSession
11	Done     chan error
12	onFinish func()
13	paused   bool
14}
15
16var audioEncodeOptions = &dca.EncodeOptions{
17	Channels:         2,
18	FrameRate:        48000,
19	FrameDuration:    20,
20	Bitrate:          96,
21	Application:      dca.AudioApplicationLowDelay,
22	CompressionLevel: 10,
23	PacketLoss:       1,
24	BufferedFrames:   100,
25	VBR:              true,
26	StartTime:        0,
27	VolumeFloat:      1,
28	RawOutput:        true,
29}
30
31func NewAudio(url string, vc *discordgo.VoiceConnection) (as *Audio, err error) {
32	as = &Audio{
33		session: nil,
34		stream:  nil,
35		paused:  false,
36		Done:    make(chan error),
37	}
38
39	as.session, err = dca.EncodeFile(url, audioEncodeOptions)
40	if err != nil {
41		return
42	}
43
44	as.stream = dca.NewStream(as.session, vc, as.Done)
45	return
46}
47
48func (a *Audio) Pause() {
49	if a.stream == nil || a.paused {
50		return
51	}
52
53	a.stream.SetPaused(true)
54	a.paused = true
55}
56
57func (a *Audio) Resume() {
58	if a.stream == nil || !a.paused {
59		return
60	}
61
62	a.stream.SetPaused(false)
63	a.paused = false
64}
65
66func (a *Audio) Stop() {
67	if a.stream == nil {
68		return
69	}
70
71	a.stream.FinishNow()
72	a.session.Stop()
73	a.session.Cleanup()
74	a.stream = nil
75	a.session = nil
76}
77
78func (a *Audio) Finished() (bool, error) {
79	return a.stream.Finished()
80}
81
82func (a *Audio) Monitor(onFinish func()) {
83	go func() {
84		for err := range a.Done {
85			if err != nil {
86				logger.Errorf("Playback error: %v", err)
87				break
88			}
89		}
90
91		a.Stop()
92
93		if onFinish != nil {
94			onFinish()
95		}
96	}()
97}