Question

I want to hide keyboard on UITextField end editing event but somehow I am not able to get following code working! When I press Done button, it hides the keyboard but not when I don't press done button and move to another UITextField where I don't need keyboard but UIPickerView. Basically UIPickerView is appearing but behind the keyboard. I am resigning current UITextField on end editing event as well as on begin editing for required text fields. The begin editing code works fine if I don't have keyboard already shown for previous UITextField. Could someone please tell me what am I doing wrong?

Following sequence works:

  1. Select normal UITextField and insert text, press done button (this hides keyboard)
  2. Select picker UITextField (this displays picker view)

..but following doesn't:

  1. Select normal UITextField and insert text
  2. Select picker UITextField (the picker view is behind the keyboard as I didn't press done button for previous UITextField). Here it calls end editing but it doesn't hide keyboard!

    - (BOOL)textFieldShouldReturn:(UITextField *)textField {
        [textField resignFirstResponder];
        scrollView.contentSize = CGSizeMake(320, 750);
        [scrollView setFrame:CGRectMake(0, 0, 320, 480)];
        return YES;
     }
    
    -(void)textFieldDidEndEditing:(UITextField *)textField  
    {
        [textField resignFirstResponder];
    }
    
    - (void)textFieldDidBeginEditing:(UITextField *)textField {
        DatePicker.hidden = YES;
        CountryPickerView.hidden = YES;
    
        switch (textField.tag) {
            case 3:
                [textField resignFirstResponder];
                DatePicker.hidden = NO;
                return;
            case 6:
                [textField resignFirstResponder];
                CountryPickerView.hidden = NO;
                return;
            default:
                break;
        }
        scrollView.contentSize = CGSizeMake(320, 650);
        [scrollView setFrame:CGRectMake(0, 0, 320, 260)];
    }
    
Was it helpful?

Solution

it hides the keyboard but not when I don't press done button and move to another uitextfield where I don't need keyboard but PickerView.

The right way to handle this is to set the inputView property for the field that uses a picker instead of the keyboard. Configure the picker as you need it (set up delegate, data source, etc.) and then set it as the field's inputView. The system will handle hiding the keyboard and showing the picker view, or vice versa, as you move from one field to the next.

OTHER TIPS

You should not be relying on tags but pointers to the objects and remove [textField resignFirstResponder]; from textFieldDidEndEditing.

- (BOOL)textFieldShouldBeginEditing:(UITextField *)textField 
{ 
    if (textField == theTextFieldIDontWantKeyboardFor) {  
        [thepreviousTextField resignFirstResponder]; 
        return NO;
    }
    return YES; 
}
[yourTextField resignFirstResponder];

Is what actually hides the keyboard, so use that when the picker is about to open.

when you switch control from one textfield to next without resigning, textFieldDidBeginEditing does not get called so, you need to resign the textfield by making it "firstResponder" (as it is not firstResponder due to change in the active textfield) then calling resignFirstResponder

Try this code

 -(void)textFieldDidEndEditing:(UITextField *)textField  
  {
  if(textField==nameTextField){
    [nameTextField resignFirstResponder];

     //
  }
  else if(textField==pickerTextField){

  ///
  }
  }

  - (BOOL)textFieldShouldReturn:(UITextField *)textField {
  if(textField==nameTextField){
    [nameTextField resignFirstResponder];

    //
  }
  else if(textField==pickerTextField){

  ///
  }
  }

Adding here my final outcomes!

Solution by Valexa. This worked absolutely fine but I needed to handle different input views manually.

    - (BOOL)textFieldShouldReturn:(UITextField *)textField {
        [textField resignFirstResponder];
            scrollView.contentSize = CGSizeMake(320, 750);
            [scrollView setFrame:CGRectMake(0, 0, 320, 480)];
        return YES;
    }

    - (void)textFieldDidBeginEditing:(UITextField *)textField {    
           previousTextField = textField;
           scrollView.contentSize = CGSizeMake(320, 650);
           [scrollView setFrame:CGRectMake(0, 0, 320, 260)];
    }

    - (BOOL)textFieldShouldBeginEditing:(UITextField *)textField {
           if (textField == CountryTextField || textField == BirthdayTextField) {
                  [previousTextField resignFirstResponder]; 
                  return NO; 
           }
          return YES; 
    }

Amazing solution(Thanks Caleb): No need to monitor extra variable for previous textfield and no need of having headache of showing and adding require views

BirthdayTextField.inputView = DatePickerView;
CountryTextField.inputView = CountryPickerView;
SexTextField.inputView = SexPickerView;

- (BOOL)textFieldShouldReturn:(UITextField *)textField {
[textField resignFirstResponder];
    scrollView.contentSize = CGSizeMake(320, 750);
    [scrollView setFrame:CGRectMake(0, 0, 320, 480)];
return YES;
}

- (void)textFieldDidBeginEditing:(UITextField *)textField {
    scrollView.contentSize = CGSizeMake(320, 650);
    [scrollView setFrame:CGRectMake(0, 0, 320, 260)];
}
-(void)hidekeybord
{
    [_txt_fname resignFirstResponder];
    [_txt_lname resignFirstResponder];
    [_txt_email resignFirstResponder];
    [_txt_phoneN resignFirstResponder];
    [_txt_dateofbd resignFirstResponder];
    [_txt_address resignFirstResponder];
    [_txt_city resignFirstResponder];

}

- (IBAction)btn_open_datepiker:(id)sender
{
    [self hidekeybord];

    _datepiker_bd.hidden=FALSE;
    _toolbar_db.hidden=FALSE;


}
Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top