测试目标中从资源目录中获取NSImage

8

我的单元测试目标需要加载一张图片资源,以便在某些测试中使用,但我无法成功加载它。

  1. 我已经在测试目标中创建了一个资产目录(asset catalog)
  2. 我向目录中添加了一个新的图像集(image set)资源,勾选了“设备”下的“Mac”,并设置了两个分辨率(@1x 和 @2x)的源图像:

enter image description here

  1. 我检查了测试目标的“复制包资源”构建阶段,并确保其中包含了该资产目录。

  2. 我检查了资产目录和图像集的目标成员身份,确认它们确实是测试目标。


在运行测试时,我尝试使用以下代码加载图片:

guard let image = NSImage(named: NSImage.Name("TestSourceImage")) else {
    fatalError("Test Resource is Missing.")
}

...但是守卫失败了。

我还尝试了以下方法:

let bundle = Bundle(for: MyClassTests.self)

guard let path = bundle.pathForImageResource(NSImage.Name("TestSourceImage")) else {
    fatalError("Test Resource is Missing.")
}

guard let image = NSImage(contentsOfFile: path) else {
    fatalError("Test Resource File is Corrupt.")
}

...但第一个守卫失败了(无法检索资源路径)。

我已经尝试了两种格式。

NSImage.Name("TestSourceImage")

并且:

NSImage.Name(rawValue: "TestSourceImage")

我还尝试过使用Bundle.urlForImageResource(_),但它也失败了。
我看到了类似的问题和答案,但它们要么适用于iOS,要么适用于应用程序(主)包中的资源。
我错过了什么?
更新:
与此同时,我通过将我的测试图像作为独立的图像资源添加(不使用资产目录),并使用以下代码加载它来解决了这个问题。
let bundle = Bundle(for: MyClassTests.self)
guard let url = bundle.url(forResource: "TestSourceImage", withExtension: "png") else {
    fatalError("!!!")
}
guard let image = NSImage(contentsOf: url) else {
    fatalError("!!!")
}

在这种情况下,我不需要支持多个分辨率(我的图像是图像处理算法的源;它已经假定为必要的最高分辨率),即使我需要,我也只需从.png切换到.tiff

问题似乎在于,NSImage没有类似于UIImage的初始化程序init(named:in:compatibleWith:),该初始化程序允许您指定要从中加载图像的bundle(第二个参数)。

相反,您可以请求特定的bundle(而不是main)来创建资源URL并从中实例化图像(就像我上面所做的那样),但似乎这与资产目录不兼容。欢迎进一步的信息...

1个回答

9

Bundle有一个扩展,可以从资源目录中加载指定名称的图像:

extension Bundle {
    @available(OSX 10.7, *)
    open func image(forResource name: NSImage.Name) -> NSImage?
}

参考您的示例,您可以在 XCTestCase 中使用以下代码访问图像(Swift 5):

guard let image = Bundle(for: type(of: self)).image(forResource: "TestSourceImage") else {
    fatalError("Test Resource is Missing.")
}

在macOS 10.14上进行了测试。


谢谢,它有效!已经有一段时间了,我现在并没有在那个项目上工作(虽然它并没有完全被放弃),所以我不得不进行一些搜索来找到它并尝试您的解决方案 :-) - Nicolas Miari

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接