mirror of
https://github.com/ghostty-org/ghostty.git
synced 2025-07-17 09:16:11 +03:00
macos: detect keyboard layout change and reload the keymap
This commit is contained in:
@ -283,6 +283,7 @@ ghostty_app_t ghostty_app_new(const ghostty_runtime_config_s *, ghostty_config_t
|
||||
void ghostty_app_free(ghostty_app_t);
|
||||
bool ghostty_app_tick(ghostty_app_t);
|
||||
void *ghostty_app_userdata(ghostty_app_t);
|
||||
void ghostty_app_keyboard_changed(ghostty_app_t);
|
||||
|
||||
ghostty_surface_t ghostty_surface_new(ghostty_app_t, ghostty_surface_config_s*);
|
||||
void ghostty_surface_free(ghostty_surface_t);
|
||||
|
@ -75,6 +75,13 @@ extension Ghostty {
|
||||
}
|
||||
self.app = app
|
||||
|
||||
// Subscribe to notifications for keyboard layout change so that we can update Ghostty.
|
||||
NotificationCenter.default.addObserver(
|
||||
self,
|
||||
selector: #selector(self.keyboardSelectionDidChange(notification:)),
|
||||
name: NSTextInputContext.keyboardSelectionDidChangeNotification,
|
||||
object: nil)
|
||||
|
||||
self.readiness = .ready
|
||||
}
|
||||
|
||||
@ -82,6 +89,12 @@ extension Ghostty {
|
||||
// This will force the didSet callbacks to run which free.
|
||||
self.app = nil
|
||||
self.config = nil
|
||||
|
||||
// Remove our observer
|
||||
NotificationCenter.default.removeObserver(
|
||||
self,
|
||||
name: NSTextInputContext.keyboardSelectionDidChangeNotification,
|
||||
object: nil)
|
||||
}
|
||||
|
||||
/// Initializes a new configuration and loads all the values.
|
||||
@ -132,6 +145,13 @@ extension Ghostty {
|
||||
ghostty_surface_split_focus(surface, direction.toNative())
|
||||
}
|
||||
|
||||
// Called when the selected keyboard changes. We have to notify Ghostty so that
|
||||
// it can reload the keyboard mapping for input.
|
||||
@objc private func keyboardSelectionDidChange(notification: NSNotification) {
|
||||
guard let app = self.app else { return }
|
||||
ghostty_app_keyboard_changed(app)
|
||||
}
|
||||
|
||||
// MARK: Ghostty Callbacks
|
||||
|
||||
static func newSplit(_ userdata: UnsafeMutableRawPointer?, direction: ghostty_split_direction_e) {
|
||||
|
@ -92,6 +92,17 @@ pub const App = struct {
|
||||
self.keymap.deinit();
|
||||
}
|
||||
|
||||
/// This should be called whenever the keyboard layout was changed.
|
||||
pub fn reloadKeymap(self: *App) !void {
|
||||
// Reload the keymap
|
||||
try self.keymap.reload();
|
||||
|
||||
// Clear the dead key state since we changed the keymap, any
|
||||
// dead key state is just forgotten. i.e. if you type ' on us-intl
|
||||
// and then switch to us and type a, you'll get a rather than á.
|
||||
self.keymap_state = .{};
|
||||
}
|
||||
|
||||
pub fn reloadConfig(self: *App) !?*const Config {
|
||||
// Reload
|
||||
if (self.opts.reload_config(self.opts.userdata)) |new| {
|
||||
@ -475,6 +486,15 @@ pub const CAPI = struct {
|
||||
core_app.destroy();
|
||||
}
|
||||
|
||||
/// Notify the app that the keyboard was changed. This causes the
|
||||
/// keyboard layout to be reloaded from the OS.
|
||||
export fn ghostty_app_keyboard_changed(v: *App) void {
|
||||
v.reloadKeymap() catch |err| {
|
||||
log.err("error reloading keyboard map err={}", .{err});
|
||||
return;
|
||||
};
|
||||
}
|
||||
|
||||
/// Create a new surface as part of an app.
|
||||
export fn ghostty_surface_new(
|
||||
app: *App,
|
||||
|
Reference in New Issue
Block a user