如何手动创建动态(深色/浅色)NSImage实例?



似乎在macOS 10.14 Mojave中,创建自动绘制明暗版本的NSImage实例的唯一方法是通过资产目录和+[NSImage imageNamed:]。但是,我需要在运行时创建动态图像,并且似乎没有办法在不使用私有 API 的情况下做到这一点。

在引擎盖下,似乎已经向NSImageRep引入了私有财产_appearanceName以某种方式用于选择正确的表示。使用设置了相应_appearanceName的图像表示创建一个NSImage应该是直截了当的,但我想避免这种情况。

我找到了一个简单的解决方法(发布在下面(,但是当系统外观发生变化(即用户从浅色切换到深色,反之亦然(或在将appearance属性设置为不同外观的视图层次结构中使用时(例如,一个视图硬编码为深色模式,另一个视图硬编码为浅色模式(。

那么,如何手动创建正确显示浅色或深色版本的动态NSImage,就像资产目录图像一样?


@implementation NSImage (CustomDynamic)
+ (NSImage *)imageWithLight:(NSImage *)light dark:(NSImage *)dark
{
if (@available(macOS 10.14, *)) {
return [NSImage
imageWithSize:light.size
flipped:NO
drawingHandler:^(NSRect dstRect) {
if ([NSImage appearanceIsDarkMode:NSAppearance.currentAppearance]) {
[dark drawInRect:dstRect];
} else {
[light drawInRect:dstRect];
}
return YES;
}
];
} else {
return light;
}
}
+ (BOOL)appearanceIsDarkMode:(NSAppearance *)appearance
{
if (@available(macOS 10.14, *)) {
NSAppearanceName basicAppearance = [appearance bestMatchFromAppearancesWithNames:@[
NSAppearanceNameAqua,
NSAppearanceNameDarkAqua
]];
return [basicAppearance isEqualToString:NSAppearanceNameDarkAqua];
} else {
return NO;
}
}
@end

D'uh,事实证明问题中发布的代码工作得很好!实际上,绘图处理程序是在适当的时间调用的,并且确实处理所有外观情况。

但是,我有缩放和缓存这些图像的代码,并且它仍然使用古老的[image lockFocus]; … [image unlockFocus];绘制图像的方式,而不是使用+[NSImage imageWithSize:flipped:drawingHandler:]

最新更新