diff options
| author | Ruben Beltran del Rio <ruben@unlimited.pizza> | 2023-02-11 13:37:20 +0100 |
|---|---|---|
| committer | Ruben Beltran del Rio <ruben@unlimited.pizza> | 2023-02-11 13:37:20 +0100 |
| commit | 768e492ea13d8c0f62e0334c4c626db4596a66d8 (patch) | |
| tree | a6027ff28e371f90bfb1d22c576dbd36dd0a632d /Flat Bezel | |
| parent | 285ac7c2364f90a6bfc7853e25ec7f592d2009bc (diff) | |
Port more files to swift
Diffstat (limited to 'Flat Bezel')
| -rw-r--r-- | Flat Bezel/BBFlatBezelInterface.xib | 6 | ||||
| -rw-r--r-- | Flat Bezel/BBObjectCell.h | 4 | ||||
| -rw-r--r-- | Flat Bezel/BBObjectCell.m (renamed from Flat Bezel/BBSearchObjectView.m) | 43 | ||||
| -rw-r--r-- | Flat Bezel/BBSearchObjectView.h | 10 | ||||
| -rw-r--r-- | Flat Bezel/BackgroundView.swift | 12 | ||||
| -rw-r--r-- | Flat Bezel/FlatBezel-Bridging-Header.h | 2 | ||||
| -rw-r--r-- | Flat Bezel/FlatBezelCollectingSearchObjectView.swift | 38 | ||||
| -rw-r--r-- | Flat Bezel/FlatBezelObjectCell.swift | 164 | ||||
| -rw-r--r-- | Flat Bezel/FlatBezelSearchObjectView.swift | 6 |
9 files changed, 219 insertions, 66 deletions
diff --git a/Flat Bezel/BBFlatBezelInterface.xib b/Flat Bezel/BBFlatBezelInterface.xib index b3039c6..b6fd59e 100644 --- a/Flat Bezel/BBFlatBezelInterface.xib +++ b/Flat Bezel/BBFlatBezelInterface.xib @@ -28,7 +28,7 @@ <rect key="frame" x="0.0" y="0.0" width="608" height="200"/> <autoresizingMask key="autoresizingMask" widthSizable="YES" heightSizable="YES"/> <subviews> - <customView translatesAutoresizingMaskIntoConstraints="NO" id="68" customClass="BBCollectingSearchObjectView"> + <customView translatesAutoresizingMaskIntoConstraints="NO" id="68" customClass="FlatBezelCollectingSearchObjectView" customModule="Flat_Bezel" customModuleProvider="target"> <rect key="frame" x="8" y="8" width="184" height="184"/> <constraints> <constraint firstAttribute="height" constant="184" id="SwQ-fC-3aw"/> @@ -38,7 +38,7 @@ <outlet property="nextKeyView" destination="69" id="105"/> </connections> </customView> - <customView translatesAutoresizingMaskIntoConstraints="NO" id="69" customClass="BBSearchObjectView"> + <customView translatesAutoresizingMaskIntoConstraints="NO" id="69" customClass="FlatBezelSearchObjectView" customModule="Flat_Bezel" customModuleProvider="target"> <rect key="frame" x="200" y="8" width="184" height="184"/> <constraints> <constraint firstAttribute="width" constant="184" id="O3w-M3-b05"/> @@ -48,7 +48,7 @@ <outlet property="nextKeyView" destination="70" id="106"/> </connections> </customView> - <customView translatesAutoresizingMaskIntoConstraints="NO" id="70" customClass="BBCollectingSearchObjectView"> + <customView translatesAutoresizingMaskIntoConstraints="NO" id="70" customClass="FlatBezelCollectingSearchObjectView" customModule="Flat_Bezel" customModuleProvider="target"> <rect key="frame" x="392" y="8" width="184" height="184"/> <constraints> <constraint firstAttribute="width" constant="184" id="Jbn-VW-sSJ"/> diff --git a/Flat Bezel/BBObjectCell.h b/Flat Bezel/BBObjectCell.h new file mode 100644 index 0000000..3fa67c6 --- /dev/null +++ b/Flat Bezel/BBObjectCell.h @@ -0,0 +1,4 @@ +#import <QSInterface/QSInterface.h> + +@interface BBObjectCell : QSObjectCell +@end diff --git a/Flat Bezel/BBSearchObjectView.m b/Flat Bezel/BBObjectCell.m index 0722e0c..28e79d2 100644 --- a/Flat Bezel/BBSearchObjectView.m +++ b/Flat Bezel/BBObjectCell.m @@ -1,45 +1,4 @@ -#import "BBSearchObjectView.h" - -@implementation BBSearchObjectView -+ (Class)cellClass { return [BBObjectCell class]; } - -@end - -@implementation BBCollectingSearchObjectView -+ (Class)cellClass { return [BBObjectCell class]; } - -- (void)drawRect:(NSRect)rect { - NSRect frame = [self frame]; - NSInteger count = [collection count]; - if (![self currentEditor] && count) { - frame.origin = NSZeroPoint; - [[self cell] drawWithFrame:frame inView:self]; - NSInteger i; - CGFloat iconSize = collectionSpace?collectionSpace:16; - CGFloat opacity = collecting?1.0:0.75; - QSObject *object; - CGFloat totalWidth = iconSize + 2; - for (i = 0; i<count; i++) { - object = [collection objectAtIndex:i]; - NSImage *icon = [object icon]; - [icon setSize:QSSize16]; - [icon drawInRect:NSMakeRect(frame.size.width-totalWidth*(count-i), frame.origin.y+2, iconSize, iconSize) fromRect:rectFromSize([icon size]) operation:NSCompositingOperationSourceOver fraction:opacity]; - } - } else { - [super drawRect:rect]; - } -} - -- (NSRect)textEditorFrame { - NSRect titleFrame = [self frame]; - NSRect editorFrame = NSInsetRect(titleFrame, 8, 8); - editorFrame.origin = NSMakePoint(8, 8); - editorFrame = NSIntegralRect(editorFrame); - return editorFrame; -} - - -@end +#import "BBObjectCell.h" @implementation BBObjectCell diff --git a/Flat Bezel/BBSearchObjectView.h b/Flat Bezel/BBSearchObjectView.h deleted file mode 100644 index b60a637..0000000 --- a/Flat Bezel/BBSearchObjectView.h +++ /dev/null @@ -1,10 +0,0 @@ -#import <QSInterface/QSInterface.h> - -@interface BBSearchObjectView : QSSearchObjectView -@end - -@interface BBCollectingSearchObjectView : QSCollectingSearchObjectView -@end - -@interface BBObjectCell : QSObjectCell -@end diff --git a/Flat Bezel/BackgroundView.swift b/Flat Bezel/BackgroundView.swift index 041874a..7890798 100644 --- a/Flat Bezel/BackgroundView.swift +++ b/Flat Bezel/BackgroundView.swift @@ -1,24 +1,16 @@ -// -// BBBackgroundView.swift -// Flat Bezel -// -// Created by Ruben Beltran del Rio on 2/8/23. -// Copyright © 2023 BRNBW. All rights reserved. -// - import Foundation import Cocoa class BackgroundView: QSBezelBackgroundView { override func draw(_ rect: NSRect) { - let boundsRect = self.bounds + let boundsRect = bounds let roundRect = NSBezierPath() roundRect.appendRoundedRect(boundsRect, xRadius: 8.0, yRadius: 8.0) roundRect.addClip() - let darkMode = self.effectiveAppearance.name == .darkAqua + let darkMode = effectiveAppearance.name == .darkAqua if (darkMode) { NSColor(red: 0.1, green: 0.1, blue: 0.1, alpha: 0.99).setFill() } else { diff --git a/Flat Bezel/FlatBezel-Bridging-Header.h b/Flat Bezel/FlatBezel-Bridging-Header.h index f41b12c..f216cf4 100644 --- a/Flat Bezel/FlatBezel-Bridging-Header.h +++ b/Flat Bezel/FlatBezel-Bridging-Header.h @@ -1,2 +1,2 @@ #import "Quicksilver.pch" -#import "BBSearchObjectView.h" +#import "BBObjectCell.h" diff --git a/Flat Bezel/FlatBezelCollectingSearchObjectView.swift b/Flat Bezel/FlatBezelCollectingSearchObjectView.swift new file mode 100644 index 0000000..26586be --- /dev/null +++ b/Flat Bezel/FlatBezelCollectingSearchObjectView.swift @@ -0,0 +1,38 @@ +class FlatBezelCollectingSearchObjectView: QSCollectingSearchObjectView { + override static var cellClass : AnyClass? { + get { return BBObjectCell.self } + set { super.cellClass = newValue } + } + + override func draw(_ rect: NSRect) { + var frame = frame + + // These properties aren't available to Swift, so they need to be accessed in this way. + let collection = (value(forKey: "collection") as! NSMutableArray) + let collecting = (value(forKey: "collecting") as! Bool) + + let count = collection.count + if self.currentEditor() == nil && count != 0 { + frame.origin = NSZeroPoint + cell?.draw(withFrame: frame, in: self) + let iconSize = collectionSpace() != 0 ? collectionSpace() : 16 + let opacity = collecting ? 1.0 : 0.75 + let totalWidth = iconSize + 2 + for i in 0..<count { + let object = collection.object(at: i) as! QSObject + var icon = object.icon() + let size = NSMakeSize(16, 16) + icon?.size = size + let inRect = NSMakeRect( + frame.size.width - totalWidth * CGFloat(count - i), + frame.origin.y + 2, + iconSize, + iconSize + ) + icon?.draw(in: inRect, from: rectFromSize(size), operation: .sourceOver, fraction: opacity) + } + } else { + super.draw(rect) + } + } +} diff --git a/Flat Bezel/FlatBezelObjectCell.swift b/Flat Bezel/FlatBezelObjectCell.swift new file mode 100644 index 0000000..da38a1b --- /dev/null +++ b/Flat Bezel/FlatBezelObjectCell.swift @@ -0,0 +1,164 @@ +/* +import Foundation + +class FlatBezelObjectCell: QSObjectCell { + override func preferredImagePosition() -> NSControl.ImagePosition { + return .imageAbove + } + + override func draw(withFrame cellFrame: NSRect, in controlView: NSView?) { + if let controlView { + + let isFirstResponder = controlView.window?.firstResponder == controlView && !(controlView is NSTableView) + let dropTarget = isHighlighted && ((highlightsBy.rawValue & NSCell.StyleMask.changeBackgroundCellMask.rawValue) != 0) && !isBezeled + + var fillColor: NSColor? + let strokeColor = NSColor.clear + + if isFirstResponder { + fillColor = self.highlightColor() + } else { + fillColor = self.backgroundColor + } + + if dropTarget { + fillColor = NSColor(red: 0.77, green: 0.91, blue: 0.96, alpha: 1) + } + + fillColor?.setFill() + strokeColor.setStroke() + + let roundRect = NSBezierPath() + roundRect.append(withRoundedRectangle: cellFrame, withRadius: cellRadiusFactor()) + roundRect.fill() + + drawInterior(withFrame: drawingRect(forBounds: cellFrame), in: controlView) + } + } + + override func titleRect(forBounds _rect: NSRect) -> NSRect { + var rect = _rect + rect = NSOffsetRect(rect, 0, -4) + return super.titleRect(forBounds: rect) + } + + override func drawText(for drawObject: QSObject!, withFrame cellFrame: NSRect, in controlView: NSView!) { + if imagePosition == .imageOnly { + return + } + + var abbrString: String? = nil + + if controlView.responds(to: #selector(QSSearchObjectView.matchedString)) { + abbrString = (controlView as! QSSearchObjectView).matchedString() + } + + var nameString: String? = nil + var hitMask: NSIndexSet? = nil + + let ranker = drawObject.ranker() + if ranker != nil && abbrString != nil { + nameString = ranker?.matchedString(forAbbreviation: abbrString, hitmask: &hitMask, inContext: nil) + } + + if (nameString == nil) { + nameString = drawObject.displayName() + } + + let rankedStringIsName = nameString == drawObject.displayName() || nameString == nil + + if nameString == nil { + nameString = drawObject.identifier() ?? "Unknown" + } + + let useAlternateColor = controlView is NSTableView && (controlView as! NSTableView).isRowSelected((controlView as! NSTableView).row(at: cellFrame.origin)) + let mainColor = textColor() ?? (useAlternateColor ? .alternateSelectedControlTextColor : .controlTextColor) + let fadedColor = mainColor.withAlphaComponent(0.50) + let textDrawRect = titleRect(forBounds: cellFrame) + + + let titleString = NSMutableAttributedString(string: nameString!) + let nameAttributes = (value(forKey: "nameAttributes") as? [NSAttributedString.Key : Any]) + let detailsAttributes = (value(forKey: "detailsAttributes") as? [NSAttributedString.Key : Any]) + titleString.setAttributes(rankedStringIsName ? nameAttributes : detailsAttributes, range: NSMakeRange(0, titleString.length)) + + if abbrString != nil && abbrString!.hasPrefix("QSActionMnemonic") { + titleString.addAttribute(.foregroundColor, value: rankedStringIsName ? fadedColor : fadedColor.withAlphaComponent(0.8), range: NSMakeRange(0, titleString.length)) + + var hits: Int = 0 + let count = hitMask?.getIndexes(&hits, maxCount: titleString.length, inIndexRange: nil) + for i in 0..<(count ?? 0) { + for j in 1.. { + } + } + } +} + + NSUInteger i = 0; + NSUInteger j = 0; + NSUInteger hits[[titleString length]]; + NSUInteger count = [hitMask getIndexes:(NSUInteger *)&hits maxCount:[titleString length] inIndexRange:nil]; + NSDictionary *attributes = @{ + NSForegroundColorAttributeName: rankedStringIsName ? mainColor : fadedColor + }; + for(i = 0; i<count; i += j) { + for (j = 1; i+j<count && hits[i+j-1] +1 == hits[i+j]; j++); + [titleString addAttributes:attributes range:NSMakeRange(hits[i], j)]; + } + } else { + [titleString addAttribute:NSBaselineOffsetAttributeName value:[NSNumber numberWithDouble:-1.0] range:NSMakeRange(0, [titleString length])]; + } + + if (showDetails) { + NSString *detailsString = [drawObject details]; + + NSRange returnRange = [detailsString rangeOfString:@"\n"]; + if (returnRange.location != NSNotFound) { + detailsString = [detailsString substringToIndex:returnRange.location]; + } + + detailsAttributes = [detailsAttributes mutableCopy]; + [detailsAttributes setValue:[NSColor grayColor] forKey:NSForegroundColorAttributeName]; + + if (detailsString && detailsString.length && ![detailsString isEqualToString:nameString]) { + [titleString appendAttributedString:[[[NSAttributedString alloc] initWithString:[NSString stringWithFormat:@"\n%@",detailsString] attributes:detailsAttributes] autorelease]]; + } + } + + NSRect centerRect = rectFromSize([titleString size]); + centerRect.size.width = NSWidth(textDrawRect); + centerRect.size.height = MIN(NSHeight(textDrawRect), centerRect.size.height); + [titleString drawInRect:centerRectInRect(centerRect, textDrawRect)]; +} + +- (void)drawSearchPlaceholderWithFrame:(NSRect)cellFrame inView:(NSView *)controlView { + NSString *defaultText = NSLocalizedStringWithDefaultValue(@"Type to search", nil, [NSBundle mainBundle], @"Type to search", @"Hint that appears in the first pane of the QS interface when it's empty."); + NSSize textSize = [defaultText sizeWithAttributes:nameAttributes]; + NSRect textRect = centerRectInRect(rectFromSize(textSize), cellFrame); + BOOL isFirstResponder = [[controlView window] firstResponder] == controlView && ![controlView isKindOfClass:[NSTableView class]]; + + if (isFirstResponder && [controlView isKindOfClass:[QSSearchObjectView class]]) { + NSImage *find = [NSImage imageWithSystemSymbolName:@"magnifyingglass.circle.fill" accessibilityDescription:nil]; + + + [find setSize:QSSize16]; + NSRect findImageRect = expelRectFromRectOnEdge(centerRectInRect(rectFromSize([find size]), cellFrame), textRect, NSRectEdgeMinX, -2); + + + NSGraphicsContext *graphicsContext = [NSGraphicsContext currentContext]; + [graphicsContext saveGraphicsState]; + CGContextRef context = [graphicsContext CGContext]; + CGContextBeginTransparencyLayerWithRect(context, findImageRect, nil); + CGContextSetBlendMode(context, kCGBlendModeNormal); + [find drawInRect:findImageRect fromRect:rectFromSize([find size]) operation:NSCompositingOperationSourceOver fraction:1]; + CGContextSetBlendMode(context, kCGBlendModeSourceIn); + CGContextSetFillColorWithColor(context, [[NSColor textColor] CGColor]); + CGContextFillRect(context, findImageRect); + CGContextEndTransparencyLayer(context); + + [defaultText drawInRect:textRect withAttributes:nameAttributes]; + } +} + +@end +*/ diff --git a/Flat Bezel/FlatBezelSearchObjectView.swift b/Flat Bezel/FlatBezelSearchObjectView.swift new file mode 100644 index 0000000..902bede --- /dev/null +++ b/Flat Bezel/FlatBezelSearchObjectView.swift @@ -0,0 +1,6 @@ +class FlatBezelSearchObjectView: QSSearchObjectView { + override static var cellClass : AnyClass? { + get { return BBObjectCell.self } + set { super.cellClass = newValue } + } +} |