iPhone development common problems with UITextField and UITextViews - iphone

I've been using iPhone SDK from last 2 months.
One thing I observed is SDK isn't very nice in terms of getting text inputs.
Everytime I use a UITextView and UITextField followings are the common problems I always have to deal with:
Keyboard overlaps the textinput.
There is not a default way to hide the keyboard.
Although I know how to deal with both, for the first, I scrolls up the entire view at the keyboardshown notification call and to hide I know resignFirstResponder.
Here is how I deal with this.
But I hate the way I work!!
I don't want to copy the same code at all the .h and .m files.
I love the way the safari keyboard works like toolbar.
Kindly advice me if there is any reusable class I can use in my projects to tackle the problem.
I am sure there should be some re-usable solution to this problem as this is the common problem every developer must have seen!

UITableViewController will automatically resize its UITableView when keyboard is shown/hidden. If your UI has table-like design, you can place your controls inside UITableView so you won't have to implement resizing manually.

While it can be a pain, how could Apple possibly code that functionality to account for every possible use case?
Instead, you need to figure out what your common use cases are and then program accordingly. This is object-oriented programming - code reuse is encouraged! But, if you are copying and pasting between projects, you are doing it wrong.
For example, it is very common for me to do this with text inputes in UITableViews that are not part of a UITableView controller. Obviously, the keyboard becomes a problem that I need to fix.
So, do I write the necessary code to fix it every time? Nope, I wrote it once in a UITableView subclass and I use that class in all my projects.
Remember, good programmers are lazy and will use the tools available to them to avoid writing the same thing over and over. Create your own class, categories, etc. to handle you common problems and you'll be fine.

Textfield's and scrolling view in up/down's. using NSNotificationCenter code.
Write code in "viewDidLoad":
[[NSNotificationCenter defaultCenter] addObserver:self selector:#selector (keyboardDidShow:)
name: UIKeyboardDidShowNotification object:nil];
[[NSNotificationCenter defaultCenter] addObserver:self selector:#selector (keyboardDidHide:)
name: UIKeyboardDidHideNotification object:nil];
add to code in delegate methods:
-(void) keyboardDidShow: (NSNotification *)notif
{ [calendarView removeFromSuperview];
// If keyboard is visible, return
if (keyboardVisible)
{
NSLog(#"Keyboard is already visible. Ignore notification.");
return;
}
// Keyboard is now visible
keyboardVisible = YES;
}
-(void) keyboardDidHide: (NSNotification *)notif
{ [calendarView removeFromSuperview];
// Is the keyboard already shown
if (!keyboardVisible)
{
NSLog(#"Keyboard is already hidden. Ignore notification.");
return;
}
if (up == 1) {
up = 0;
[self down];
}
// Keyboard is no longer visible
keyboardVisible = NO;
}
add to remaining default methods:
- (BOOL)textField:(UITextField *)textField shouldChangeCharactersInRange:(NSRange)range replacementString:(NSString *)string
{
if(textField == txt_Zip){
NSString *newString = [textField.text stringByReplacingCharactersInRange:range withString:string];
return !([newString length] > 6);
}
else {
return YES;
}
}
-(void) touchesBegan :(NSSet *) touches withEvent:(UIEvent *)event
{
if(up==1)
{
up=0;
[self down];
}
[txtMake_Model resignFirstResponder];
[txtSerial_Vin resignFirstResponder];
[txtDaysPerWeek resignFirstResponder];
[txtAnnualMiles resignFirstResponder];
[txtPurchasedDate resignFirstResponder];
[txtInterestLocation resignFirstResponder];
[txtInterestSequence resignFirstResponder];
[txtInterestName resignFirstResponder];
[txt_City resignFirstResponder];
[txtAddress1 resignFirstResponder];
[txtAddress2 resignFirstResponder];
[txt_Zip resignFirstResponder];
[txtAdditionalInfo resignFirstResponder];
[txtVehicleNumber resignFirstResponder];
[txtMilesToWork resignFirstResponder];
[txtCostNew resignFirstResponder];
[super touchesBegan:touches withEvent:event ];
}
//- (BOOL)textFieldShouldReturn:(UITextField *)textField // called when 'return' key pressed. return NO to ignore.
//{
// [textField resignFirstResponder];
// return YES;
//}
- (BOOL)textFieldShouldReturn:(UITextField *)textField{
[textField resignFirstResponder];
if (up==1) {
up =0;
[self down];
}
return YES ;
}
- (void)textFieldDidBeginEditing:(UITextField *)textField{
if(textField == txtInterestSequence)
{ if(up==0){up=1;[self moveUp];}
}else if(textField == txtInterestName)
{ if(up==0){up=1;[self moveUp];}
}else if(textField == txtAddress1)
{ if(up==0){up=1;[self moveUp];}
} else if(textField == txtAddress2)
{ if(up==0){up=1;[self moveUp];}
} else if(textField == txt_City)
{ if(up==0){up=1;[self moveUp];}
} else if(textField == txt_Zip)
{ if(up==0){up=1;[self moveUp];}
} else if(textField == txtAdditionalInfo)
{ if(up==0){up=1;[self moveUp];}
} else if(textField == txtMilesToWork)
{ if(up==0){up=1;[self moveUp];}
} else if(textField == txtCostNew)
{ if(up==0){up=1;[self moveUp];}
}
}
-(void)moveUp{
// up=1;
[UIView beginAnimations:nil context:nil];
self.view.center=CGPointMake(self.view.center.x, self.view.center.y-200);
[UIView commitAnimations];
}
-(void)down{
[UIView beginAnimations:nil context:nil];
self.view.center=CGPointMake(self.view.center.x, self.view.center.y+200);
[UIView commitAnimations];
// up=0;
}

Related

How do I set the next text field in focus for editing when the user hits return? [duplicate]

This question already has answers here:
Closed 10 years ago.
Possible Duplicate:
How to navigate through textfields (Next / Done Buttons)
iOS app “next” key won’t go to the next text field
I have two text fields in my view and I'd like the cursor to move from the email text field to the password text field when the user hits the return key. If the password text field is the one in focus, I'd like the keyboard to hide. Here's what I currently have, but it doesn't work...
- (BOOL)textFieldShouldReturn:(UITextField *)textField {
return YES;
}
- (void)textFieldDidEndEditing:(UITextField *)textField {
if(textField == self.emailTextField) {
[self.passwordTextField becomeFirstResponder];
}
else if (textField == self.passwordTextField) {
[textField resignFirstResponder];
}
}
What am I missing? Thanks so much in advance for your wisdom!
The code you have in the textFieldDidEndEditing: method belongs in the textFieldShouldReturn: method.
- (BOOL)textFieldShouldReturn:(UITextField *)textField {
if(textField == self.emailTextField) {
[self.passwordTextField becomeFirstResponder];
} else if (textField == self.passwordTextField) {
[textField resignFirstResponder];
}
return NO;
}
Well, for the reference we have below two textfields,
UITextField *email_Text;
email_Text.tag = 100;
email_Text.delegate = self;
UITextField *password_Text;
password_Text.tag = 101;
password_Text.delegate = self;
You must implement UITextFieldDelegate in you .h file.
Currently iam not using any allocation methods here now for the textfields. You have to alloc it or making it as outlet if the textfield is in the xib by yourself. I am simply just having two objects for reference only. And also these objects must be globally accessible in the class (i mean you should declare it in the header).
The next step is to implement the textFieldShouldReturn: delegate of UITextField.
- (BOOL)textFieldShouldReturn:(UITextField *)textField {
if(textField.tag == 100)
{
[password_Text becomeFirstResponder];
}
else if(textField.tag == 101)
{
[textField resignFirstResponder];
}
else
{
; //NOP
}
return YES;
}
Try this.
Happy Coding :)
you miss one thing
- (BOOL)textFieldShouldReturn:(UITextField *)textField {
if(textField == self.emailTextField) {
[self.passwordTextField becomeFirstResponder];
[self.emailTextField resignFirstResponder];
} else if (textField == self.passwordTextField) {
[textField resignFirstResponder];
[self.emailTextField becomeFirstResponder];
}
return NO;
}

UItextField Delegate not working

In my iPad app I have two textfields. One displays the normal, default textfield and the other should display a picker as its input view.
Problem is, once I use the txt1 which displays default keyboard and then when I touch the 2nd textField the txt1 keyboard is staying visible.
I have also written [txt1 resignFirstResponder]; [txt2 resignFirstResponder]; while displaying the picker.
I have checked the txt1 IBOutlet connection and the delegate assignment, those seem to be correct.
What am I missing?
Write the following code :
- (BOOL)textFieldShouldBeginEditing:(UITextField *)textField
{
if(textField == txt1)
{
return YES;
}
else
{
return NO; // Write the code for displaying UIPickerView instead of the Keyboard.
}
}
Hope this might solve your issue......
txt2.userInteractionEnabled = NO;
- (BOOL)textFieldShouldBeginEditing:(UITextField *)textField
{
if(textField == txt1)
{
[txt2 resignFirstResponder];
// code for Hide Picker
return YES;
   }
else {
// [txt2 resignFirstResponder];
[txt1 resignFirstResponder];
// code for go in picker
return YES;
}
}
for more information
You have to implement below method to resign Keyboard......
-(BOOL)textFieldShouldReturn:(UITextField *)textField
{
[textField resignFirstResponder];
return YES;
}
Have u implemented this method ??
-(BOOL)textFieldShouldReturn:(UITextField *)textField
{
[textField resignFirstResponder];
return YES;
}
In your viewDidLoad method write this,
txt2.inputView = pickerView;
and other resignFirstResponder codes should be placed correctly , by this on Tapping txt2, you will directly get pickerview instead of Keyboard.
did you implement the delegates property of UITextFieldDelegates to in the header file, if not do that and check

UITextField ResignFirstRespond not working in iphone?

I am designed one form with four UITextFields. First One for entering numbers, Second for entering name, third for choosing date and last one for choosing time. First textfield using Numberpad it will hide by using done button on the keyboard. If the user when enter into second (Name textfield) from first (number textfield) the first keyboard hide perfectly. If the user entering name and select date textfield am showing the datepicker in Actionsheet, when the user pick the date and hit done/cancel button i hide the actionsheet. But, the name textfield keyboard don't dismiss from the screen. I have tied below code, it is not working. Can anyone please suggest the idea for this clarification? Thanks in advance.
-(void)textFieldDidBeginEditing:(UITextField *)textField
{
if (textField == numberTextfield)
{
[textField setInputAccessoryView:keyboardToolbar];
}
else if(textField == nameTextfield)
{
}
else if(textField == dateTextField)
{
[self showdateActionSheet];
[nameTextfield resignFirstResponder];
[dateTextField resignFirstResponder];
}
else if(textField == timeTextField)
{
[timeTextField resignFirstResponder];
[nameTextfield resignFirstResponder];
}
}
- (BOOL) textFieldShouldReturn:(UITextField *)textField // If the user select Return key it is dismissing fine
{
[nameTextfield resignFirstResponder];
return YES;
}
-(BOOL) textFieldShouldEndEditing:(UITextField *)textField
{
[nameTextfield resignFirstResponder];
return YES;
}
-(void) DateDone
{
[nameTextfield resignFirstResponder];
}
-(void) timeDone
{
[nameTextfield resignFirstResponder];
}
Gopinath. Please try my following code,
- (BOOL)textFieldShouldBeginEditing:(UITextField *)textField
{
if (textField == dateTextField )
{
[nameTextfield resignFirstResponder];
[self showdateActionSheet];
[dateTextField resignFirstResponder];
}
else if( textField == timeTextField)
{
[nameTextfield resignFirstResponder];
[self ShowTime];
[timeTextField resignFirstResponder];
}
return YES;
}
I am sure i will help you.
Just do this:
self.view.editable = NO;
Link: How can I programmatically link an UIView or UIImageView with an event like “touch up inside”.

How to unhide the keyboard of the current active textbox?

I have an IBAction linked up to EditingDidBegin on all my UITextFields, so why isn't the following code working when the UITextFields are tapped on?
-(IBAction)keyboardShouldShow
{
[self becomeFirstResponder];
NSLog(#"Keyboard Showing");
}
Also bear in mind that the keyboard will not show unless this code is added because of other code I have in my project file.
Thanks
your self is not your textfield.try to change the method to this and relink it to editingdidbegin.
-(IBAction)keyboardShouldShow:(UITextField*)sender
{
[sender becomeFirstResponder];
NSLog(#"Keyboard Showing");
}
HIH
Because self is your view controller, not the UITextField.
Use the UITextFieldDelegate method:
- (void) textFieldDidBeginEditing:(UITextField *)textField {
if ([textField isKindOfClass:[UITextField class]]) {
[textField resignFirstResponder];
NSLog(#"Keyboard Showing");
}
}
And if you want to use your own method, be sure to pass the UITextField as a parameter.
Change the method to something like:
-(IBAction)keyboardShouldShow:(id)sender {
if ([sender isKindOfClass:[UITextField class]]) {
[sender resignFirstResponder];
NSLog(#"Keyboard Showing");
}
}

Problem showing/hiding keyboard in iPhone app

In my iPhone app, I am facing some problems related to keyboard show/hide behavior.
I have three text fields; when the third text field is clicked, I want to display a UIPickerView and hide the keyboard for that text field. That I can do.
Now the problem is that, if the keyboard of either first or second text field is visible, and I click on the third text field, the picker becomes visible, but it appears behind the keyboard (it is only behind the keyboard of the first or second text field).
So what should I do to make the picker visible by itself and not to display any keyboard at that time?
Here is the code:-
-(void) textFieldDidBeginEditing:(UITextField *)textField{
if (textField==thirdTextField) {
[scroll setFrame:CGRectMake(00, 48, 320, 160)];
[scroll setContentSize:CGSizeMake(320,335)];
[picker setHidden:NO];
[tool1 setFrame:CGRectMake(0,180,320,44)];
[tool1 setHidden:NO];
[self.picker reloadAllComponents];
[firtTextField resignFirstResponder];
[secondTextField resignFirstResponder];
[thirdTextField resignFirstResponder];
}
else {
[scroll setFrame:CGRectMake(00, 48, 320, 200)];
[scroll setContentSize:CGSizeMake(320,335)];
[tool1 setHidden:NO];
[tool1 setFrame:CGRectMake(0,220,320,44)];
}
}
the problem is like
Keep three textfields as member of the controller.
- (void)textFieldDidBeginEditing:(UITextField *)textField {
if(textField == 3rdTextField){
[self.firstTextField resignFirstResponder];
[self.secondTextField resignFirstResponder];
[self.thirdTextField resignFirstResponder];
}
}
- (BOOL)textFieldShouldBeginEditing:(UITextField *)textField{
if(textField==3rdTextField){
[firstTextField resignFirstResponder];
[secondTextField resignFirstResponder];
}
else if(textField==secondTextField){
[firstTextField resignFirstResponder];
[3rdTextField resignFirstResponder];
}
else if(textField==firstTextField){
[secondTextField resignFirstResponder];
[3rdTextField resignFirstResponder];
}
return YES;
}
Hope this will help you.
Call
[yourTextField resignFirstResponder]
on all other textfields to make their keyboard disappear.
use the resignFirstResponder methods and the text fields. [textField resignFirstResponder] that will hide the keyboard.
Then use a Notification when keyboard becomes visible and have a boolean called isPickerVisible.When picker becomes visible set isPickerVisible to TRUE.
In the keyboardDidShow method check whether picker is visible or not. If it is visible then hide it.
Adding a notification:[[NSNotificationCenter defaultCenter] addObserver:self
selector:#selector(keyboardDidShow:)
name:UIKeyboardWillShowNotification
object:nil];
And the method...
- (void)keyboardDidShow:(NSNotification*)notif {
if(isPickerVisible) {
[self hidePicker];
}
}
Hope this helped...
In - (BOOL)textFieldShouldBeginEditing:(UITextField *)textField method use resignFirstResponder for all the textfield except the third textFied:-
- (BOOL)textFieldShouldBeginEditing:(UITextField *)textField
{
if(textField==thirdTextField)
{
[firstTextField resignFirstResponder];
[secondTextField resignFirstResponder];
[textField resignFirstResponder];
[self showPickerView];
}
return YES;
}