Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Custom Controller and Button Actions #10

Open
YaroslawBagriy opened this issue Jun 18, 2015 · 4 comments
Open

Custom Controller and Button Actions #10

YaroslawBagriy opened this issue Jun 18, 2015 · 4 comments

Comments

@YaroslawBagriy
Copy link

Hello,

So I've implemented the code below.

    let storyboard = UIStoryboard(name: "Main", bundle: nil)
    self.window = UIWindow(frame: UIScreen.mainScreen().bounds)
    var orange = UIColor(red: 255/255, green: 69.0/255, blue: 0.0/255, alpha: 1.0)
    var gray = UIColor(red: 0.84, green: 0.84, blue: 0.84, alpha: 1.0)

    var ctr1 = storyboard.instantiateViewControllerWithIdentifier("SettingsViewController") as! SettingsViewController
    ctr1.title = "Settings"
    var ctr2 = storyboard.instantiateViewControllerWithIdentifier("gameViewController") as! SeekerViewController
    ctr2.title = "Game"
    var ctr3 = UIViewController()
    ctr3.title = "Exit"
    ctr3.view.backgroundColor = gray

    var img1 = UIImage(named: "gear")
    img1 = img1?.imageWithRenderingMode(.AlwaysTemplate)
    var img2 = UIImage(named: "profile")
    img2 = img2?.imageWithRenderingMode(.AlwaysTemplate)
    var img3 = UIImage(named: "chat")
    img3 = img3?.imageWithRenderingMode(.AlwaysTemplate)


    var items = [UIImageView(image: img1), UIImageView(image: img2), UIImageView(image: img3)]
    var controllers = [ctr1, ctr2]
    controller = SLPagingViewSwift(items: items, controllers: controllers, showPageControl: false)

    controller?.pagingViewMoving = ({ subviews in
        for v in subviews {
            var lbl = v as! UIImageView
            var c = gray

            if(lbl.frame.origin.x > 45 && lbl.frame.origin.x < 145) {
                c = gradient(Double(lbl.frame.origin.x), Double(46), Double(144), orange, gray)
            }
            else if (lbl.frame.origin.x > 145 && lbl.frame.origin.x < 245) {
                c = gradient(Double(lbl.frame.origin.x), Double(146), Double(244), gray, orange)
            }
            else if(lbl.frame.origin.x == 145){
                c = orange
            }
            lbl.tintColor = c
        }
    })

    self.nav = UINavigationController(rootViewController: self.controller!)
    self.window?.rootViewController = self.nav
    self.window?.backgroundColor = UIColor.whiteColor()
    self.window?.makeKeyAndVisible()

I added two new custom controllers. The SettingsViewController has a button with an action. When I go to click the button my program crashes. Any reasons why? The button works perfectly if I don't have it go through the SLPagingViewSwift controller.

@YaroslawBagriy
Copy link
Author

Hello,

So I see there was Swift 1.2 updates. I pulled the code from https://github.com/kobim/SLPagingViewSwift/tree/swift1.2

it still doesn't seem to work. It builds great. But I get a EXE_BAD_ACCESS (code=EXC_i386_GPFLT) when I click a button on one of my custom ViewControllers that I added. I would greatly appreciate help with this. I've been searching all over the internet for the answer but couldn't find it.

I added a new subclass of UIViewController

class TestViewController: UIViewController {

override func viewDidLoad() {
    super.viewDidLoad()

    let button   = UIButton()
    button.frame = CGRectMake(100, 100, 100, 50)
    button.backgroundColor = UIColor.greenColor()
    button.setTitle("Test Button", forState: UIControlState.Normal)
    button.addTarget(self, action: "buttonAction:", forControlEvents: UIControlEvents.TouchUpInside)

    self.view.addSubview(button)

    // Do any additional setup after loading the view.
}

override func didReceiveMemoryWarning() {
    super.didReceiveMemoryWarning()
    // Dispose of any resources that can be recreated.
}


func buttonAction(sender:UIButton!)
{
    println("Button tapped")
}

/*
// MARK: - Navigation

// In a storyboard-based application, you will often want to do a little preparation before navigation
override func prepareForSegue(segue: UIStoryboardSegue, sender: AnyObject?) {
    // Get the new view controller using segue.destinationViewController.
    // Pass the selected object to the new view controller.
}
*/

}

Which then I replaced one of the UIVIewControllers in AppDelegate with it. Code is shown below.

var window: UIWindow?
var nav: UINavigationController?
var controller: SLPagingViewSwift!

func application(application: UIApplication, didFinishLaunchingWithOptions launchOptions: [NSObject: AnyObject]?) -> Bool {
    self.window = UIWindow(frame: UIScreen.mainScreen().bounds)
    let orange = UIColor(red: 255/255, green: 69.0/255, blue: 0.0/255, alpha: 1.0)
    let gray = UIColor(red: 0.84, green: 0.84, blue: 0.84, alpha: 1.0)

    var ctr1 = UIViewController()
    ctr1.title = "Ctr1"
    ctr1.view.backgroundColor = orange
    var ctr2 = UIViewController()
    ctr2.title = "Ctr2"
    ctr2.view.backgroundColor = UIColor.yellowColor()
    var ctr3 = TestViewController()
    ctr3.title = "Ctr3"
    ctr3.view.backgroundColor = gray

    var img1 = UIImage(named: "gear")
    img1 = img1?.imageWithRenderingMode(.AlwaysTemplate)
    var img2 = UIImage(named: "profile")
    img2 = img2?.imageWithRenderingMode(.AlwaysTemplate)
    var img3 = UIImage(named: "chat")
    img3 = img3?.imageWithRenderingMode(.AlwaysTemplate)


    var items = [UIImageView(image: img1), UIImageView(image: img2), UIImageView(image: img3)]
    var controllers = [ctr1, ctr2, ctr3]
    controller = SLPagingViewSwift(items: items, controllers: controllers, showPageControl: false)

    controller.pagingViewMoving = ({ subviews in
        if let imageViews = subviews as? [UIImageView] {
            for imgView in imageViews {
                var c = gray
                let originX = Double(imgView.frame.origin.x)

                if (originX > 45 && originX < 145) {
                    c = self.gradient(originX, topX: 46, bottomX: 144, initC: orange, goal: gray)
                }
                else if (originX > 145 && originX < 245) {
                    c = self.gradient(originX, topX: 146, bottomX: 244, initC: gray, goal: orange)
                }
                else if(originX == 145){
                    c = orange
                }
                imgView.tintColor = c
            }
        }
    })

    self.nav = UINavigationController(rootViewController: self.controller)
    self.window?.rootViewController = self.nav
    self.window?.backgroundColor = UIColor.whiteColor()
    self.window?.makeKeyAndVisible()
    return true
}

func applicationWillResignActive(application: UIApplication) {
    // Sent when the application is about to move from active to inactive state. This can occur for certain types of temporary interruptions (such as an incoming phone call or SMS message) or when the user quits the application and it begins the transition to the background state.
    // Use this method to pause ongoing tasks, disable timers, and throttle down OpenGL ES frame rates. Games should use this method to pause the game.
}

func applicationDidEnterBackground(application: UIApplication) {
    // Use this method to release shared resources, save user data, invalidate timers, and store enough application state information to restore your application to its current state in case it is terminated later.
    // If your application supports background execution, this method is called instead of applicationWillTerminate: when the user quits.
}

func applicationWillEnterForeground(application: UIApplication) {
    // Called as part of the transition from the background to the inactive state; here you can undo many of the changes made on entering the background.
}

func applicationDidBecomeActive(application: UIApplication) {
    // Restart any tasks that were paused (or not yet started) while the application was inactive. If the application was previously in the background, optionally refresh the user interface.
}

func applicationWillTerminate(application: UIApplication) {
    // Called when the application is about to terminate. Save data if appropriate. See also applicationDidEnterBackground:.
}

func viewWithBackground(color: UIColor) -> UIView{
    var v = UIView()
    v.backgroundColor = color
    return v
}

func gradient(percent: Double, topX: Double, bottomX: Double, initC: UIColor, goal: UIColor) -> UIColor{
    var t = (percent - bottomX) / (topX - bottomX)

    let cgInit = CGColorGetComponents(initC.CGColor)
    let cgGoal = CGColorGetComponents(goal.CGColor)


    var r = cgInit[0] + CGFloat(t) * (cgGoal[0] - cgInit[0])
    var g = cgInit[1] + CGFloat(t) * (cgGoal[1] - cgInit[1])
    var b = cgInit[2] + CGFloat(t) * (cgGoal[2] - cgInit[2])

    return UIColor(red: r, green: g, blue: b, alpha: 1.0)
}

screen shot 2015-08-28 at 2 46 32 pm

Here is the stack trace. I made a new project and make a one screen app with the screens class as my TestViewController, I clicked the button and it worked.

@kobim
Copy link
Contributor

kobim commented Aug 30, 2015

The problem is that your TestViewController isn't retained - this library only retains the views of the view controllers, and not the view controllers themselves.

If you add var ctr3 : UIViewController! to your AppDelegate, and assign that to SLPagingViewSwift's controllers parameter, your code will work.

@YaroslawBagriy
Copy link
Author

Koblm,

Thank you for such a quick response. It works just like I want.

Thanks,

Yaroslaw Bagriy

@MuhammadMazharIqbal
Copy link

Thanks its working

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

3 participants