diff --git a/build.zig b/build.zig index e6e95b0fe..cc914dca2 100644 --- a/build.zig +++ b/build.zig @@ -795,30 +795,24 @@ fn addDeps( // get access to glib for dbus. if (flatpak) step.linkSystemLibrary2("gtk4", dynamic_link_opts); - // We may link GLFW below - const glfw_dep = b.dependency("glfw", .{ - .target = step.target, - .optimize = step.optimize, - .x11 = step.target.isLinux(), - .wayland = step.target.isLinux(), - .metal = step.target.isDarwin(), - }); - switch (app_runtime) { .none => {}, .glfw => { + const glfw_dep = b.dependency("glfw", .{ + .target = step.target, + .optimize = step.optimize, + .x11 = step.target.isLinux(), + .wayland = step.target.isLinux(), + .metal = step.target.isDarwin(), + }); + step.addModule("glfw", mach_glfw_dep.module("mach-glfw")); step.linkLibrary(mach_glfw_dep.artifact("mach-glfw")); step.linkLibrary(glfw_dep.artifact("glfw")); }, .gtk => { - // We need glfw for GTK because we use GLFW to get DPI. - step.addModule("glfw", mach_glfw_dep.module("mach-glfw")); - step.linkLibrary(mach_glfw_dep.artifact("mach-glfw")); - step.linkLibrary(glfw_dep.artifact("glfw")); - step.linkSystemLibrary2("gtk4", dynamic_link_opts); }, } diff --git a/src/apprt/gtk/App.zig b/src/apprt/gtk/App.zig index 74d3c6b76..47e69eba3 100644 --- a/src/apprt/gtk/App.zig +++ b/src/apprt/gtk/App.zig @@ -13,7 +13,6 @@ const App = @This(); const std = @import("std"); const assert = std.debug.assert; const builtin = @import("builtin"); -const glfw = @import("glfw"); const configpkg = @import("../../config.zig"); const input = @import("../../input.zig"); const internal_os = @import("../../os/main.zig"); @@ -53,12 +52,6 @@ running: bool = true, pub fn init(core_app: *CoreApp, opts: Options) !App { _ = opts; - // This is super weird, but we still use GLFW with GTK only so that - // we can tap into their folklore logic to get screen DPI. If we can - // figure out a reliable way to determine this ourselves, we can get - // rid of this dep. - if (!glfw.init(.{})) return error.GlfwInitFailed; - // Load our configuration var config = try Config.load(core_app.alloc); errdefer config.deinit(); @@ -166,8 +159,6 @@ pub fn terminate(self: *App) void { if (self.menu) |menu| c.g_object_unref(menu); self.config.deinit(); - - glfw.terminate(); } /// Reload the configuration. This should return the new configuration. diff --git a/src/apprt/gtk/Surface.zig b/src/apprt/gtk/Surface.zig index 86a6c816e..054c736e5 100644 --- a/src/apprt/gtk/Surface.zig +++ b/src/apprt/gtk/Surface.zig @@ -4,7 +4,6 @@ const Surface = @This(); const std = @import("std"); -const glfw = @import("glfw"); const configpkg = @import("../../config.zig"); const apprt = @import("../../apprt.zig"); const font = @import("../../font/main.zig"); @@ -19,9 +18,6 @@ const c = @import("c.zig"); const log = std.log.scoped(.gtk); -// We need native X11 access to access the primary clipboard. -const glfw_native = glfw.Native(.{ .x11 = true }); - /// This is detected by the OpenGL renderer to move to a single-threaded /// draw operation. This basically puts locks around our draw path. pub const opengl_single_threaded_draw = true; @@ -354,10 +350,10 @@ pub fn shouldClose(self: *const Surface) bool { } pub fn getContentScale(self: *const Surface) !apprt.ContentScale { - _ = self; - const monitor = glfw.Monitor.getPrimary() orelse return error.NoMonitor; - const scale = monitor.getContentScale(); - return apprt.ContentScale{ .x = scale.x_scale, .y = scale.y_scale }; + // Future: detect GTK version 4.12+ and use gdk_surface_get_scale so we + // can support fractional scaling. + const scale = c.gtk_widget_get_scale_factor(@ptrCast(self.gl_area)); + return .{ .x = @floatFromInt(scale), .y = @floatFromInt(scale) }; } pub fn getSize(self: *const Surface) !apprt.SurfaceSize { @@ -625,6 +621,15 @@ fn gtkResize(area: *c.GtkGLArea, width: c.gint, height: c.gint, ud: ?*anyopaque) .height = @intCast(height), }; + // We also update the content scale because there is no signal for + // content scale change and it seems to trigger a resize event. + if (self.getContentScale()) |scale| { + self.core_surface.contentScaleCallback(scale) catch |err| { + log.err("error in content scale callback err={}", .{err}); + return; + }; + } else |_| {} + // Call the primary callback. if (self.realized) { self.core_surface.sizeCallback(self.size) catch |err| {