Skip to content

Commit 26d40e1

Browse files
committed
feat: titles appearance now resizes for better readability
parts of #3882 also fixed a display of titles in every appearance, especially on first display of the switcher ui
1 parent 15a55e6 commit 26d40e1

File tree

5 files changed

+55
-16
lines changed

5 files changed

+55
-16
lines changed

src/api-wrappers/HelperExtensions.swift

Lines changed: 0 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -193,15 +193,6 @@ extension DispatchQoS {
193193
}
194194
}
195195

196-
extension NSTextField {
197-
func setWidth(_ width: CGFloat) {
198-
frame.size.width = width
199-
// TODO: NSTextField does some internal magic, and ends up with constraints. We need to add our own to force its size
200-
// I wish there was a better way to only set the frame.size
201-
addOrUpdateConstraint(widthAnchor, width)
202-
}
203-
}
204-
205196
extension NSImage {
206197
func appIconFixedSize(_ size: NSSize) -> CGImage? {
207198
var rect = NSRect(origin: .zero, size: size)

src/logic/Appearance.swift

Lines changed: 1 addition & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -37,7 +37,7 @@ class Appearance {
3737
// derived
3838
static var font: NSFont {
3939
if #available(macOS 26.0, *) {
40-
return NSFont.systemFont(ofSize: fontHeight, weight: .semibold)
40+
return NSFont.systemFont(ofSize: fontHeight, weight: currentStyle == .appIcons ? .semibold : .medium)
4141
}
4242
return NSFont.systemFont(ofSize: fontHeight)
4343
}
@@ -155,7 +155,6 @@ class Appearance {
155155
windowCornerRadius = 23
156156
cellCornerRadius = 10
157157
edgeInsetsSize = 7
158-
maxWidthOnScreen = isHorizontalScreen ? 0.6 : 0.8
159158
windowMinWidthInRow = 0.6
160159
windowMaxWidthInRow = 0.9
161160
rowsCount = 1

src/ui/main-window/ThumbnailTitleView.swift

Lines changed: 15 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -5,6 +5,8 @@ class ThumbnailTitleView: NSTextField {
55
self.init(labelWithString: "")
66
self.font = font
77
textColor = Appearance.fontColor
8+
// drawsBackground = true
9+
// backgroundColor = .red
810
allowsDefaultTighteningForTruncation = false
911
translatesAutoresizingMaskIntoConstraints = false
1012
}
@@ -13,6 +15,19 @@ class ThumbnailTitleView: NSTextField {
1315
heightAnchor.constraint(equalToConstant: fittingSize.height).isActive = true
1416
}
1517

18+
func setWidth(_ width: CGFloat) {
19+
frame.size.width = width
20+
// TODO: NSTextField does some internal magic, and ends up with constraints.
21+
// we can't use addOrUpdateConstraint for some reason, otherwise it will only actually apply after the UI is shown twice
22+
// i tried everything and ended up removing all constraints then adding a fresh one. This seems to work
23+
let toRemove = constraints.filter {
24+
($0.firstItem as? NSView) === self && $0.firstAttribute == .width ||
25+
($0.secondItem as? NSView) === self && $0.secondAttribute == .width
26+
}
27+
toRemove.forEach { removeConstraint($0) }
28+
widthAnchor.constraint(equalToConstant: width).isActive = true
29+
}
30+
1631
override func mouseMoved(with event: NSEvent) {
1732
// no-op here prevents tooltips from disappearing on mouseMoved
1833
}

src/ui/main-window/ThumbnailView.swift

Lines changed: 28 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -2,6 +2,8 @@ import Cocoa
22

33
class ThumbnailView: FlippedView {
44
static let noOpenWindowToolTip = NSLocalizedString("App is running but has no open window", comment: "")
5+
// when calculating the width of a nstextfield, somehow we need to add this suffix to get the correct width
6+
static let extraTextForPadding = "lmnopqrstuvw"
57
var window_: Window?
68
var thumbnail = LightImageView()
79
var windowlessIcon = LightImageView()
@@ -276,20 +278,19 @@ class ThumbnailView: FlippedView {
276278
let availableRightWidth = view.isLastInRow ? 0 : CGFloat(view.numberOfViewsInRow - 1 - view.indexInRow) * viewWidth
277279
let totalWidth = availableLeftWidth + availableRightWidth + viewWidth
278280
let maxLabelWidth = min(totalWidth, maxAllowedWidth)
279-
return maxLabelWidth - Appearance.intraCellPadding * 4
281+
return maxLabelWidth - Appearance.intraCellPadding * 2
280282
}
281283

282284
private func updateAppIconsLabelFrame(_ view: ThumbnailView) {
283285
let viewWidth = view.frame.width
284-
let labelWidth = view.label.fittingSize.width
286+
let labelWidth = view.label.cell!.cellSize.width
285287
let maxAllowedLabelWidth = getMaxAllowedLabelWidth(view)
286288
let effectiveLabelWidth = max(min(labelWidth, maxAllowedLabelWidth), viewWidth)
287-
var leftOffset = CGFloat(0)
288-
var effectiveLabelWidth = max(min(labelWidth, maxAllowedLabelWidth), viewWidth)
289+
- (view.isFirstInRow && view.isLastInRow ? 4 : (view.isFirstInRow || view.isLastInRow ? 2 : 0)) * Appearance.intraCellPadding
289290
var leftOffset = -Appearance.intraCellPadding * 2
290291
if view.isFirstInRow && view.isLastInRow {
291292
leftOffset = -Appearance.intraCellPadding * 2
292-
effectiveLabelWidth -= Appearance.intraCellPadding * 4
293+
293294
} else if view.isLastInRow {
294295
leftOffset = max(0, effectiveLabelWidth - viewWidth + Appearance.intraCellPadding * 2)
295296
} else if !view.isFirstInRow && !view.isLastInRow {
@@ -547,6 +548,28 @@ class ThumbnailView: FlippedView {
547548
return ThumbnailsPanel.maxThumbnailsWidth() * Appearance.windowMaxWidthInRow - Appearance.interCellPadding * 2
548549
}
549550

551+
static func widthOfComfortableReadability() -> CGFloat? {
552+
let labTitleView = ThumbnailTitleView(font: Appearance.font)
553+
labTitleView.stringValue = "abcdefghijklmnopqrstuvwxyz-abcdefghijklmnopqrstuvwxyz-abcdefghijk" + extraTextForPadding
554+
Logger.error(labTitleView.font)
555+
return labTitleView.fittingSize.width
556+
}
557+
558+
static func widthOfLongestTitle() -> CGFloat? {
559+
let labTitleView = ThumbnailTitleView(font: Appearance.font)
560+
var maxWidth = CGFloat(0)
561+
for window in Windows.list {
562+
guard window.shouldShowTheUser else { continue }
563+
labTitleView.stringValue = window.title + extraTextForPadding
564+
let width = labTitleView.fittingSize.width
565+
if width > maxWidth {
566+
maxWidth = width
567+
}
568+
}
569+
guard maxWidth > 0 else { return nil }
570+
return maxWidth
571+
}
572+
550573
static func minThumbnailWidth() -> CGFloat {
551574
return ThumbnailsPanel.maxThumbnailsWidth() * Appearance.windowMinWidthInRow - Appearance.interCellPadding * 2
552575
}

src/ui/main-window/ThumbnailsPanel.swift

Lines changed: 11 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -61,6 +61,17 @@ class ThumbnailsPanel: NSPanel {
6161
}
6262

6363
static func maxThumbnailsWidth() -> CGFloat {
64+
if Preferences.appearanceStyle == .titles,
65+
let readableWidth = ThumbnailView.widthOfComfortableReadability(),
66+
let widthOfLongestTitle = ThumbnailView.widthOfLongestTitle() {
67+
return (
68+
min(
69+
NSScreen.preferred.frame.width * Appearance.maxWidthOnScreen,
70+
readableWidth + Appearance.intraCellPadding * 2 + Appearance.appIconLabelSpacing + Appearance.iconSize,
71+
widthOfLongestTitle + Appearance.intraCellPadding * 2 + Appearance.appIconLabelSpacing + Appearance.iconSize
72+
) - Appearance.windowPadding * 2
73+
).rounded()
74+
}
6475
return (NSScreen.preferred.frame.width * Appearance.maxWidthOnScreen - Appearance.windowPadding * 2).rounded()
6576
}
6677

0 commit comments

Comments
 (0)