How to play sound using Gtk (original) (raw)

February 16, 2024, 7:02pm 1

I am completely new to Gtk development, and I am struggling to find a way to play sound using gtk.

From the documentation, it seems there is a MediaFile class that inherits a MediaStream class that can play files, although I am not sure whether this suits Audio files.

        const mediaFile = Gtk.MediaFile.new_for_resource("/dev/louscouture/watchsync/beep.wav")
        mediaFile.play()

It doesn’t say to me that the function doesn’t exists but the sound does not play. I have no idea how to do this.

mcatanzaro (Michael Catanzaro) February 16, 2024, 7:14pm 2

You want to use libgsound!

ebassi (Emmanuele Bassi) February 16, 2024, 9:14pm 3

You most definitely don’t want to use an unmaintained wrapper like gsound around an unmaintained library like libcanberra.

Playing a sound is done by loading a file using GtkMediaFile, and using the GtkMediaStream API:

You may need to set the volume of the media stream to 1.

There is a simple example in the GTK repository: tests/testsounds.c · main · GNOME / gtk · GitLab

sonny (Sonny Piers) February 16, 2024, 9:52pm 4

There is an “Audio” demo in Workbench library in case that’s helpful.

Louis_Couture (Louis Couture) February 16, 2024, 11:51pm 6

I am unable to reproduce this for my use case, which is a sounds that needs to play without a MediaControlWidget

        const file = Gio.File.new_for_uri("/beep.ogg");

        let media_stream = Gtk.MediaFile.new_for_file(file)
        media_stream.set_volume(1.0)
        media_stream.play()

chrisaw (Chris Williams) February 17, 2024, 1:17am 7

/beep.ogg is an absolute path (which is probably not what you intended), and also is not a URI.

This API seems to fail silently when the file is missing. You can connect to notify::prepared on the Gtk.MediaStream and then check the has-audio property.

The example in Workbench still works for me after modifying it not to use Gtk.MediaControls.

Louis_Couture (Louis Couture) February 17, 2024, 4:03am 8

can you show your example ?

I did use a ressource and I listened to notify::change event and the sounds is there but it is not playing

 let media_stream = Gtk.MediaFile.new_for_resource("/dev/louscouture/watchsync/beep.wav")

media_stream.connect("notify::prepared", ()=>{console.log(media_stream.has_audio);media_stream.set_volume(1.0);media_stream.play()})

chrisaw (Chris Williams) February 17, 2024, 5:07am 9

In Workbench, you can just not set controls.media_stream, and it’ll be inactive. Simplifying it all the way to this also works.

import Gio from "gi://Gio";
import Gtk from "gi://Gtk";

let file = Gio.File.new_for_uri(workbench.resolve("./Dog.ogg"));
let media_stream = Gtk.MediaFile.new_for_file(file);
media_stream.play();

I did notice at one point that it wouldn’t play the first time (even with the original, unmodified example). I haven’t been able to make that happen again though.

Louis_Couture (Louis Couture) February 17, 2024, 10:11pm 10

Is there a way to do this but on gnome builder.
I want it to be on a real app.

Louis_Couture (Louis Couture) February 18, 2024, 3:25am 11

The template uses workbench specific class.

I cannot use this to make a real app using builder.

It is unclear looking at the code workbench.resolve

I’ve tried using ressource but the sound just doesn’t play

sonny (Sonny Piers) February 18, 2024, 9:42am 12

Probably because your resource isn’t registered properly.

You’ll have to share a repo for us to be able to help you.

Louis_Couture (Louis Couture) February 18, 2024, 4:31pm 13

I ended up finding the reason why the sound wasn’t playing

I had to register permissions in the finish args in my .json file

        "--socket=pulseaudio",

system (system) Closed March 19, 2024, 4:32pm 14

This topic was automatically closed 30 days after the last reply. New replies are no longer allowed.