Why am I getting unrecognized selector sent to class?
Asked Answered
H

4

11

I have been going through all stack overflow trying to solve this but none of the solutions work.

class ToastView: UIView {

    static func showInParent(parentView: UIView!, withText text: String, forDuration duration: double_t) {

        //Count toast views are already showing on parent. Made to show several toasts one above another
        var toastsAlreadyInParent = 0;

        for view in parentView.subviews {
            if (view.isKindOfClass(ToastView)) {
                toastsAlreadyInParent++
            }
        }

        var parentFrame = parentView.frame;

        var yOrigin = parentFrame.size.height - getDouble(toastsAlreadyInParent)

        var selfFrame = CGRectMake(parentFrame.origin.x + 20.0, yOrigin, parentFrame.size.width - 40.0, toastHeight);
        var toast = ToastView(frame: selfFrame)

        toast.textLabel.backgroundColor = UIColor.clearColor()
        toast.textLabel.textAlignment = NSTextAlignment.Center
        toast.textLabel.textColor = UIColor.whiteColor()
        toast.textLabel.numberOfLines = 2
        toast.textLabel.font = UIFont.systemFontOfSize(13.0)
        toast.addSubview(toast.textLabel)

        toast.backgroundColor = UIColor.darkGrayColor()
        toast.alpha = 0.0;
        toast.layer.cornerRadius = 4.0;
        toast.textLabel.text = text;

        parentView.addSubview(toast)
        UIView.animateWithDuration(0.4, animations: {
            toast.alpha = 0.9
            toast.textLabel.alpha = 0.9
        })

        var timer = NSTimer.scheduledTimerWithTimeInterval(duration, target: self , selector: "hideSelf:", userInfo: nil,     repeats: false)
        //toast.performSelector(Selector("hideSelf"), withObject: nil, afterDelay: duration)

    }

    static private func getDouble(toastsAlreadyInParent : Int) -> CGFloat {
        return (70.0 + toastHeight * CGFloat(toastsAlreadyInParent) + toastGap * CGFloat(toastsAlreadyInParent));
    }

    func hideSelf( timer: NSTimer) {
        UIView.animateWithDuration(0.4, animations: {
            self.alpha = 0.0
            self.textLabel.alpha = 0.0
            }, completion: { t in self.removeFromSuperview() })
    }

} 

This is the error I get:

NSInvalidArgumentException', reason: '+[HonorsApp.ToastView hideSelf:]: unrecognized selector sent to class 0x10b564530' *** First throw call stack:

I have tried adding @objc to the method called from selector and to the class but it has been useless

Also:

Selector("hideSelf")

declaring the method as hideSelf()

Selector("hideSelf:")

declaring the method as hideSelf( timer: NSTimer)

have also checked that the class inherits from NSObject which is accomplished by inheriting from UIView, if I am not wrong.

I am using XCode 6.4 and swift 1.2

I am new at programming in swift and needed something like the Toast function in android and I found this code but as soon as i hit run the error came up.

Thanks for the help in advance.

Hypotension answered 4/7, 2016 at 11:33 Comment(2)
what version of swift are you using?Swordfish
Thanks so much that was exactly it.Hypotension
I
18

Since showInParent is a static function, the self you are using in NSTimer.scheduledTimerWithTimeInterval refers to the class and not an instance of the class. iOS isn't going to find the instance method hideSelf if it isn't looking in the right target.

Try passing the instance of ToastView that you create to the timer:

var timer = NSTimer.scheduledTimerWithTimeInterval(duration, target: toast, selector: "hideSelf:", userInfo: nil, repeats: false)
Intolerable answered 4/7, 2016 at 11:48 Comment(1)
Not thinking, I slipped my addObserver for notifications into a class method and did not think about it. Then after many more adds and edits of addObserver's and postNotification's elsewhere found that my exception handling was getting triggered and the NSNotification observers were not. Fooled with this thinking method name context conflicts and a bunch of debugging... and then found this and in the words of the late great James Brown "Good God!" :-) Thanks from me too!Abrupt
K
1

I got this error earlier today. Xcode suggested putting this:

self' refers to the method 'LoginController.self', which may be unexpected Use 'LoginController.self' to silence this warning

But turns out the LoginController.self does not work. This is a bug in Xcode

Kerge answered 26/1, 2023 at 15:56 Comment(1)
No no no. The compiler gave you a warning because self would have been something unusual. It told how to write this in a way that makes it look intentional, so the warning goes away. But self was \wrong\ all the time, so after convincing the compiler that you meant it, the compiler figured out you were wrong all along.Measure
I
0

try this code.

toast.performSelector(Selector("hideSelf:"), withObject: nil) or

toast.performSelector(#selector(ClassName.hideSelf(_:)), withObject: nil) s
Item answered 4/7, 2016 at 11:47 Comment(0)
M
0

Change this line:

var timer = NSTimer.scheduledTimerWithTimeInterval(duration, target: self , selector: "hideSelf:", userInfo: nil, repeats: false)

into:

var timer = NSTimer.scheduledTimerWithTimeInterval(duration, target: toast , selector: "hideSelf:", userInfo: nil, repeats: false)

This should help.

Maggio answered 4/7, 2016 at 11:50 Comment(0)

© 2022 - 2024 — McMap. All rights reserved.