12

我目前在鍵盤上有一個UITextField。當你敲擊它時,它應該粘在鍵盤的頂部並順利地向上移動。我不知道鍵盤的確切持續時間和動畫類型,所以它真的很顛簸。下面是我有:在becomeFirstResponder或resignFirstResponder事件中將對象保留在鍵盤上?

[theTextView resignFirstResponder]; 
[UIView beginAnimations:nil context:NULL]; 
[UIView setAnimationDelegate:self]; 
[UIView setAnimationDuration:0.25]; 
[UIView setAnimationCurve:UIViewAnimationCurveLinear]; 
// Frame changes go here (move down 216px) 
[UIView commitAnimations]; 

[theTextView becomeFirstResponder]; 
[UIView beginAnimations:nil context:NULL]; 
[UIView setAnimationDelegate:self]; 
[UIView setAnimationDuration:0.25]; 
[UIView setAnimationCurve:UIViewAnimationCurveLinear]; 
// Frame changes go here (move up 216px) 
[UIView commitAnimations]; 

如果有人做過這樣的事情,我想知道你用來做動畫光滑,使它看起來,酒吧的「粘」的頂部設置鍵盤。

回答

44

UIKit在顯示鍵盤時發帖UIKeyboardWillShowNotification,在隱藏鍵盤時發帖UIKeyboardWillHideNotification。這些通知包含您爲使UITextField正確動畫所需的一切。

假設您的UITextField位於名爲myTextField的屬性中。

首先,您需要在某處註冊通知。你在哪裏註冊取決於什麼對象負責移動myTextField。在我的項目,該領域的上海華負責,因爲我從筆尖加載我的UI,我這樣做是在上海華的awakeFromNib

- (void)awakeFromNib 
{ 
    [[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(keyboardWillHideOrShow:) name:UIKeyboardWillHideNotification object:nil]; 
    [[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(keyboardWillHideOrShow:) name:UIKeyboardWillShowNotification object:nil]; 
} 

如果使用UIViewController左右移動領域,你可能會想要在viewWillAppear:animated:中做到這一點。

- (void)dealloc 
{ 
    [[NSNotificationCenter defaultCenter] removeObserver:self]; 
} 

當然棘手位是keyboardWillHideOrShow:方法:

你應該在你deallocviewWillDisappear:animated:註銷。首先,我從通知中提取動畫參數:

- (void)keyboardWillHideOrShow:(NSNotification *)note 
{ 
    NSDictionary *userInfo = note.userInfo; 
    NSTimeInterval duration = [[userInfo objectForKey:UIKeyboardAnimationDurationUserInfoKey] doubleValue]; 
    UIViewAnimationCurve curve = [[userInfo objectForKey:UIKeyboardAnimationCurveUserInfoKey] intValue]; 

    CGRect keyboardFrame = [[userInfo objectForKey:UIKeyboardFrameEndUserInfoKey] CGRectValue]; 

keyboardFrame是全局座標系統相同。我需要的幀轉換到同一座標系myTextField.frame,並且myTextField.framemyTextField.superview座標系中:

CGRect keyboardFrameForTextField = [self.myTextField.superview convertRect:keyboardFrame fromView:nil]; 

接下來,我計算,我想myTextField移動到框架。新框架的底部邊緣應等於鍵盤的框架的頂邊:

CGRect newTextFieldFrame = self.myTextField.frame; 
    newTextFieldFrame.origin.y = keyboardFrameForTextField.origin.y - newTextFieldFrame.size.height; 

最後,我動畫myTextField其新幀,使用相同的動畫參數,該鍵盤使用:

[UIView animateWithDuration:duration delay:0 options:UIViewAnimationOptionBeginFromCurrentState | curve animations:^{ 
     self.myTextField.frame = newTextFieldFrame; 
    } completion:nil]; 
} 

這一切放在一起:

- (void)keyboardWillHideOrShow:(NSNotification *)note 
{ 
    NSDictionary *userInfo = note.userInfo; 
    NSTimeInterval duration = [[userInfo objectForKey:UIKeyboardAnimationDurationUserInfoKey] doubleValue]; 
    UIViewAnimationCurve curve = [[userInfo objectForKey:UIKeyboardAnimationCurveUserInfoKey] intValue]; 

    CGRect keyboardFrame = [[userInfo objectForKey:UIKeyboardFrameEndUserInfoKey] CGRectValue]; 
    CGRect keyboardFrameForTextField = [self.myTextField.superview convertRect:keyboardFrame fromView:nil]; 

    CGRect newTextFieldFrame = self.myTextField.frame; 
    newTextFieldFrame.origin.y = keyboardFrameForTextField.origin.y - newTextFieldFrame.size.height; 

    [UIView animateWithDuration:duration delay:0 options:UIViewAnimationOptionBeginFromCurrentState | curve animations:^{ 
     self.myTextField.frame = newTextFieldFrame; 
    } completion:nil]; 
} 
+1

謝謝。謝謝。謝謝。謝謝。稍作修改,我就可以工作,它看起來非常漂亮。 – iosfreak 2012-01-05 21:34:31

+0

@rob mayoff問題是當我有一個'UITabBar'。當鍵盤將「UITextField」隱藏在「UITabBar」下面時。爲什麼? – 2012-02-05 20:41:28

+0

如果您有一個標籤欄,那麼當鍵盤隱藏時,您需要根據標籤欄的框架而不是鍵盤的框架來計算'newTextFieldFrame'。 – 2012-02-05 21:30:04

0

爲了使UITextField停靠在鍵盤上(使用動畫),您需要使用setContentOffset:animation:方法進行偏移量計算並在滾動視圖上應用偏移更改(假設UITextField位於UIScrollView中)。

+0

它不在ScrollView中。一個scrollView甚至不存在,它是一個UITableView。 – iosfreak 2012-01-02 18:49:31

+2

@ phpnerd211:UITableView是UIScrollView的子類。 – Andrew 2013-07-19 07:46:00

5

設置你的文本字段(或持有該文本字段的視圖)作爲域的inputAccessoryView那你正在編輯。然後它會自動粘貼到鍵盤的頂部並適當地進行動畫。