While the image selected from the camera roll is depicted in imageView, the function of filtering sepia or black and white by tapping the button is implemented.
In addition, we would like to implement a feature that allows users to drag the UISlider from side to side to select sepia or black and white shades.
I did coding on my own, but I don't know where to go.
import UIKit
classViewController:UIViewController, UINavigationControllerDelegate, UIImagePickerControllerDelegate{
@IBOutlet varmainImageView: UIImageView!
@ IBAction func pickImageFromLibrary(){
if UIImagePickerController.isSourceTypeAvailable (.PhotoLibrary) {
let controller = UIImagePickerController()
controller.delegate=self
controller.sourceType=UIImagePickerControllerSourceType.PhotoLibrary
self.presentViewController(controller, animated:true, completion:nil)
}
}
override func viewDidLoad(){
super.viewDidLoad()
let slider = UISlider()
slider.frame = CGRect (x:80, y:380, width:200, height:40)
slider.minimumValue = 0.0
slider.maximumValue=1.0
slider.addTarget(self, action: "sepiaFilter:", forControlEvents:UICControlEvents.ValueChanged)
slider.addTarget(self, action: "monoFilter:", forControlEvents:UICControlEvents.ValueChanged)
self.view.addSubview(slider)
}
funcimagePickerController(picker:UIImagePickerController,
DidFinishPickingImage: UIImage, editingInfo: String: AnyObject?) {
self.mainImageView.image=image
(self.view.viewWithTag(1)as!UIButton).setImage(image, forState:.Normal)
(self.view.viewWithTag(2)as!UIButton).setImage(sepiaFilter(image, slider:UISlider())), forState:.Normal)
(self.view.viewWithTag(3) as!UIButton).setImage(monoFilter(image, slider:UISlider())), forState:.Normal)
picker.dismissViewControllerAnimated(true, completion:nil)
}
func sepiaFilter (image:UIImage, slider:UISlider) - > UIImage {
let sepiaFilter=CIFilter(name: "CISepiaTone")
sepiaFilter!.setDefaults()
let ciImage: CIIimage= CIIimage(image:image)!
sepiaFilter!.setValue(ciImage, forKey:kCIInputImageKey)
sepiaFilter!.setValue(slider.value, forKey: "inputIntensity")
iflet outputImage=sepiaFilter!.valueForKey("outputImage") as? CIIimage{
let managedImage = UIImage (CIImage: outputImage)
self.mainImageView.image=manipulatedImage
}
return mainImageView.image!
}
funcmonoFilter (image:UIImage, slider:UISlider) - > UIImage {
letmonoFilter=CIFilter(name: "CIColorControls")
US>monoFilter!.setDefaults()
letciImage=CIImage(image:image)!
monoFilter!.setValue(ciImage, forKey:kCIInputImageKey)
monoFilter!.setValue(slider.value, forKey: "inputSaturation")
iflet outputImage=monoFilter!.valueForKey("outputImage") as? CIIimage{
let managedImage = UIImage (CIImage: outputImage)
self.mainImageView.image=manipulatedImage
}
return mainImageView.image!
}
@ IBAction func filterTapped (sender: UIButton) {
switch sender.tag {
case1:
mainImageView.image=(self.view.viewWithTag(1)as!UIButton).imageView?.image
case2:
mainImageView.image=(self.view.viewWithTag(2)as!UIButton).imageView?.image
default:
break
}
}
}
If you test the actual machine with the code above, you will get an error when you drag the UISlider.
(No error mark before build)
Action: "sepiaFilter:" and "monoFilter:"
in parentheses of addTarget() when creating UISlider
I think it's an error because of the mix of
What kind of grammatical description should I use to correct it?
追Additional
Sorry for the insufficient explanation.
The contents of the debug area are as follows.
(Edit note) sepiaFilter
, monoFilter
was used for both the function for the filter and the action method, but I didn't notice and recommended an inappropriate method, so I fixed it.
This is the most important error message you quoted.
[_picFilter_2016_0725.ViewController sepiaFilter:]:unrecognized selector sent to instance 0x1553f930'
This says that an unrecognized selector called sepiaFilter:
was sent to an instance of the ViewController
class."Selector" is an Objective-C term, which is an essential concept for iOS programming, so you may understand a little bit, but the bottom line is that ""ViewController
class does not define a method for sepiaFilter:
.""
Your class includes
func sepiaFilter (image:UIImage, slider:UISlider) - > UIImage{
//...
return mainImageView.image!
}
There is a method called sepiaFilter:slider:
in this method (in the Objective-C expression).(Swift3 will be different from Swift2)
If you simply describe a selector called sepiaFilter:
, it has only one argument,
func sepiaFilter (param:SomeParamType) - >SomeReturnType{
//...
returnReturnTypeObject
}
You have specified a method of type called .
(Objective-C selector does not matter if there is a return value, parameters or type of return value, but the target-action method described later should not return the return value.)
"I was told to call the sepiaFilter:
method when an event occurs, but you don't have that method!!!" So what can I do?
(1) action: Specify the correct selector for methods that already exist in the
argument.
(2) action:Define the method specified by the
argument
(3) action: Modify the existing method to match the form specified by the
argument
(4) action:
Modify the argument specification and define the method
For iOS UIControl
(UISlider
is another type), the method that can be specified in target-action must be one of the following forms:
Listing 1 Swift
@IBAction func doSomething()
@ IBAction func doSomething (sender: UIButton)
@ IBAction func doSomething (sender: UIButton, forEvent:UIEvent)
(The return value is not omitted, but no return value is specified.)
The second of these methods is one argument that matches your specified selector sepiaFilter:
, but your sepiaFilter(_:slider:)
method is also used as a filter function, so you cannot modify it to match the above form.
Therefore, the above (2) correspondence in the form of is required to add the action method separately from the filter function.
@IBAction func sepiaFilter(sender:UISlider){
guard let image=self.mainImageView.imageelse{
fatalError("something is wrong with mainImageView...")
}
self.mainImageView.image=sepiaFilter(image, slider:sender)
}
func sepiaFilter (image:UIImage, slider:UISlider) - > UIImage {
guardlet sepiaFilter=CIFilter(name: "CISepiaTone") else {
fatalError("something is wrong with CIFilter...")
}
sepiaFilter.setDefaults()
guard let ciImage: CIIimage= CIIimage(image:image) else {
print("cannot create CIIimage...")
return image
}
sepiaFilter.setValue(ciImage, forKey:kCIInputImageKey)
sepiaFilter.setValue(slider.value, forKey: "inputIntensity")
iflet outputImage=sepiaFilter.valueForKey("outputImage") as? CIIimage{
let managedImage = UIImage (CIImage: outputImage)
return managedImage// Filter function returns modified image as return value without changing mainImageView
}
return image
}
*You should not use Crash Me operator !
as much as possible, and you should not change it to mainImageView
for button image filtering, so I have modified the filter function a little.Also, @IBAction
is not required for addTarget
in the program, but it can be clearly distinguished from the filter function side, so I will leave it as it is.
Naturally, if you don't make the same correction to monoFilter:
, which was in almost the same condition, you will end up with a runtime error.
As the sentence has become quite long, I will put the subject of this question here to resolve the error you indicated in the postscript.
© 2024 OneMinuteCode. All rights reserved.