fix: apply background-opacity and background-blur to terminal rendering area
Two root causes for issue #879: 1. GhosttyNSView was missing makeBackingLayer(), so AppKit provided a generic CALayer as the view's backing layer. libghostty expects (view.layer as? CAMetalLayer) != nil to set up Metal rendering on the existing layer. Without a CAMetalLayer backing layer, the Metal surface defaulted to isOpaque=true, making the terminal area fully opaque regardless of background-opacity config. Fix: override makeBackingLayer() to return a CAMetalLayer with isOpaque=false and bgra8Unorm pixel format (matching standalone Ghostty's SurfaceView behavior). 2. ghostty_set_window_background_blur(app, window) is exposed in ghostty.h but was never called in cmux. Without this call the macOS window never gets the NSVisualEffectView blur backdrop that background-blur requires. Fix: add applyWindowBlurIfNeeded() on GhosttyApp that reads background-blur from config via ghostty_config_get and calls ghostty_set_window_background_blur when the value is non-zero. Called from applyBackgroundToKeyWindow() and applyWindowBackgroundIfActive() whenever the window is made transparent. Fixes #879 Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
This commit is contained in:
parent
c44e975855
commit
1235daff04
1 changed files with 24 additions and 0 deletions
|
|
@ -2411,6 +2411,7 @@ class GhosttyApp {
|
|||
if cmuxShouldUseClearWindowBackground(for: defaultBackgroundOpacity) {
|
||||
window.backgroundColor = cmuxTransparentWindowBaseColor()
|
||||
window.isOpaque = false
|
||||
applyWindowBlurIfNeeded(window)
|
||||
if backgroundLogEnabled {
|
||||
logBackground("applied transparent window background opacity=\(String(format: "%.3f", defaultBackgroundOpacity))")
|
||||
}
|
||||
|
|
@ -2424,6 +2425,16 @@ class GhosttyApp {
|
|||
}
|
||||
}
|
||||
|
||||
func applyWindowBlurIfNeeded(_ window: NSWindow) {
|
||||
guard let app = self.app else { return }
|
||||
// ghostty_set_window_background_blur reads background-blur and
|
||||
// background-opacity from the app config internally and calls
|
||||
// CGSSetWindowBackgroundBlurRadius — a compositor-level setter that is
|
||||
// idempotent. It is a no-op when opacity >= 1.0 or blur is disabled,
|
||||
// so we can call it unconditionally whenever the window is transparent.
|
||||
ghostty_set_window_background_blur(app, Unmanaged.passUnretained(window).toOpaque())
|
||||
}
|
||||
|
||||
private func activeMainWindow() -> NSWindow? {
|
||||
let keyWindow = NSApp.keyWindow
|
||||
if let raw = keyWindow?.identifier?.rawValue,
|
||||
|
|
@ -3849,6 +3860,18 @@ class GhosttyNSView: NSView, NSUserInterfaceValidations {
|
|||
setup()
|
||||
}
|
||||
|
||||
override func makeBackingLayer() -> CALayer {
|
||||
let metalLayer = CAMetalLayer()
|
||||
metalLayer.pixelFormat = .bgra8Unorm
|
||||
metalLayer.isOpaque = false
|
||||
// framebufferOnly=false lets the macOS compositor read the drawable
|
||||
// when blending translucent or blurred window layers. This matches
|
||||
// standalone Ghostty's SurfaceView and is required for background-opacity
|
||||
// and background-blur to render correctly.
|
||||
metalLayer.framebufferOnly = false
|
||||
return metalLayer
|
||||
}
|
||||
|
||||
private func setup() {
|
||||
// Only enable our instrumented CAMetalLayer in targeted debug/test scenarios.
|
||||
// The lock in GhosttyMetalLayer.nextDrawable() adds overhead we don't want in normal runs.
|
||||
|
|
@ -3931,6 +3954,7 @@ class GhosttyNSView: NSView, NSUserInterfaceValidations {
|
|||
if cmuxShouldUseClearWindowBackground(for: color.alphaComponent) {
|
||||
window.backgroundColor = cmuxTransparentWindowBaseColor()
|
||||
window.isOpaque = false
|
||||
GhosttyApp.shared.applyWindowBlurIfNeeded(window)
|
||||
} else {
|
||||
window.backgroundColor = color
|
||||
window.isOpaque = color.alphaComponent >= 1.0
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue