I have a UIPickerView on my UIView along with a UITextField. I am letting the user select a value from the picker or enter a custom va
Instead of "pushing" the value of the picker each time you make a selection with this code:
- (void)pickerView:(UIPickerView *)pickerView didSelectRow:(NSInteger)row inComponent:(NSInteger)component
you should "pull it" when the user clicks the button (or other event you are using) using something similar to:
- (void)myAction:(id)sender
{
NSInteger row = [myPicker selectedRowInComponent:0];
selectedText = [myArray objectAtIndex:(NSUInteger)row];
}
For clearing the text: The UITextField class provides a built-in button for clearing the current text. So if the user does not want that text he can discard it.
myTextField.clearButtonMode = UITextFieldViewModeAlways;
So in the script, will you check if the TextField has a value, if it does have a value u use the TextField, if it doesn't have a value, you pull the information from the Picker.
-(void)textFieldDidBeginEditing:(UITextField *)textField
{
// Only for the text field with the picker
if (textField == self.yourTextField && [textField length]!=0)
{
// Select the first row programmatically
[self.categoriesPicker selectRow:0 inComponent:0 animated:YES];
// The delegate method isn't called if the row is selected programmatically
[self pickerView:self.categoriesPicker didSelectRow:0 inComponent:0];
}
}
- (void)pickerView:(UIPickerView *)pickerView didSelectRow:(NSInteger)row inComponent:(NSInteger)component
{
//Do all the stuff to populate the TextField
}
To overcome the didSelectRow not getting called in the UIPickerView when the user selected the first item in the list, you can use UITapGestureRecognizer. (Code example in Swift)
self.txtTransType = self.makeTextField(self.transType, placeHolder: "Check-in or Check-out")
self.txtTransType?.addTarget(self, action: "txtTransTypeEditing:", forControlEvents: UIControlEvents.EditingDidBegin)
func makeTextField(text: String?, placeHolder: String) -> UITextField {
var textField = UITextField(frame: CGRect(x: 140, y: 0, width: 220.00, height: 40.00));
textField.placeholder = placeHolder
textField.text = text
textField.borderStyle = UITextBorderStyle.Line
textField.secureTextEntry = false;
textField.delegate = self
return textField
}
func txtTransTypeEditing(sender: UITextField) {
var ttPickerView:UIPickerView = UIPickerView()
ttPickerView.dataSource = self
ttPickerView.delegate = self
sender.inputView = ttPickerView
let recognizer = UITapGestureRecognizer(target: self, action:Selector("handleTransTypePickerTap:"))
recognizer.delegate = self
ttPickerView.addGestureRecognizer(recognizer)
}
func handleTransTypePickerTap(recognizer: UITapGestureRecognizer) {
let ttPickerView = recognizer.view as! UIPickerView
let row = ttPickerView.selectedRowInComponent(0)
self.txtTransType!.text = self.transTypeData[row]
}
Use the following link UIGestureRecognizer Tutorial: Getting Started to get tap recognizer to work (need to add UIGestureRecognizerDelegate) and following code
class TransactionViewController: UIViewController, UITextFieldDelegate,UIPickerViewDataSource,UIPickerViewDelegate, UIGestureRecognizerDelegate { }
func gestureRecognizer(UIGestureRecognizer,
shouldRecognizeSimultaneouslyWithGestureRecognizer:UIGestureRecognizer) -> Bool {
return true
}
Can you programmatically select a row right after you instantiate the UIPickerView?
int firstRow = 0;
int firstOptionIndex = 0;
[myPickerView selectRow:firstRow inComponent:firstOptionIndex animated:NO];
That last line will trigger your pickerView:didSelectRow:inComponent delegate method.
In other words, that should set the value of the variable, wherever you are storing it (NSArray? not clear).
You can directly call delegate's method like
picker.delegate?.pickerView?(picker, didSelectRow: 0, inComponent: 0)