13

我目前在键盘顶部有一个 UITextField 。当您点击它时,它应该会粘在键盘顶部并平稳地向上移动。我不知道键盘的确切时长和动画类型,所以真的很坎坷。这是我所拥有的:

[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];

如果有人以前做过这样的事情,我想知道你用来使动画流畅的设置,并让它看起来像是“卡”在键盘的顶部。

4

4 回答 4

46

UIKitUIKeyboardWillShowNotification在显示键盘和UIKeyboardWillHideNotification隐藏键盘时发布。这些通知包含正确设置UITextField.

假设您UITextField在一个名为 called 的属性中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];
}

如果您使用 aUIViewController来移动字段,您可能希望在viewWillAppear:animated:.

您应该在您的deallocor中取消注册viewWillDisappear:animated:

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

当然,棘手的地方在于keyboardWillHideOrShow:方法。首先我从通知中提取动画参数:

- (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.frame位于以下坐标系中myTextField.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];
}
于 2012-01-02T19:04:18.660 回答
5

将您的文本字段(或包含文本字段的视图)设置为inputAccessoryView您正在编辑的字段。然后它会自动连接到键盘的顶部并进行适当的动画处理。

于 2012-01-02T19:11:48.310 回答
0

为了使 UITextField 停靠到键盘(带有动画),您需要使用方法进行偏移计算并在滚动视图上应用偏移更改(假设 UITextField 放置在 UIScrollView 中)setContentOffset:animation:

于 2012-01-02T18:42:21.833 回答
0

在键盘通知中使用此代码:

@objc func keyboardWillShowNotification(notification: Notification) {
    let keyboardHeight = (notification.userInfo?[UIKeyboardFrameEndUserInfoKey] as? NSValue)?.cgRectValue.size.height ?? 216
    let duration = notification.userInfo?[UIKeyboardAnimationDurationUserInfoKey] as? Double ?? 0.25
    let curve = (notification.userInfo?[UIKeyboardAnimationCurveUserInfoKey] as? UInt ?? 7) << 16
    tableViewBottomConstraint.constant = keyboardHeight - submitButtonContainer.frame.size.height

    UIView.animate(withDuration: duration, delay: 0, options: [UIViewAnimationOptions(rawValue: curve)], animations: {
        // Animation
    }, completion: nil)
}
于 2018-07-19T05:29:11.613 回答