如何通过带有 Swift 的 UISlider 使用 CIColorControls 更改亮度、对比度和饱和度
How to change Brightness, Contrast and Saturation using CIColorControls via UISlider with Swift
我正在开发一个照片滤镜应用程序,如您所见,我添加了一项功能来调整对比度、亮度、饱和度和噪点。但问题是它们独立工作,这意味着当我开始编辑对比度时,我正在调整亮度,它 returns 到原始亮度。
这是我将亮度调到最大(图像变白)然后尝试调整其对比度并且滑块改变了原始图像的对比度时的预览。
在这里我能够捕捉到释放滑块并将其值放在原始图像上的时刻,正如你所看到的那样,在演示中我将饱和度设置为 0,然后将相同饱和度的对比度更改为0 张图片。
。
问题是,现在当我只单击滑块而不更改其值时,它会将当前值加倍。例如,如果我将亮度设置为 5,将饱和度设置为 10,并决定在单击亮度后立即调整亮度,它的值会加倍,我不知道为什么。
这是一个例子。我只是点击滑块而不改变它的值。
这是代码
@objc func sliderValueDidChange(_ sender: UISlider!) {
if sender.tag == 0 {
let displayinPercentage: Int = Int((sender.value/200) * 10000)
brightnessValueLabel.text = ("\(displayinPercentage)")
selectedPictureImageView.image = originalImage
let beginImage = CIImage(image: selectedPictureImageView.image!)
self.filter = CIFilter(name: "CIColorControls")
self.filter?.setValue(beginImage, forKey: kCIInputImageKey)
self.filter.setValue(sender.value, forKey: kCIInputBrightnessKey)
self.filteredImage = self.filter?.outputImage
selectedPictureImageView.image = UIImage(cgImage: self.context.createCGImage(self.filteredImage!, from: (self.filteredImage?.extent)!)!)
sliderValue = sender.value
} else if sender.tag == 1 {
let displayinPercentage: Int = Int((sender.value/200) * 10000)
contrastValueLabel.text = ("\(displayinPercentage)")
self.selectedPictureImageView.image = originalImage
let beginImage = CIImage(image: self.selectedPictureImageView.image!)
self.filter = CIFilter(name: "CIColorControls")
self.filter?.setValue(beginImage, forKey: kCIInputImageKey)
self.filter.setValue(sender.value, forKey: kCIInputContrastKey)
self.filteredImage = self.filter?.outputImage
self.selectedPictureImageView.image = UIImage(cgImage: self.context.createCGImage(self.filteredImage!, from: (self.filteredImage?.extent)!)!)
sliderValue = sender.value
} else if sender.tag == 2 {
let displayinPercentage: Int = Int((sender.value/200) * 10000)
saturationValueLabel.text = ("\(displayinPercentage)")
self.selectedPictureImageView.image = originalImage
let beginImage = CIImage(image: self.selectedPictureImageView.image!)
self.filter = CIFilter(name: "CIColorControls")
self.filter?.setValue(beginImage, forKey: kCIInputImageKey)
self.filter.setValue(sender.value, forKey: kCIInputSaturationKey)
self.filteredImage = self.filter?.outputImage
self.selectedPictureImageView.image = UIImage(cgImage: self.context.createCGImage(self.filteredImage!, from: (self.filteredImage?.extent)!)!)
sliderValue = sender.value
} else if sender.tag == 3 {
let displayinPercentage: Int = Int((sender.value/200) * 10000)
sharpenValueLabel.text = ("\(displayinPercentage)")
self.selectedPictureImageView.image = originalImage
let beginImage = CIImage(image: self.selectedPictureImageView.image!)
self.filter = CIFilter(name: "CIUnsharpMask")
self.filter?.setValue(beginImage, forKey: kCIInputImageKey)
self.filter.setValue(7, forKey: kCIInputRadiusKey)
self.filter.setValue(sender.value, forKey: kCIInputIntensityKey)
self.filteredImage = self.filter?.outputImage
self.selectedPictureImageView.image = UIImage(cgImage: self.context.createCGImage(self.filteredImage!, from: (self.filteredImage?.extent)!)!)
sliderValue = sender.value
}
}
@objc func sliderValueDidEnd(_ sender: UISlider!) {
if sender.tag == 0 {
originalImage = selectedPictureImageView.image
sender.value = sliderValue
print("Unpressed button slider value is \(sender.value)")
} else if sender.tag == 1 {
originalImage = selectedPictureImageView.image
sender.value = sliderValue
print("Unpressed button slider value is \(sender.value)")
} else if sender.tag == 2 {
originalImage = selectedPictureImageView.image
sender.value = sliderValue
print("Unpressed button slider value is \(sender.value)")
} else if sender.tag == 3 {
originalImage = selectedPictureImageView.image
sender.value = sliderValue
print("Unpressed button slider value is \(sender.value)")
}
}
我认为一切正常,我只是对过滤器值进行了错误的计算。
您的问题是,每次滑动滑块时,您都会将滤镜应用于前一个滤镜的结果图像,而不是将其应用于原始图像。顺便说一句,如果您在用户完成后创建一个 CGImage,则在滑动 UISlider 时可以使您的过滤器响应更快。您的代码应如下所示:
let displayinPercentage = Int((sender.value/200) * 10000)
brightnessValueLabel.text = String(displayinPercentage)
let beginImage = CIImage(image: originalImage)
filter.setValue(beginImage, forKey: kCIInputImageKey)
filter.setValue(sender.value, forKey: kCIInputBrightnessKey)
if let ciimage = filter.outputImage {
filteredImage = ciimage
selectedPictureImageView.image = UIImage(ciImage: filteredImage)
}
我正在开发一个照片滤镜应用程序,如您所见,我添加了一项功能来调整对比度、亮度、饱和度和噪点。但问题是它们独立工作,这意味着当我开始编辑对比度时,我正在调整亮度,它 returns 到原始亮度。
这是我将亮度调到最大(图像变白)然后尝试调整其对比度并且滑块改变了原始图像的对比度时的预览。
在这里我能够捕捉到释放滑块并将其值放在原始图像上的时刻,正如你所看到的那样,在演示中我将饱和度设置为 0,然后将相同饱和度的对比度更改为0 张图片。
问题是,现在当我只单击滑块而不更改其值时,它会将当前值加倍。例如,如果我将亮度设置为 5,将饱和度设置为 10,并决定在单击亮度后立即调整亮度,它的值会加倍,我不知道为什么。 这是一个例子。我只是点击滑块而不改变它的值。
这是代码
@objc func sliderValueDidChange(_ sender: UISlider!) {
if sender.tag == 0 {
let displayinPercentage: Int = Int((sender.value/200) * 10000)
brightnessValueLabel.text = ("\(displayinPercentage)")
selectedPictureImageView.image = originalImage
let beginImage = CIImage(image: selectedPictureImageView.image!)
self.filter = CIFilter(name: "CIColorControls")
self.filter?.setValue(beginImage, forKey: kCIInputImageKey)
self.filter.setValue(sender.value, forKey: kCIInputBrightnessKey)
self.filteredImage = self.filter?.outputImage
selectedPictureImageView.image = UIImage(cgImage: self.context.createCGImage(self.filteredImage!, from: (self.filteredImage?.extent)!)!)
sliderValue = sender.value
} else if sender.tag == 1 {
let displayinPercentage: Int = Int((sender.value/200) * 10000)
contrastValueLabel.text = ("\(displayinPercentage)")
self.selectedPictureImageView.image = originalImage
let beginImage = CIImage(image: self.selectedPictureImageView.image!)
self.filter = CIFilter(name: "CIColorControls")
self.filter?.setValue(beginImage, forKey: kCIInputImageKey)
self.filter.setValue(sender.value, forKey: kCIInputContrastKey)
self.filteredImage = self.filter?.outputImage
self.selectedPictureImageView.image = UIImage(cgImage: self.context.createCGImage(self.filteredImage!, from: (self.filteredImage?.extent)!)!)
sliderValue = sender.value
} else if sender.tag == 2 {
let displayinPercentage: Int = Int((sender.value/200) * 10000)
saturationValueLabel.text = ("\(displayinPercentage)")
self.selectedPictureImageView.image = originalImage
let beginImage = CIImage(image: self.selectedPictureImageView.image!)
self.filter = CIFilter(name: "CIColorControls")
self.filter?.setValue(beginImage, forKey: kCIInputImageKey)
self.filter.setValue(sender.value, forKey: kCIInputSaturationKey)
self.filteredImage = self.filter?.outputImage
self.selectedPictureImageView.image = UIImage(cgImage: self.context.createCGImage(self.filteredImage!, from: (self.filteredImage?.extent)!)!)
sliderValue = sender.value
} else if sender.tag == 3 {
let displayinPercentage: Int = Int((sender.value/200) * 10000)
sharpenValueLabel.text = ("\(displayinPercentage)")
self.selectedPictureImageView.image = originalImage
let beginImage = CIImage(image: self.selectedPictureImageView.image!)
self.filter = CIFilter(name: "CIUnsharpMask")
self.filter?.setValue(beginImage, forKey: kCIInputImageKey)
self.filter.setValue(7, forKey: kCIInputRadiusKey)
self.filter.setValue(sender.value, forKey: kCIInputIntensityKey)
self.filteredImage = self.filter?.outputImage
self.selectedPictureImageView.image = UIImage(cgImage: self.context.createCGImage(self.filteredImage!, from: (self.filteredImage?.extent)!)!)
sliderValue = sender.value
}
}
@objc func sliderValueDidEnd(_ sender: UISlider!) {
if sender.tag == 0 {
originalImage = selectedPictureImageView.image
sender.value = sliderValue
print("Unpressed button slider value is \(sender.value)")
} else if sender.tag == 1 {
originalImage = selectedPictureImageView.image
sender.value = sliderValue
print("Unpressed button slider value is \(sender.value)")
} else if sender.tag == 2 {
originalImage = selectedPictureImageView.image
sender.value = sliderValue
print("Unpressed button slider value is \(sender.value)")
} else if sender.tag == 3 {
originalImage = selectedPictureImageView.image
sender.value = sliderValue
print("Unpressed button slider value is \(sender.value)")
}
}
我认为一切正常,我只是对过滤器值进行了错误的计算。
您的问题是,每次滑动滑块时,您都会将滤镜应用于前一个滤镜的结果图像,而不是将其应用于原始图像。顺便说一句,如果您在用户完成后创建一个 CGImage,则在滑动 UISlider 时可以使您的过滤器响应更快。您的代码应如下所示:
let displayinPercentage = Int((sender.value/200) * 10000)
brightnessValueLabel.text = String(displayinPercentage)
let beginImage = CIImage(image: originalImage)
filter.setValue(beginImage, forKey: kCIInputImageKey)
filter.setValue(sender.value, forKey: kCIInputBrightnessKey)
if let ciimage = filter.outputImage {
filteredImage = ciimage
selectedPictureImageView.image = UIImage(ciImage: filteredImage)
}