1

Hey guys I need some one to help me finish my app, I need to finish it before Dec 15. I'm making a Tip Calculator Project in Swift2 and It must have a settings view where I select the default tip rate. I have some issues with passing data, when I select a default tip percentage it doesn't change in the View Controller, also I want to make the app remember the default rate when I close the app and reopened. I will really appreciate that some one corrects my code and test it. Im new in this, below is the code of the two ViewControllers and a screenshot of the Main.Storyboard (Image 1) (ViewController Screenshot) My apologies for my bad English, is not my native language

ViewController

import UIKit

class ViewController: UIViewController {
//Inputs
@IBOutlet weak var amountTextField: UITextField!
//Labels
@IBOutlet weak var TipPercentageLabel: UILabel!
@IBOutlet weak var numberOfPersonLabel: UILabel!
@IBOutlet weak var tipAmountLabel: UILabel!
@IBOutlet weak var totalBillLabel: UILabel!
@IBOutlet weak var billPerPersonLabel: UILabel!
//Slider & Stepper
@IBOutlet weak var tipSlider: UISlider!
@IBOutlet weak var personsStepper: UIStepper!
//Variables
var tipPercentage = 0.20
var numberOfPerson:Int = 1
let numberFormatter:NSNumberFormatter = NSNumberFormatter()



override func viewDidLoad() {
    super.viewDidLoad()
    // Do any additional setup after loading the view, typically from a nib.
    tipAmountLabel.text = "$0.00"
    totalBillLabel.text = "Bill Total"
    billPerPersonLabel.text = "$0.00"
    TipPercentageLabel.text =  "20.0%"
    numberOfPersonLabel.text = "1"
    self.amountTextField.becomeFirstResponder()
}

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


    tipSlider.minimumValue = 0
    tipSlider.maximumValue = 100
    tipSlider.value = 20
    tipSlider.addTarget(self, action: "sliderTipChanged:", forControlEvents: .ValueChanged)

    personsStepper.minimumValue = 1
    personsStepper.maximumValue = 30
    personsStepper.value = 1
    personsStepper.addTarget(self, action: "sliderPersonChanged:", forControlEvents: .ValueChanged)

    amountTextField.text = ""

    refreshCalculation()

}
@IBAction func OnEditingFieldBill(sender: AnyObject) {
    refreshCalculation()
}
func refreshCalculation() {
    numberFormatter.numberStyle = NSNumberFormatterStyle.DecimalStyle
    if let amount = numberFormatter.numberFromString(amountTextField.text!) as? Double {

        let tipAmount = amount * tipPercentage
        let totalBill = amount + tipAmount
        let billPerPerson = totalBill / Double(numberOfPerson)
        numberFormatter.numberStyle = NSNumberFormatterStyle.CurrencyStyle
        tipAmountLabel.text = numberFormatter.stringFromNumber(tipAmount)
        totalBillLabel.text = numberFormatter.stringFromNumber(totalBill)
        billPerPersonLabel.text = numberFormatter.stringFromNumber(billPerPerson)

    } else {

        tipAmountLabel.text = "-"
        totalBillLabel.text = "-"
        billPerPersonLabel.text = "-"
    }

    numberFormatter.numberStyle = NSNumberFormatterStyle.PercentStyle
    numberFormatter.minimumFractionDigits = 1
    numberFormatter.maximumFractionDigits = 1
    TipPercentageLabel.text = self.numberFormatter.stringFromNumber(tipPercentage)

    numberOfPersonLabel.text = "\(numberOfPerson)"

}
@IBAction func sliderTipChanged(sender: AnyObject) {
    tipPercentage = Double(round(tipSlider.value)) / 100
    refreshCalculation()
}
@IBAction func StepperPersonChanged(sender: AnyObject) {
    numberOfPerson = Int(round(personsStepper.value))
    refreshCalculation()
}
override func prepareForSegue(segue: UIStoryboardSegue, sender: AnyObject?) {
    if let id = segue.identifier {
        if id == "show settings" {
            if let SettingsViewController = segue.destinationViewController as? SettingsViewController {

            }
        }
    }
}



}

Settings View Controller

import UIKit

class SettingsViewController: UIViewController {
@IBOutlet weak var tipControl: UISegmentedControl!
var tipRates:Double?

override func viewDidLoad() {
    super.viewDidLoad()

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

override func didReceiveMemoryWarning() {
    super.didReceiveMemoryWarning()
    // Dispose of any resources that can be recreated.
}
@IBAction func DefaultRate(sender: AnyObject) {
    var tipRate = [5, 10, 15, 20, 25, 30]
    var tipRates = Double(tipRate[tipControl.selectedSegmentIndex])
}
override func prepareForSegue(segue: UIStoryboardSegue, sender: AnyObject?) {
    if let id = segue.identifier {
        if id == "goBackToViewController" {
            if let ViewController = segue.destinationViewController as? ViewController {
                if let tip = tipRates {
                    ViewController.tipPercentage = tip/100
                }
            }
        }
}
user229044
  • 232,980
  • 40
  • 330
  • 338

1 Answers1

0

---- Edit from comments ----

I think the reason it is not updating as you would like is due to a minor error with this line.

var tipRates = Double(tipRate[tipControl.selectedSegmentIndex])

Inside of your DefaultRate action function for the UISegmentedControl

Using var is a redeclaration of the same variable name, thus what you are trying to pass in the prepareForSegue is an empty variable.

This function should be changed to:

@IBAction func DefaultRate(sender: AnyObject) {
var tipRate = [5, 10, 15, 20, 25, 30]
tipRates = Double(tipRate[tipControl.selectedSegmentIndex])}

Hopefully this will now solve the error.

---- End Edit ----

From what I can see in the viewDidLoad function of your viewController, you are setting the tip label, and not updating the value based on the variable var tipPercentage.

TipPercentageLabel.text =  "20.0%"

is setting the value display to always be 20.0%, you could use this here.

var tipDisplay = tipPercentage * 100    
TipPercentageLabel.text = "\(tipDisplay)%"

This should update the displayed value in the label, however you never call on your other functions to recalculate the amount etc.

Thus you should also be calling on

func setupContainer()

or

func refreshCalculation()

within your ViewDidLoad().

In terms of remembering the default value when the app is closed you should look into using NSUserDefaults.

Some information regarding NSUserDefaults can be found here, which explains implementing small amounts of saved data and can be implemented in your case quite simply.

mdhomer
  • 490
  • 5
  • 10
  • Thanks for your support, where did I write var tipDisplay = tipPercentage * 100 TipPercentageLabel.text = "\(tipDisplay)%" ? –  Dec 13 '15 at 06:25
  • You can replace TipPercentageLabel.text = "20.0%" with var tipDisplay = tipPercentage * 100 TipPercentageLabel.text = "\(tipDisplay)%" within your ViewController's ViewDidLoad function, so it doesn't always show "20.0%" when loaded, it will instead show the value of your tipPercentage variable. – mdhomer Dec 13 '15 at 06:28
  • Got it and where I need to put func setupContair or refreshCalculation? –  Dec 13 '15 at 06:33
  • You should also be calling on one of these within your ViewDidLoad, as otherwise they will not be updated until the user alters the text. As you want the values to update once the view is shown, and to do this you use the ViewDidLoad() function. – mdhomer Dec 13 '15 at 06:36
  • I try it as you said but when I change the tip percentage in the settings and go back to the ViewController it does n't change. –  Dec 13 '15 at 06:40
  • I just noticed a pretty obvious mistake on your part which I think is what is causing the issue. @IBAction func DefaultRate(sender: AnyObject) { var tipRate = [5, 10, 15, 20, 25, 30] var tipRates = Double(tipRate[tipControl.selectedSegmentIndex]) } Should be tipRates = Double(tipRate[tipControl.selectedSegmentIndex]) without "var", I will update answer to be more clear. – mdhomer Dec 13 '15 at 07:10
  • It still be updating when I change the Default Tip Rate –  Dec 13 '15 at 07:19
  • I made the error more clear in my answer, try what I have added there to fix the issue :) – mdhomer Dec 13 '15 at 07:19
  • I do what you said and still same –  Dec 13 '15 at 07:26
  • That part now should work, but to update the value (from the SegmentedControl), you need to fix the code in your SettingsViewController, which I have edited into my original answer. – mdhomer Dec 13 '15 at 07:26