mirror of
https://github.com/ghostty-org/ghostty.git
synced 2025-08-02 14:57:31 +03:00
gtk: implement custom audio for bell
This commit is contained in:
@ -28,6 +28,9 @@
|
|||||||
pkgs.glib
|
pkgs.glib
|
||||||
pkgs.gobject-introspection
|
pkgs.gobject-introspection
|
||||||
pkgs.gsettings-desktop-schemas
|
pkgs.gsettings-desktop-schemas
|
||||||
|
pkgs.gst_all_1.gst-plugins-base
|
||||||
|
pkgs.gst_all_1.gst-plugins-good
|
||||||
|
pkgs.gst_all_1.gstreamer
|
||||||
pkgs.gtk4
|
pkgs.gtk4
|
||||||
pkgs.libadwaita
|
pkgs.libadwaita
|
||||||
]
|
]
|
||||||
|
@ -35,6 +35,7 @@
|
|||||||
gtk4,
|
gtk4,
|
||||||
gtk4-layer-shell,
|
gtk4-layer-shell,
|
||||||
gobject-introspection,
|
gobject-introspection,
|
||||||
|
gst_all_1,
|
||||||
libadwaita,
|
libadwaita,
|
||||||
blueprint-compiler,
|
blueprint-compiler,
|
||||||
gettext,
|
gettext,
|
||||||
@ -166,6 +167,9 @@ in
|
|||||||
wayland
|
wayland
|
||||||
wayland-scanner
|
wayland-scanner
|
||||||
wayland-protocols
|
wayland-protocols
|
||||||
|
gst_all_1.gstreamer
|
||||||
|
gst_all_1.gst-plugins-base
|
||||||
|
gst_all_1.gst-plugins-good
|
||||||
];
|
];
|
||||||
|
|
||||||
# This should be set onto the rpath of the ghostty binary if you want
|
# This should be set onto the rpath of the ghostty binary if you want
|
||||||
|
@ -127,6 +127,10 @@ in
|
|||||||
mv $out/share/vim/vimfiles "$vim"
|
mv $out/share/vim/vimfiles "$vim"
|
||||||
ln -sf "$vim" "$out/share/vim/vimfiles"
|
ln -sf "$vim" "$out/share/vim/vimfiles"
|
||||||
echo "$vim" >> "$out/nix-support/propagated-user-env-packages"
|
echo "$vim" >> "$out/nix-support/propagated-user-env-packages"
|
||||||
|
|
||||||
|
echo "gst_all_1.gstreamer" >> "$out/nix-support/propagated-user-env-packages"
|
||||||
|
echo "gst_all_1.gst-plugins-base" >> "$out/nix-support/propagated-user-env-packages"
|
||||||
|
echo "gst_all_1.gst-plugins-good" >> "$out/nix-support/propagated-user-env-packages"
|
||||||
'';
|
'';
|
||||||
|
|
||||||
meta = {
|
meta = {
|
||||||
|
@ -2405,6 +2405,47 @@ pub fn ringBell(self: *Surface) !void {
|
|||||||
surface.beep();
|
surface.beep();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (features.audio) audio: {
|
||||||
|
// Play a user-specified audio file.
|
||||||
|
|
||||||
|
const pathname, const optional = switch (self.app.config.@"bell-audio-path" orelse break :audio) {
|
||||||
|
.optional => |path| .{ path, true },
|
||||||
|
.required => |path| .{ path, false },
|
||||||
|
};
|
||||||
|
|
||||||
|
const volume: f64 = @min(
|
||||||
|
@max(
|
||||||
|
0.0,
|
||||||
|
self.app.config.@"bell-audio-volume",
|
||||||
|
),
|
||||||
|
1.0,
|
||||||
|
);
|
||||||
|
|
||||||
|
std.debug.assert(std.fs.path.isAbsolute(pathname));
|
||||||
|
const media_file = gtk.MediaFile.newForFilename(pathname);
|
||||||
|
|
||||||
|
if (!optional) {
|
||||||
|
_ = gobject.Object.signals.notify.connect(
|
||||||
|
media_file,
|
||||||
|
?*anyopaque,
|
||||||
|
gtkStreamError,
|
||||||
|
null,
|
||||||
|
.{ .detail = "error" },
|
||||||
|
);
|
||||||
|
}
|
||||||
|
_ = gobject.Object.signals.notify.connect(
|
||||||
|
media_file,
|
||||||
|
?*anyopaque,
|
||||||
|
gtkStreamEnded,
|
||||||
|
null,
|
||||||
|
.{ .detail = "ended" },
|
||||||
|
);
|
||||||
|
|
||||||
|
const media_stream = media_file.as(gtk.MediaStream);
|
||||||
|
media_stream.setVolume(volume);
|
||||||
|
media_stream.play();
|
||||||
|
}
|
||||||
|
|
||||||
// Mark tab as needing attention
|
// Mark tab as needing attention
|
||||||
if (self.container.tab()) |tab| tab: {
|
if (self.container.tab()) |tab| tab: {
|
||||||
const page = window.notebook.getTabPage(tab) orelse break :tab;
|
const page = window.notebook.getTabPage(tab) orelse break :tab;
|
||||||
@ -2413,3 +2454,27 @@ pub fn ringBell(self: *Surface) !void {
|
|||||||
if (page.getSelected() == 0) page.setNeedsAttention(@intFromBool(true));
|
if (page.getSelected() == 0) page.setNeedsAttention(@intFromBool(true));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// Handle a stream that is in an error state.
|
||||||
|
fn gtkStreamError(media_file: *gtk.MediaFile, _: *gobject.ParamSpec, _: ?*anyopaque) callconv(.c) void {
|
||||||
|
const path = path: {
|
||||||
|
const file = media_file.getFile() orelse break :path null;
|
||||||
|
break :path file.getPath();
|
||||||
|
};
|
||||||
|
defer if (path) |p| glib.free(p);
|
||||||
|
|
||||||
|
const media_stream = media_file.as(gtk.MediaStream);
|
||||||
|
const err = media_stream.getError() orelse return;
|
||||||
|
|
||||||
|
log.warn("error playing bell from {s}: {s} {d} {s}", .{
|
||||||
|
path orelse "<<unknown>>",
|
||||||
|
glib.quarkToString(err.f_domain),
|
||||||
|
err.f_code,
|
||||||
|
err.f_message orelse "",
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
/// Stream is finished, release the memory.
|
||||||
|
fn gtkStreamEnded(media_file: *gtk.MediaFile, _: *gobject.ParamSpec, _: ?*anyopaque) callconv(.c) void {
|
||||||
|
media_file.unref();
|
||||||
|
}
|
||||||
|
@ -1890,8 +1890,10 @@ keybind: Keybinds = .{},
|
|||||||
/// open terminals.
|
/// open terminals.
|
||||||
@"custom-shader-animation": CustomShaderAnimation = .true,
|
@"custom-shader-animation": CustomShaderAnimation = .true,
|
||||||
|
|
||||||
/// The list of enabled features that are activated after encountering
|
/// Bell features to enable if bell support is available in your runtime. Not
|
||||||
/// a bell character.
|
/// all features are available on all runtimes. The format of this is a list of
|
||||||
|
/// features to enable separated by commas. If you prefix a feature with `no-`
|
||||||
|
/// then it is disabled. If you omit a feature, its default value is used.
|
||||||
///
|
///
|
||||||
/// Valid values are:
|
/// Valid values are:
|
||||||
///
|
///
|
||||||
@ -1901,17 +1903,36 @@ keybind: Keybinds = .{},
|
|||||||
/// This could result in an audiovisual effect, a notification, or something
|
/// This could result in an audiovisual effect, a notification, or something
|
||||||
/// else entirely. Changing these effects require altering system settings:
|
/// else entirely. Changing these effects require altering system settings:
|
||||||
/// for instance under the "Sound > Alert Sound" setting in GNOME,
|
/// for instance under the "Sound > Alert Sound" setting in GNOME,
|
||||||
/// or the "Accessibility > System Bell" settings in KDE Plasma.
|
/// or the "Accessibility > System Bell" settings in KDE Plasma. (GTK only)
|
||||||
///
|
///
|
||||||
/// On macOS this has no affect.
|
/// * `audio`
|
||||||
|
///
|
||||||
|
/// Play a custom sound. (GTK only)
|
||||||
|
///
|
||||||
|
/// Example: `audio`, `no-audio`, `system`, `no-system`:
|
||||||
///
|
///
|
||||||
/// On macOS, if the app is unfocused, it will bounce the app icon in the dock
|
/// On macOS, if the app is unfocused, it will bounce the app icon in the dock
|
||||||
/// once. Additionally, the title of the window with the alerted terminal
|
/// once. Additionally, the title of the window with the alerted terminal
|
||||||
/// surface will contain a bell emoji (🔔) until the terminal is focused
|
/// surface will contain a bell emoji (🔔) until the terminal is focused
|
||||||
/// or a key is pressed. These are not currently configurable since they're
|
/// or a key is pressed. These are not currently configurable since they're
|
||||||
/// considered unobtrusive.
|
/// considered unobtrusive.
|
||||||
|
///
|
||||||
|
/// By default, no bell features are enabled.
|
||||||
@"bell-features": BellFeatures = .{},
|
@"bell-features": BellFeatures = .{},
|
||||||
|
|
||||||
|
/// If `audio` is an enabled bell feature, this is a path to an audio file. If
|
||||||
|
/// the path is not absolute, it is considered relative to the directory of the
|
||||||
|
/// configuration file that it is referenced from, or from the current working
|
||||||
|
/// directory if this is used as a CLI flag. The path may be prefixed with `~/`
|
||||||
|
/// to reference the user's home directory. (GTK only)
|
||||||
|
@"bell-audio-path": ?Path = null,
|
||||||
|
|
||||||
|
/// If `audio` is an enabled bell feature, this is the volume to play the audio
|
||||||
|
/// file at (relative to the system volume). This is a floating point number
|
||||||
|
/// ranging from 0.0 (silence) to 1.0 (as loud as possible). The default is 0.5.
|
||||||
|
/// (GTK only)
|
||||||
|
@"bell-audio-volume": f64 = 0.5,
|
||||||
|
|
||||||
/// Control the in-app notifications that Ghostty shows.
|
/// Control the in-app notifications that Ghostty shows.
|
||||||
///
|
///
|
||||||
/// On Linux (GTK), in-app notifications show up as toasts. Toasts appear
|
/// On Linux (GTK), in-app notifications show up as toasts. Toasts appear
|
||||||
@ -5765,6 +5786,7 @@ pub const AppNotifications = packed struct {
|
|||||||
/// See bell-features
|
/// See bell-features
|
||||||
pub const BellFeatures = packed struct {
|
pub const BellFeatures = packed struct {
|
||||||
system: bool = false,
|
system: bool = false,
|
||||||
|
audio: bool = false,
|
||||||
};
|
};
|
||||||
|
|
||||||
/// See mouse-shift-capture
|
/// See mouse-shift-capture
|
||||||
|
Reference in New Issue
Block a user