我遇到这个问题已有一段时间了,在这里看了几十个答案,似乎找不到任何有用的东西。
我正在应用的iOS端生成QR码,并希望将此QR码发送到我当前正在开发的WatchKit扩展程序中。
func createQR(with string: String) {
if let filter = CIFilter(name: "CIQRCodeGenerator") {
//set the data to the contact data
filter.setValue(string, forKey: "inputMessage")
filter.setValue("L", forKey: "inputCorrectionLevel")
if let codeImage = filter.outputImage {
return UIImage(ciImage: codeImage);
}
}
}
我想从QR图像中获取数据,以便可以将其发送到Apple Watch应用,如下所示:
let data = UIImagePNGRepresentation(QRCodeImage);
但是,总是返回nil
,因为没有图像数据支持过滤器的输出。
注意:我知道没有与CI图像关联的数据,因为它尚未渲染,甚至没有与之关联的数据,因为它只是过滤器的输出。 我不知道该如何解决,因为我在图像处理等方面还很陌生。 :/
cgImage
创建一个filter.outputImage
func createQR(with string: String) {
if let filter = CIFilter(name: "CIQRCodeGenerator") {
//set the data to the contact data
filter.setValue(contactData, forKey: "inputMessage")
filter.setValue("L", forKey: "inputCorrectionLevel")
if let codeImage = filter.outputImage {
let context = CIContext(options: nil)
if let cgImage = context.createCGImage(codeImage, from: codeImage.extent) {
self.QRCode = UIImage(cgImage: cgImage)
}
}
}
}
但是这不起作用,似乎也没有,因为视图上的图像是空白的。
func update(with string: String) {
let blankCiImage = CIImage(color: .white) //This probably isn't right...
if let filter = CIFilter(name: "CIQRCodeGenerator") {
filter.setValue(contactData, forKey: "inputMessage")
filter.setValue("L", forKey: "inputCorrectionLevel")
filter.setValue(blankCiImage, forKey: kCIInputImageKey)
if let codeImage = filter.outputImage {
let context = CIContext(options: nil)
if let cgImage = context.createCGImage(codeImage, from: codeImage.extent) {
self.contactCode = UIImage(cgImage: cgImage)
print(self.contactCode!)
print(UIImagePNGRepresentation(self.contactCode!))
}
}
}
}
这也不起作用-我的想法是向其添加空白图像,然后在其上方进行过滤,但是我可能做得不好。
从字面上看,只是为了从生成的QR码中获取数据。大多数线程建议使用UIImage(ciImage: output)
,但这没有任何后备数据。
如果有人可以帮助我解决这个问题,那就太好了。并且任何有关其工作原理的解释都将很棒。
编辑:我不认为这与标记的重复项相同-标记的重复项是关于使用CI过滤器编辑现有图像并获取该数据,而这是关于仅通过CI过滤器创建,没有输入图像-QR码。另一个答案并不完全相关。
答案 0 :(得分:3)
您的代码中有几个问题。您需要先使用String Encoding isoLatin1将字符串转换为数据,然后再将其传递给过滤器。另一个问题是,要将CIImage转换为数据,您需要重绘/渲染CIImage并防止在缩放时模糊图像,您需要对图像进行变换以增加其大小:
extension String {
var qrCode: UIImage? {
guard
let data = data(using: .isoLatin1),
let filter = CIFilter(name: "CIQRCodeGenerator")
else { return nil }
filter.setValue(data, forKey: "inputMessage")
filter.setValue("M", forKey: "inputCorrectionLevel")
guard let image = filter.outputImage
else { return nil }
let size = image.extent.integral
let output = CGSize(width: 250, height: 250)
let matrix = CGAffineTransform(scaleX: output.width / size.width, y: output.height / size.height)
UIGraphicsBeginImageContextWithOptions(output, false, 0)
defer { UIGraphicsEndImageContext() }
UIImage(ciImage: image.transformed(by: matrix))
.draw(in: CGRect(origin: .zero, size: output))
return UIGraphicsGetImageFromCurrentImageContext()
}
}
游乐场测试:
let link = "https://stackoverflow.com/questions/51178573/swift-image-data-from-ciimage-qr-code-how-to-render-cifilter-output?noredirect=1"
let image = link.qrCode!
let data = image.jpegData(compressionQuality: 1) // 154785 bytes