I have a complex variable that I look up from a Firestore Document but that is not important. It works perfectly in either viewDidLoad or viewDidAppear. I can print it to verify the variable has the correct value.
let q1 = data!["q1"]! as? Bool ?? true
When I call the variable in the if statement in the button action I get the following error:
Use of unresolved identifier 'q1'
print(q1)
But print(q1) works perfectly if run in the viewDidAppear.
Can someone tell me what I am doing wrong? How can I pass a variable from viewDidLoad to the button action?
How can I pass a variable from viewDidLoad to the button action?
Store the value in an instance property. Properties are global to all methods, so viewDidLoad can see it (to store the value in it) and the button action method can see it (to retrieve and use it).
Related
I received data from my application server, and then assign that data to ios's object(articles).
And using that object(articles), I save values to cell's label in tableView.
After that, when user click the cell of tableView, this app move to another ViewController(NoticeArticleVC). Before moving, I assign value of object(articles) to that ViewController's variable like below code.
However, as usual, I did optional binding using 'if let' statement. But I got error as if I didn't do optional binding.
Though I cleaned build folder, and then rebuilded, it didn't work.
Please let me know what's wrong with my code.
You've instantiated the new ViewController, but I don't think titleLabel will be set until the view has loaded. You will need to present the new view controller and then set the label. Or better, set a variable on the new ViewController and only set the label field from within that VC code (e.g. in/after viewDidLoad).
I have a little problem with my code so that I can't call a function. I created a function func changeLabelText(text: String) { mylabel.stringValue = text } in the ViewController with that I can update the Text in the Label. When I try to call the function from another class in the Project, I get a runtime error(EXC_BAD_Instr...) and the Debugger holds on the line where I try to change the Label's text, with the error: fatal error: unexpectedly found nil while unwrapping an Optional value. Where is the problem? Can someone help me please!
Regarding the "unexpectedly found nil while unwrapping an Optional value" error, the problem is that you have an optional (judging from the code snippet you've provided, it must be an implicitly unwrapped optional) that is nil. Most likely, mylabel is nil. Either print the value or add a breakpoint and examine the property in the debugger to confirm.
If it is nil, you then have to figure out why. In our discussion, it turns out that you're trying to call the Log event in the view controller:
ViewController().Log("asdf")
The problem is that this doesn't call Log in the existing view controller, but rather the ViewController() expression ends up instantiating a new, completely unrelated view controller with its outlets not hooked up to anything. Thus the attempt to update the implicitly unwrapped outlet will cause the error you shared with us.
If you want this separate class (a database manager object) to inform the view controller of event in order to allow the view controller to update the UI, there are three common approaches:
Completion/progress handlers that are closures/blocks.
This is used for simple interface where the database needs to inform view controller when the request is done.
Delegate-protocol pattern.
The delegation pattern (usually conforming to some well-established protocol) is used for rich interfaces where the database needs to inform the view controller of a variety of different types of events.
Notification pattern.
Notifications are used when you want a loosely coupled interface between the database object and whatever is handling these notifications. The view controller might register itself as an observer of any notifications of a particular name with the defaultCenter() of the NSNotificationCenter. The database object can then post notifications of that name (supplying details via the userInfo dictionary) and the view controller will be informed of these events.
A few things are you calling an instance of the view controller properly
e.g if the class name is ViewController, in the the view controller that you are calling the function make sure you use
let VC = ViewController ()
and then use VC.yourFunctionName
also instead of stringValue use .text
I've got a dynamic table with a cell for a UIDatePicker. There's a function in the UITableViewCell class that updates a variable when the picker changes. I'm just having trouble getting that value back to the UITableViewController class. I can print the correct variable while spinning the picker, but when I go to reloadRowsAtIndexPaths for the tableView I need the value available.
Since there's no segue, I can't get a protocol/delegate to work. I imagine a global variable might also work, but that's cheating. Any suggestions?
You can use NSUserDefaults for storing values globally which can access anywhere into your project. you can set values this way for your picker.
NSUserDefaults.standardUserDefaults().setObject("YouValueForm", forKey: "YourKey")
After that you can access this value anywhere in your project this way:
let yourVar = NSUserDefaults.standardUserDefaults().objectForKey("YourKey") as! String
You can modify this as per your need. and once you got your values you can do reloadRowsAtIndexPaths.
Hope this will help.
Simple question.
I have a tableViewController that will display a list of search results.
I want to create a block based callback (I think that's what you would call it)
I would present the viewController
[searchResultController showSearchResults //BlockCode here {
//did select this item...
}];
but use a block so that I can detect the selection made from the tableview instead of using a delegate method.
Problem is I have no idea how to implement this. Is there a good tutorial or a simple example on how to do this?
Your search results controller needs to have a block property. This block should be defined with no return type, and should take a parameter of whatever object you are going to use to represent the selected item.
Before presenting your search results controller, set the block property to whatever you wish to do for your callback.
Within the search results controller, when a row is selected, execute the block, passing in the selected object. Either this method, or the block itself, should also dismiss your controller.
I'm a c++ programmer new to objective-c.
I created a calculator app that is working fine using a single view. I have a Calculations class and a ViewController. Every time a button is pressed, an IBAction method in the ViewController calls methods defined in the Calculations class to handle the input and returns the output as an NSString which I then set as the value of the label.text field.
Now I am working on a tab bar app using the same Calculations class. This app has two tabs, each with a unique set of input buttons for the calculator (both views sharing the same input/output data). The first tab is identical to my first app with the single view, so I am trying to do this in a similar fashion.
Here is the problem:
When a button is pressed, the IBAction method that handles the input runs through the calls to the Calculations class methods (shown below) without error:
-(IBAction)readInput:(id)sender {
[_calculations input:[sender titleForState:UIControlStateNormal]];
inputField.text = [_calculations inputDisplay];
outputField.text = [_calculations outputDisplay];
}
however, both the inputDisplay and outputDisplay methods return nil. Using the debugger I noticed that I am unable to "step into" the calls to _calculations methods, instead the line is skipped and the value returned by both is nil. I added the following method:
-(IBAction)setNumber:(id)sender {
NSString *button =(NSString *)[sender titleForState:UIControlStateNormal];
inputField.text = button;
}
and if I attach this to the input buttons I can see the display updated. This seems to be an issue with calling the _calculations member functions and tab bar views (because this issue is not present using a single view).
I realize that I left out a lot of information, but I did it to avoid providing irrelevant information. I will provide all details that are necessary if asked.
Check to make sure _calculations is not nil.
You can send any message (call any method) on nil and it will just return nil, not cause an exception.
Without seeing more code it is going to be a bit difficult to diagnose.
If I was trying to debug this issue I would first make sure _calculations points to the object you want it to point to. If its loaded from a NIB then it might not be getting initialised, and still be nil. You can send messages to nil objects without any issues. If an object receives a message that it cant handle (the method doesn't exist, or the target object is nil) then the return for that call will be nil.
I have in the past put initilization code into the init: method, and spent a few hours why it wasn't being called, until it dawned on me that I needed to put my init code into the viewDidLoad:, or the initWithNibName:bundle: or even the initWithCoder: selector.
HTH, Matt