diff --git a/.github/workflows/cd.yml b/.github/workflows/cd.yml index 6c8088ca..964c8c12 100644 --- a/.github/workflows/cd.yml +++ b/.github/workflows/cd.yml @@ -20,7 +20,7 @@ jobs: go-version: '1.19.5' - run: echo "VERSION=$(echo ${{ github.event.release.tag_name }} | cut -c 2-)" >> $GITHUB_ENV - run: sudo apt-get update -q - - run: sudo apt-get install libopenal-dev xorg-dev libgl1-mesa-dev -y --allow-unauthenticated + - run: sudo apt-get install portaudio19-dev xorg-dev libgl1-mesa-dev -y --allow-unauthenticated - run: OS=Linux ARCH=x86_64 VERSION=$VERSION make tar - run: OS=Linux ARCH=x86_64 VERSION=$VERSION make deb - run: sha256sum Ludo-Linux-x86_64-${VERSION}.tar.gz > Ludo-Linux-x86_64-${VERSION}.tar.gz.sha256 @@ -53,7 +53,7 @@ jobs: - run: echo "deb [arch=armhf] http://ports.ubuntu.com/ubuntu-ports bionic-backports main restricted universe multiverse" | sudo tee -a /etc/apt/sources.list - run: sudo apt-key adv --keyserver hkp://keyserver.ubuntu.com:80 --recv-keys 6B05F25D762E3157 - run: sudo apt update -q - - run: sudo apt install -f libgl1-mesa-dev:amd64 libc6-dev:armhf gcc-arm-linux-gnueabihf libopenal-dev:armhf libgl1-mesa-dev:armhf libxcursor-dev:armhf libxrandr-dev:armhf libxinerama-dev:armhf libxi-dev:armhf -y --allow-unauthenticated + - run: sudo apt install -f libgl1-mesa-dev:amd64 libc6-dev:armhf gcc-arm-linux-gnueabihf portaudio19-dev:armhf libgl1-mesa-dev:armhf libxcursor-dev:armhf libxrandr-dev:armhf libxinerama-dev:armhf libxi-dev:armhf -y --allow-unauthenticated - run: export PKG_CONFIG_PATH=/usr/lib/arm-linux-gnueabihf/pkgconfig/ - run: GOOS=linux GOARCH=arm GOARM=7 CGO_ENABLED=1 CC=arm-linux-gnueabihf-gcc go build -v - run: OS=Linux ARCH=arm VERSION=$VERSION make tar @@ -80,7 +80,7 @@ jobs: - run: echo "/Users/runner/go/bin" >> $GITHUB_PATH - run: go install golang.org/x/lint/golint@latest - run: go install honnef.co/go/tools/cmd/staticcheck@latest - - run: brew install openal-soft + - run: brew install portaudio - run: echo ${{ secrets.OSXCERT }} | base64 --decode > dev.p12 - run: security create-keychain -p github build.keychain - run: security default-keychain -s build.keychain @@ -113,13 +113,20 @@ jobs: go-version: '1.19.5' - run: echo "VERSION=$(echo ${{ github.event.release.tag_name }} | cut -c 2-)" >> $GITHUB_ENV - run: choco install wget make hashdeep --ignore-checksums - - run: wget --no-check-certificate http://www.openal-soft.org/openal-binaries/openal-soft-1.21.0-bin.zip - run: wget https://github.com/electron/rcedit/releases/download/v1.1.1/rcedit-x64.exe - - run: 7z x openal-soft-1.21.0-bin.zip -o/c/ - - run: echo "CGO_CFLAGS=-I/c/openal-soft-1.21.0-bin/include/" >> $GITHUB_ENV - - run: echo "CGO_LDFLAGS=-L/c/openal-soft-1.21.0-bin/libs/Win64/" >> $GITHUB_ENV + - run: wget --no-check-certificate http://files.portaudio.com/archives/pa_stable_v190700_20210406.tgz + - run: tar -xf pa_stable_v190700_20210406.tgz -C/c/ + # Not sure if this work on windows; Build portaudio because it has no binary dists + - run: cmake -G "MinGW Makefiles" -S/c/portaudio/ -B/c/portaudio/ + - run: make -C/c/portaudio/ + - run: echo "CGO_CFLAGS=-I/c/portaudio/include/" >> $GITHUB_ENV + - run: echo "CGO_LDFLAGS=-L/c/portaudio/" >> $GITHUB_ENV + #- run: sh -c 'cd /c/portaudio/; ./configure; make' + #- run: echo "CGO_CFLAGS=-I/c/openal-soft-1.21.0-bin/include/" >> $GITHUB_ENV + #- run: echo "CGO_LDFLAGS=-L/c/openal-soft-1.21.0-bin/libs/Win64/" >> $GITHUB_ENV - run: cp /c/ProgramData/chocolatey/lib/mingw/tools/install/mingw64/x86_64-w64-mingw32/lib/libwinpthread* . - - run: cp /c/openal-soft-1.21.0-bin/bin/Win64/soft_oal.dll OpenAL32.dll + # I'm not sure about this... Digged from configure, Needs more tests + - run: cp /c/portaudio/libportaudio.dll libportaudio.dll - run: cp /c/Windows/System32/VCRUNTIME140.dll . - run: mkdir -p ./Ludo-Windows-x86_64-${VERSION}/ - run: cp *.dll ./Ludo-Windows-x86_64-${VERSION}/ diff --git a/.github/workflows/ci.yml b/.github/workflows/ci.yml index 1cbe3e09..c6eb1b15 100644 --- a/.github/workflows/ci.yml +++ b/.github/workflows/ci.yml @@ -24,7 +24,7 @@ jobs: - run: go install golang.org/x/lint/golint@latest - run: go install honnef.co/go/tools/cmd/staticcheck@latest - run: sudo apt-get update -q - - run: sudo apt-get install libopenal-dev xorg-dev libgl1-mesa-dev -y --allow-unauthenticated + - run: sudo apt-get install portaudio19-dev xorg-dev libgl1-mesa-dev -y --allow-unauthenticated - run: go get . - run: xvfb-run -a go test -v -race ./... - run: go vet ./... @@ -52,7 +52,7 @@ jobs: - run: echo "deb [arch=armhf] http://ports.ubuntu.com/ubuntu-ports bionic-backports main restricted universe multiverse" | sudo tee -a /etc/apt/sources.list - run: sudo apt-key adv --keyserver hkp://keyserver.ubuntu.com:80 --recv-keys 6B05F25D762E3157 - run: sudo apt update -q - - run: sudo apt install -f libgl1-mesa-dev:amd64 libc6-dev:armhf gcc-arm-linux-gnueabihf libopenal-dev:armhf libgl1-mesa-dev:armhf libxcursor-dev:armhf libxrandr-dev:armhf libxinerama-dev:armhf libxi-dev:armhf -y --allow-unauthenticated + - run: sudo apt install -f libgl1-mesa-dev:amd64 libc6-dev:armhf gcc-arm-linux-gnueabihf portaudio19-dev:armhf libgl1-mesa-dev:armhf libxcursor-dev:armhf libxrandr-dev:armhf libxinerama-dev:armhf libxi-dev:armhf -y --allow-unauthenticated - run: export PKG_CONFIG_PATH=/usr/lib/arm-linux-gnueabihf/pkgconfig/ - run: GOOS=linux GOARCH=arm GOARM=7 CGO_ENABLED=1 CC=arm-linux-gnueabihf-gcc go build -v @@ -68,7 +68,7 @@ jobs: - run: echo "/Users/runner/go/bin" >> $GITHUB_PATH - run: go install golang.org/x/lint/golint@latest - run: go install honnef.co/go/tools/cmd/staticcheck@latest - - run: brew install openal-soft + - run: brew install portaudio - run: go get . - run: go test -v -race ./... - run: go vet ./... @@ -89,10 +89,14 @@ jobs: - run: go install golang.org/x/lint/golint@latest - run: go install honnef.co/go/tools/cmd/staticcheck@latest - run: choco install wget --ignore-checksums - - run: wget --no-check-certificate http://www.openal-soft.org/openal-binaries/openal-soft-1.21.0-bin.zip - - run: 7z x openal-soft-1.21.0-bin.zip -o/c/ - - run: echo "CGO_CFLAGS=-I/c/openal-soft-1.21.0-bin/include/" >> $GITHUB_ENV - - run: echo "CGO_LDFLAGS=-L/c/openal-soft-1.21.0-bin/libs/Win64/" >> $GITHUB_ENV + - run: wget --no-check-certificate http://files.portaudio.com/archives/pa_stable_v190700_20210406.tgz + - run: tar -xf pa_stable_v190700_20210406.tgz -C/c/ + # Not sure if this work on windows; Build portaudio because it has no binary dists + - run: cmake -G "MinGW Makefiles" -S/c/portaudio/ -B/c/portaudio/ + - run: make -C/c/portaudio/ + #- run: sh -c 'cd /c/portaudio/; ./configure; make' + - run: echo "CGO_CFLAGS=-I/c/portaudio/include/" >> $GITHUB_ENV + - run: echo "CGO_LDFLAGS=-L/c/portaudio/" >> $GITHUB_ENV - run: go get . #- run: go test -v -race ./... #- run: go vet ./... diff --git a/README.md b/README.md index 83e73347..9232aa15 100644 --- a/README.md +++ b/README.md @@ -12,31 +12,31 @@ It works on OSX, Linux, Linux ARM and Windows. You can download releases [here]( - GLFW 3.3 - OpenGL >= 2.1 -- OpenAL +- PortAudio #### On OSX You can execute the following command and follow the instructions about exporting PKG_CONFIG - brew install openal-soft + brew install portaudio #### On Debian or Ubuntu - sudo apt-get install libopenal-dev xorg-dev golang + sudo apt-get install portaudio19-dev xorg-dev golang #### On Raspbian You need to enable the experimental VC4 OpenGL support (Full KMS) in raspi-config. - sudo apt-get install libopenal-dev xorg-dev + sudo apt-get install portaudio19-dev xorg-dev #### On Alpine / postmarketOS - sudo apk add musl-dev gcc openal-soft-dev libx11-dev libxcursor-dev libxrandr-dev libxinerama-dev libxi-dev mesa-dev + sudo apk add musl-dev gcc portaudio-dev libx11-dev libxcursor-dev libxrandr-dev libxinerama-dev libxi-dev mesa-dev #### On Windows -Setup openal headers and dll in mingw-w64 `include` and `lib` folders. +Setup portaudio headers and dll in mingw-w64 `include` and `lib` folders. ## Building diff --git a/audio/audio.go b/audio/audio.go index dae4bc60..08c83c97 100644 --- a/audio/audio.go +++ b/audio/audio.go @@ -1,4 +1,4 @@ -// Package audio uses OpenAL to play game audio by exposing the two audio +// Package audio uses PortAudio to play game audio by exposing the two audio // callbacks Sample and SampleBatch for the libretro implementation. package audio @@ -8,39 +8,162 @@ import ( "time" "unsafe" + "github.com/gordonklaus/portaudio" "github.com/libretro/ludo/settings" "github.com/libretro/ludo/state" "github.com/libretro/ludo/utils" - "golang.org/x/mobile/exp/audio/al" ) -const bufSize = 1024 * 8 +const bufSize = 256 * 32 +const bufThreshold = 256 * 24 +const bufThreshold2 = 256 * 8 +const bufBlock = 256 * 8 * 1000 +const maxSeLen = 44100 * 8 +const ffMult = 0.25 var ( - source al.Source - buffers []al.Buffer - rate int32 - numBuffers int32 - tmpBuf [bufSize]byte - tmpBufPtr int32 - resPtr int32 + paBuf [bufSize]int32 + paSeBuf [maxSeLen]int32 + paRate int32 + paPtr int64 + paPlayPtr int64 + paSePtr int + paSeLen int + paCh int + paStream *portaudio.Stream + paSeStream *portaudio.Stream + paUp = false ) // Effects are sound effects var Effects map[string]*Effect -// SetVolume sets the audio volume -func SetVolume(vol float32) { - source.SetGain(vol) +func st2mono(in [2]int16) [2]int16 { + return [2]int16{in[0]/2 + in[1]/2, 0} +} + +func paAudProc(in int32) [2]int16 { + pi := (*[2]int16)(unsafe.Pointer(&in)) + var mt float32 = 1.0 + if state.FastForward { + mt = ffMult + } + pi[0] = int16(float32(pi[0]) * settings.Current.AudioVolume * mt) + pi[1] = int16(float32(pi[1]) * settings.Current.AudioVolume * mt) + if paCh == 1 { + return st2mono(*pi) + } + return *pi +} + +func paSeProc(in int32) [2]int16 { + pi := (*[2]int16)(unsafe.Pointer(&in)) + pi[0] = int16(float32(pi[0]) * settings.Current.MenuAudioVolume) + pi[1] = int16(float32(pi[1]) * settings.Current.MenuAudioVolume) + if paCh == 1 { + return st2mono(*pi) + } + return *pi +} + +// PortAudio Callback +func paCallback(out []int16) { + for i := range out { + if i%paCh == paCh-1 { + if !state.MenuActive { + if paPlayPtr < paPtr { + s := paAudProc(paBuf[paPlayPtr-(paPlayPtr/bufSize)*bufSize]) + for j := 0; j < paCh; j++ { + out[i-(paCh-1)+j] = s[j] + } + paPlayPtr++ + if paPtr-paPlayPtr < bufThreshold2 { + // We have no choice but block pa here (can we speed up the core for a little?) + time.Sleep(time.Millisecond * time.Duration(int64(bufBlock/int(paRate)))) + } + } else { + for j := 0; j < paCh; j++ { + out[i-(paCh-1)+j] = 0 + } + } + } else { + for j := 0; j < paCh; j++ { + out[i-(paCh-1)+j] = 0 + } + } + } + } +} + +// Create PortAudio parameters +func NewParameters(out *portaudio.DeviceInfo) (p portaudio.StreamParameters) { + if out != nil { + p := &p.Output + p.Device = out + p.Channels = 2 + if out.MaxOutputChannels < 2 { + log.Println("[PA]Output device is mono") + p.Channels = out.MaxOutputChannels + } + paCh = p.Channels + p.Latency = out.DefaultLowOutputLatency + } + p.SampleRate = float64(paRate) + p.FramesPerBuffer = portaudio.FramesPerBufferUnspecified + return p } // Init initializes the audio device func Init() { - err := al.OpenDevice() + if paUp { + return + } + err1 := portaudio.Initialize() + if err1 != nil { + log.Println(err1) + } + + paRate = 44100 + paPtr = 0 + paPlayPtr = 0 + paSePtr = 0 + paSeLen = 0 + + h, err := portaudio.DefaultOutputDevice() + if err != nil { + log.Fatalln(err) + } + paStream, err = portaudio.OpenStream(NewParameters(h), paCallback) if err != nil { - log.Println(err) + log.Fatalln(err) } + if err = paStream.Start(); err != nil { + log.Fatalln(err) + } + paSeStream, err = portaudio.OpenStream(NewParameters(h), func(out []int16) { + for i := range out { + if i%paCh == paCh-1 { + if paSePtr < paSeLen { + s := paSeProc(paSeBuf[paSePtr]) + for j := 0; j < paCh; j++ { + out[i-(paCh-1)+j] = s[j] + } + paSePtr++ + } else { + for j := 0; j < paCh; j++ { + out[i-(paCh-1)+j] = 0 + } + } + } + } + }) + if err != nil { + log.Fatalln(err) + } + if err = paSeStream.Start(); err != nil { + log.Fatalln(err) + } Effects = map[string]*Effect{} assets := settings.Current.AssetsDirectory @@ -55,87 +178,64 @@ func Init() { // Reconfigure initializes the audio package. It sets the number of buffers, the // volume and the source for the games. func Reconfigure(r int32) { - rate = r - numBuffers = 4 - - log.Printf("[OpenAL]: Using %v buffers of %v bytes.\n", numBuffers, bufSize) - - source = al.GenSources(1)[0] - buffers = al.GenBuffers(int(numBuffers)) - resPtr = numBuffers - tmpBufPtr = 0 - tmpBuf = [bufSize]byte{} - - source.SetGain(settings.Current.AudioVolume) + paRate = r + paBuf = [bufSize]int32{} + paPtr = 0 + paPlayPtr = 0 + if paStream != nil { + if err := paStream.Close(); err != nil { + log.Fatalln(err) + } + } + h, err := portaudio.DefaultOutputDevice() + if err != nil { + log.Fatalln(err) + } + paStream, err = portaudio.OpenStream(NewParameters(h), paCallback) + if err != nil { + log.Fatalln(err) + } + if err = paStream.Start(); err != nil { + log.Fatalln(err) + } } -func min(a, b int32) int32 { +func min(a, b int) int { if a < b { return a } return b } -func alUnqueueBuffers() bool { - val := source.BuffersProcessed() - - if val <= 0 { - return false - } - - source.UnqueueBuffers(buffers[resPtr:val]...) - resPtr += val - return true -} - -func alGetBuffer() al.Buffer { - if resPtr == 0 { - for { - if alUnqueueBuffers() { - break - } - time.Sleep(time.Millisecond) - } - } - - resPtr-- - return buffers[resPtr] -} - -func fillInternalBuf(buf []byte) int32 { - readSize := min(bufSize-tmpBufPtr, int32(len(buf))) - copy(tmpBuf[tmpBufPtr:], buf[:readSize]) - tmpBufPtr += readSize - return readSize -} - func write(buf []byte, size int32) int32 { written := int32(0) + bufOff := paPtr - paPlayPtr if state.FastForward { - return size + bufOff = 0 + } else { + blk := (paPtr - paPlayPtr) / bufThreshold + if blk > 0 { + log.Println("[PA]Core goes too fast, slowing down") + time.Sleep(time.Millisecond * time.Duration(blk*int64(bufBlock/int(paRate)))) + } } - for size > 0 { - - rc := fillInternalBuf(buf[written:]) - - written += rc - size -= rc + mm := min(int(size/4), int(bufSize-bufOff)) + for i := 0; i < mm; i++ { + p := 4 * i + paBuf[paPtr-(paPtr/bufSize)*bufSize] = *(*int32)(unsafe.Pointer(&buf[p])) + paPtr++ + written += 4 + } - if tmpBufPtr != bufSize { + // Reset ptr into single range + for { + if paPtr-paPlayPtr < bufSize*2 { break } - - buffer := alGetBuffer() - - buffer.BufferData(al.FormatStereo16, tmpBuf[:], rate) - tmpBufPtr = 0 - source.QueueBuffers(buffer) - - if source.State() != al.Playing { - al.PlaySources(source) - } + log.Println("[PA]Buffer bit the tail! Are we fast-forwarding?") + paPtr -= int64(bufSize) } return written diff --git a/audio/audio_test.go b/audio/audio_test.go index dc4e8170..a43d165e 100644 --- a/audio/audio_test.go +++ b/audio/audio_test.go @@ -4,55 +4,9 @@ import ( "testing" ) -func Test_alUnqueueBuffers(t *testing.T) { - t.Run("Return false if no buffers were processed", func(t *testing.T) { - got := alUnqueueBuffers() - if got { - t.Errorf("alUnqueueBuffers() = %v, want %v", got, false) - } - }) -} - func Test_Sample(t *testing.T) { t.Run("Doesn't crash when called", func(t *testing.T) { Sample(-30000, -30000) - Sample( 30000, 30000) + Sample(30000, 30000) }) } - -func Test_fillInternalBuf(t *testing.T) { - Reconfigure(48000) - type args struct { - buf []byte - size int32 - } - tests := []struct { - name string - args args - want int32 - }{ - { - name: "Fill the buffer partially", - args: args{ - buf: make([]byte, bufSize), - size: 6000, - }, - want: 6000, - }, - { - name: "Fill the buffer fully", - args: args{ - buf: make([]byte, bufSize), - size: 6000, - }, - want: 2192, - }, - } - for _, tt := range tests { - t.Run(tt.name, func(t *testing.T) { - if got := fillInternalBuf(tt.args.buf[:tt.args.size]); got != tt.want { - t.Errorf("fillInternalBuf() = %v, want %v", got, tt.want) - } - }) - } -} diff --git a/audio/effect.go b/audio/effect.go index 56bb511a..258ca698 100644 --- a/audio/effect.go +++ b/audio/effect.go @@ -2,25 +2,20 @@ package audio import ( "os" + "unsafe" - "github.com/libretro/ludo/settings" wav "github.com/youpy/go-wav" - "golang.org/x/mobile/exp/audio/al" ) // Effect is a static sound effect type Effect struct { Format *wav.WavFormat - source al.Source + paBuf []int32 } -// LoadEffect loads a wav into memory and prepare the buffer and source in OpenAL +// LoadEffect loads a wav into memory and prepare the buffer func LoadEffect(filename string) (*Effect, error) { var e Effect - e.source = al.GenSources(1)[0] - buffer := al.GenBuffers(1)[0] - e.source.SetGain(settings.Current.MenuAudioVolume) - file, err := os.Open(filename) if err != nil { return nil, err @@ -43,21 +38,29 @@ func LoadEffect(filename string) (*Effect, error) { wav = append(wav, data[:]...) } - buffer.BufferData(al.FormatStereo16, wav, int32(e.Format.SampleRate)) - e.source.QueueBuffers(buffer) - al.DeleteBuffers(buffer) + var step int = int(e.Format.NumChannels) * 2 + samples := len(wav) / step + e.paBuf = make([]int32, samples) + for i := 0; i < samples; i++ { + if e.Format.NumChannels == 2 { + e.paBuf[i] = *(*int32)(unsafe.Pointer(&wav[step*i])) + } else { + var s *[2]int16 + s[0] = *(*int16)(unsafe.Pointer(&wav[step*i])) + s[1] = s[0] + e.paBuf[i] = *(*int32)(unsafe.Pointer(&s[0])) + } + } return &e, nil } // PlayEffect plays a sound effect func PlayEffect(e *Effect) { - al.PlaySources(e.source) -} - -// SetEffectsVolume sets the audio volume of sound effects -func SetEffectsVolume(vol float32) { - for _, e := range Effects { - e.source.SetGain(vol) + if len(e.paBuf) > 0 && len(e.paBuf) < maxSeLen { + paSeBuf = [maxSeLen]int32{} + copy(paSeBuf[:], e.paBuf) + paSeLen = len(e.paBuf) + paSePtr = 0 } } diff --git a/core/core_test.go b/core/core_test.go index f0f73fd0..b25082da 100644 --- a/core/core_test.go +++ b/core/core_test.go @@ -9,6 +9,7 @@ import ( "testing" "github.com/go-gl/glfw/v3.3/glfw" + "github.com/libretro/ludo/audio" "github.com/libretro/ludo/libretro" "github.com/libretro/ludo/state" "github.com/libretro/ludo/utils" @@ -34,6 +35,7 @@ func Test_coreLoad(t *testing.T) { ext := utils.CoreExt() Init(&video.Video{}) + audio.Init() out := utils.CaptureOutput(func() { Load("testdata/vecx_libretro" + ext) }) @@ -194,6 +196,7 @@ func Test_coreLoadGame(t *testing.T) { ext := utils.CoreExt() Init(&video.Video{}) + audio.Init() if err := glfw.Init(); err != nil { log.Fatalln("failed to initialize glfw") diff --git a/go.mod b/go.mod index 5d5ef1d6..f4684f9c 100644 --- a/go.mod +++ b/go.mod @@ -11,6 +11,7 @@ require ( github.com/go-gl/glfw/v3.3/glfw v0.0.0-20220806181222-55e207c401ad github.com/golang/freetype v0.0.0-20170609003504-e2365dfdc4a0 github.com/golang/snappy v0.0.4 // indirect + github.com/gordonklaus/portaudio v0.0.0-20220320131553-cc649ad523c1 github.com/klauspost/compress v1.13.6 // indirect github.com/kr/text v0.2.0 // indirect github.com/lucasb-eyer/go-colorful v1.2.0 diff --git a/go.sum b/go.sum index 86c1e21b..51faf081 100644 --- a/go.sum +++ b/go.sum @@ -29,6 +29,8 @@ github.com/golang/snappy v0.0.4/go.mod h1:/XxbfmMg8lxefKM7IXC3fBNl/7bRcc72aCRzEW github.com/google/go-cmp v0.5.5/go.mod h1:v8dTdLbMG2kIc/vJvl+f65V22dbkXbowE6jgT/gNBxE= github.com/google/go-cmp v0.5.6 h1:BKbKCqvP6I+rmFHt06ZmyQtvB8xAkWdhFyr0ZUNZcxQ= github.com/google/go-cmp v0.5.6/go.mod h1:v8dTdLbMG2kIc/vJvl+f65V22dbkXbowE6jgT/gNBxE= +github.com/gordonklaus/portaudio v0.0.0-20220320131553-cc649ad523c1 h1:FgUJ91JoMbS5qWXdIpnHta1hLtw1X8n2ek5JRED3R1I= +github.com/gordonklaus/portaudio v0.0.0-20220320131553-cc649ad523c1/go.mod h1:HfYnZi/ARQKG0dwH5HNDmPCHdLiFiBf+SI7DbhW7et4= github.com/klauspost/compress v1.4.1/go.mod h1:RyIbtBH6LamlWaDj8nUwkbUhJ87Yi3uG0guNDohfE1A= github.com/klauspost/compress v1.11.4/go.mod h1:aoV0uJVorq1K+umq18yTdKaF57EivdYsUV+/s2qKfXs= github.com/klauspost/compress v1.13.6 h1:P76CopJELS0TiO2mebmnzgWaajssP/EszplttgQxcgc= diff --git a/menu/menu_test.go b/menu/menu_test.go index a6e65796..09ee7e95 100644 --- a/menu/menu_test.go +++ b/menu/menu_test.go @@ -5,6 +5,7 @@ import ( "reflect" "testing" + "github.com/libretro/ludo/audio" "github.com/libretro/ludo/state" "github.com/libretro/ludo/video" @@ -14,6 +15,7 @@ import ( func Test_WarpToQuickMenu(t *testing.T) { m := Init(&video.Video{}) + audio.Init() t.Run("Starts with a single scene if no game is running", func(t *testing.T) { got := len(menu.stack) diff --git a/menu/scene_settings.go b/menu/scene_settings.go index c5e93bf1..b7c324b8 100644 --- a/menu/scene_settings.go +++ b/menu/scene_settings.go @@ -8,7 +8,6 @@ import ( "github.com/fatih/structs" "github.com/go-gl/glfw/v3.3/glfw" - "github.com/libretro/ludo/audio" "github.com/libretro/ludo/ludos" ntf "github.com/libretro/ludo/notifications" "github.com/libretro/ludo/settings" @@ -219,7 +218,6 @@ var incrCallbacks = map[string]callbackIncrement{ v = 1 } f.Set(v) - audio.SetVolume(v) settings.Save() }, "MenuAudioVolume": func(f *structs.Field, direction int) { @@ -232,7 +230,6 @@ var incrCallbacks = map[string]callbackIncrement{ v = 1 } f.Set(v) - audio.SetEffectsVolume(v) settings.Save() }, "ShowHiddenFiles": func(f *structs.Field, direction int) { diff --git a/pkg/control b/pkg/control index 4301b187..63e3a8f6 100644 --- a/pkg/control +++ b/pkg/control @@ -1,7 +1,7 @@ Package: ludo Version: VERSION Architecture: ARCH -Depends: libc6, libopenal1, libgl1 +Depends: libc6, libportaudio2, libgl1 Maintainer: Jean-André Santoni jean.andre.santoni@gmail.com Section: games Priority: optional