Efectuarea unui parcurgere UITableView când este selectat câmpul de text

voturi
228

După o mulțime de studiu și de eroare, eu renunț și a pune întrebarea. Am văzut o mulțime de oameni cu probleme similare, dar nu pot obține toate răspunsurile la locul de muncă dreapta.

Am o UITableViewcare este compus din celule personalizate. Celulele sunt realizate din 5 câmpuri text unul lângă altul (ca un fel de grilă).

Când încerc să defila și edita celulele de la partea de jos a UITableView, nu pot gestiona pentru a obține celulele mele poziționate corect deasupra tastaturii.

Am văzut multe răspunsuri vorbesc despre schimbarea dimensiunile, etc ... dar nici unul dintre ei a lucrat bine până acum.

Ar putea cineva să clarifice modul în care „dreptul“ de a face acest lucru cu un exemplu concret de cod?

Întrebat 27/02/2009 la 11:05
sursa de către utilizator
În alte limbi...                            


48 răspunsuri

voturi
110

Dacă utilizați UITableViewController în loc de UIViewController, se va face automat acest lucru.

Publicat 21/09/2010 la 04:42
sursa de către utilizator

voturi
89

Funcția care face defilare ar putea fi mult mai simplu:

- (void) textFieldDidBeginEditing:(UITextField *)textField {
    UITableViewCell *cell;

    if (floor(NSFoundationVersionNumber) <= NSFoundationVersionNumber_iOS_6_1) {
    // Load resources for iOS 6.1 or earlier
        cell = (UITableViewCell *) textField.superview.superview;

    } else {
        // Load resources for iOS 7 or later
        cell = (UITableViewCell *) textField.superview.superview.superview; 
       // TextField -> UITableVieCellContentView -> (in iOS 7!)ScrollView -> Cell!
    }
    [tView scrollToRowAtIndexPath:[tView indexPathForCell:cell] atScrollPosition:UITableViewScrollPositionTop animated:YES];
}

Asta e. Nu există calcule la toate.

Publicat 15/04/2009 la 13:21
sursa de către utilizator

voturi
65

Fac ceva foarte asemănător este generic, nu este nevoie pentru a calcula ceva specific pentru codul. Doar verifica remarci cu privire la codul:

În MyUIViewController.h

@interface MyUIViewController: UIViewController <UITableViewDelegate, UITableViewDataSource>
{
     UITableView *myTableView;
     UITextField *actifText;
}

@property (nonatomic, retain) IBOutlet UITableView *myTableView;
@property (nonatomic, retain) IBOutlet UITextField *actifText;

- (IBAction)textFieldDidBeginEditing:(UITextField *)textField;
- (IBAction)textFieldDidEndEditing:(UITextField *)textField;

-(void) keyboardWillHide:(NSNotification *)note;
-(void) keyboardWillShow:(NSNotification *)note;

@end

În MyUIViewController.m

@implementation MyUIViewController

@synthesize myTableView;
@synthesize actifText;

- (void)viewDidLoad 
{
    // Register notification when the keyboard will be show
    [[NSNotificationCenter defaultCenter] addObserver:self
                                          selector:@selector(keyboardWillShow:)
                                          name:UIKeyboardWillShowNotification
                                          object:nil];

    // Register notification when the keyboard will be hide
    [[NSNotificationCenter defaultCenter] addObserver:self
                                          selector:@selector(keyboardWillHide:)
                                          name:UIKeyboardWillHideNotification
                                          object:nil];
}

// To be link with your TextField event "Editing Did Begin"
//  memoryze the current TextField
- (IBAction)textFieldDidBeginEditing:(UITextField *)textField
{
    self.actifText = textField;
}

// To be link with your TextField event "Editing Did End"
//  release current TextField
- (IBAction)textFieldDidEndEditing:(UITextField *)textField
{
    self.actifText = nil;
}

-(void) keyboardWillShow:(NSNotification *)note
{
    // Get the keyboard size
    CGRect keyboardBounds;
    [[note.userInfo valueForKey:UIKeyboardFrameBeginUserInfoKey] getValue: &keyboardBounds];

    // Detect orientation
    UIInterfaceOrientation orientation = [[UIApplication sharedApplication] statusBarOrientation];
    CGRect frame = self.myTableView.frame;

    // Start animation
    [UIView beginAnimations:nil context:NULL];
    [UIView setAnimationBeginsFromCurrentState:YES];
    [UIView setAnimationDuration:0.3f];

    // Reduce size of the Table view 
    if (orientation == UIInterfaceOrientationPortrait || orientation == UIInterfaceOrientationPortraitUpsideDown)
        frame.size.height -= keyboardBounds.size.height;
    else 
        frame.size.height -= keyboardBounds.size.width;

    // Apply new size of table view
    self.myTableView.frame = frame;

    // Scroll the table view to see the TextField just above the keyboard
    if (self.actifText)
      {
        CGRect textFieldRect = [self.myTableView convertRect:self.actifText.bounds fromView:self.actifText];
        [self.myTableView scrollRectToVisible:textFieldRect animated:NO];
      }

    [UIView commitAnimations];
}

-(void) keyboardWillHide:(NSNotification *)note
{
    // Get the keyboard size
    CGRect keyboardBounds;
    [[note.userInfo valueForKey:UIKeyboardFrameBeginUserInfoKey] getValue: &keyboardBounds];

    // Detect orientation
    UIInterfaceOrientation orientation = [[UIApplication sharedApplication] statusBarOrientation];
    CGRect frame = self.myTableView.frame;

    [UIView beginAnimations:nil context:NULL];
    [UIView setAnimationBeginsFromCurrentState:YES];
    [UIView setAnimationDuration:0.3f];

    // Increase size of the Table view 
    if (orientation == UIInterfaceOrientationPortrait || orientation == UIInterfaceOrientationPortraitUpsideDown)
        frame.size.height += keyboardBounds.size.height;
    else 
        frame.size.height += keyboardBounds.size.width;

    // Apply new size of table view
    self.myTableView.frame = frame;

    [UIView commitAnimations];
}

@end

Swift 1.2+ versiune:

class ViewController: UIViewController, UITextFieldDelegate {
    @IBOutlet weak var activeText: UITextField!
    @IBOutlet weak var tableView: UITableView!

    override func viewDidLoad() {
        NSNotificationCenter.defaultCenter().addObserver(self,
            selector: Selector("keyboardWillShow:"),
            name: UIKeyboardWillShowNotification,
            object: nil)
        NSNotificationCenter.defaultCenter().addObserver(self,
            selector: Selector("keyboardWillHide:"),
            name: UIKeyboardWillHideNotification,
            object: nil)
    }

    func textFieldDidBeginEditing(textField: UITextField) {
        activeText = textField
    }

    func textFieldDidEndEditing(textField: UITextField) {
        activeText = nil
    }

    func keyboardWillShow(note: NSNotification) {
        if let keyboardSize = (note.userInfo?[UIKeyboardFrameBeginUserInfoKey] as? NSValue)?.CGRectValue() {
            var frame = tableView.frame
            UIView.beginAnimations(nil, context: nil)
            UIView.setAnimationBeginsFromCurrentState(true)
            UIView.setAnimationDuration(0.3)
            frame.size.height -= keyboardSize.height
            tableView.frame = frame
            if activeText != nil {
                let rect = tableView.convertRect(activeText.bounds, fromView: activeText)
                tableView.scrollRectToVisible(rect, animated: false)
            }
            UIView.commitAnimations()
        }
    }

    func keyboardWillHide(note: NSNotification) {
        if let keyboardSize = (note.userInfo?[UIKeyboardFrameBeginUserInfoKey] as? NSValue)?.CGRectValue() {
            var frame = tableView.frame
            UIView.beginAnimations(nil, context: nil)
            UIView.setAnimationBeginsFromCurrentState(true)
            UIView.setAnimationDuration(0.3)
            frame.size.height += keyboardSize.height
            tableView.frame = frame
            UIView.commitAnimations()
        }
    }
}
Publicat 13/04/2010 la 15:46
sursa de către utilizator

voturi
41

Am avut aceeași problemă, dar a observat că apare doar într-o singură vizualizare. Așa că am început să caute diferențele controlorilor.

Am aflat că comportamentul de defilare este stabilit în - (void)viewWillAppear:(BOOL)animatedal super - instanță.

Deci, asigurați-vă că pentru a pune în aplicare astfel:

- (void)viewWillAppear:(BOOL)animated {
    [super viewWillAppear:animated];
    // your code
}

Și nu contează dacă utilizați UIViewControllersau UITableViewController; verificat prin punerea unei UITableViewca subview a self.view în UIViewController. Acesta a fost același comportament. Punctul de vedere nu a permis pentru a defila în cazul în care apelul a [super viewWillAppear:animated];fost lipsă.

Publicat 29/05/2011 la 01:42
sursa de către utilizator

voturi
37

am ratat acest lucru, deoarece nu am citit întregul post aici, dar ceea ce am venit cu pare inselator de simplu. nu am pus acest lucru prin storcător, testarea în toate situațiile, dar se pare ca ar trebui să funcționeze bine.

pur și simplu a regla contentInset a tableview de înălțimea tastaturii, și apoi derulați celula la partea de jos:

- (void)keyboardWasShown:(NSNotification *)aNotification
{
    NSDictionary* info = [aNotification userInfo];
    CGSize kbSize = [[info objectForKey:UIKeyboardFrameBeginUserInfoKey] CGRectValue].size;

    UIEdgeInsets contentInsets = UIEdgeInsetsMake(0.0, 0.0, kbSize.height, 0.0);
    self.myTableView.contentInset = contentInsets;
    self.myTableView.scrollIndicatorInsets = contentInsets;

    [self.myTableView scrollToRowAtIndexPath:self.currentField.indexPath atScrollPosition:UITableViewScrollPositionBottom animated:YES];
}

și, desigur

- (void)keyboardWasHidden:(NSNotification *)aNotification
{
    [UIView animateWithDuration:.3 animations:^(void) 
    {
        self.myTableView.contentInset = UIEdgeInsetsZero;
        self.myTableView.scrollIndicatorInsets = UIEdgeInsetsZero;
    }];
}

este acest lucru prea simplu? am pierdut ceva? până în prezent este de lucru pentru mine bine, dar, așa cum am spus, nu am pus-o prin storcător ...

Publicat 18/08/2012 la 01:12
sursa de către utilizator

voturi
35

Cea mai simplă soluție pentru Swift 3 , bazată pe soluție Bartłomiej Semańczyk :

override func viewDidLoad() {
    super.viewDidLoad()

    NotificationCenter.default.addObserver(self, selector: #selector(CreateEditRitualViewController.keyboardWillShow(notification:)), name: NSNotification.Name.UIKeyboardDidShow, object: nil)
    NotificationCenter.default.addObserver(self, selector: #selector(CreateEditRitualViewController.keyboardWillHide(notification:)), name: NSNotification.Name.UIKeyboardDidHide, object: nil)
}

deinit {
    NotificationCenter.default.removeObserver(self)
}

// MARK: Keyboard Notifications

@objc func keyboardWillShow(notification: NSNotification) {
    if let keyboardHeight = (notification.userInfo?[UIKeyboardFrameEndUserInfoKey] as? NSValue)?.cgRectValue.height {
        tableView.contentInset = UIEdgeInsetsMake(0, 0, keyboardHeight, 0)
    }
}

@objc func keyboardWillHide(notification: NSNotification) {
    UIView.animate(withDuration: 0.2, animations: {
        // For some reason adding inset in keyboardWillShow is animated by itself but removing is not, that's why we have to use animateWithDuration here
        self.tableView.contentInset = UIEdgeInsetsMake(0, 0, 0, 0)
    })
}
Publicat 08/12/2016 la 13:26
sursa de către utilizator

voturi
34

Dacă puteți utiliza UITableViewController, veți obține funcționalitatea gratuit. Uneori, cu toate acestea, acest lucru nu este o opțiune, în special dacă aveți nevoie de mai multe puncte de vedere , nu doar UITableView.

Unele dintre soluțiile prezentate aici nu funcționează pe iOS ≥4, unele nu funcționează pe iPad sau în modul peisaj, unele nu funcționează pentru tastaturi Bluetooth ( în cazul în care nu vrem nici o defilare), unele nu lucra la comutarea între câmpuri de text multiple. Deci , dacă alegeți orice soluție, asigurați - vă că pentru a testa aceste cazuri. Aceasta este soluția ne folosim folosită în InAppSettingsKit :

- (void)_keyboardWillShow:(NSNotification*)notification {
    if (self.navigationController.topViewController == self) {
        NSDictionary* userInfo = [notification userInfo];

        // we don't use SDK constants here to be universally compatible with all SDKs ≥ 3.0
        NSValue* keyboardFrameValue = [userInfo objectForKey:@"UIKeyboardBoundsUserInfoKey"];
        if (!keyboardFrameValue) {
            keyboardFrameValue = [userInfo objectForKey:@"UIKeyboardFrameEndUserInfoKey"];
        }

        // Reduce the tableView height by the part of the keyboard that actually covers the tableView
        CGRect windowRect = [[UIApplication sharedApplication] keyWindow].bounds;
        if (UIInterfaceOrientationLandscapeLeft == self.interfaceOrientation ||UIInterfaceOrientationLandscapeRight == self.interfaceOrientation ) {
            windowRect = IASKCGRectSwap(windowRect);
        }
        CGRect viewRectAbsolute = [_tableView convertRect:_tableView.bounds toView:[[UIApplication sharedApplication] keyWindow]];
        if (UIInterfaceOrientationLandscapeLeft == self.interfaceOrientation ||UIInterfaceOrientationLandscapeRight == self.interfaceOrientation ) {
            viewRectAbsolute = IASKCGRectSwap(viewRectAbsolute);
        }
        CGRect frame = _tableView.frame;
        frame.size.height -= [keyboardFrameValue CGRectValue].size.height - CGRectGetMaxY(windowRect) + CGRectGetMaxY(viewRectAbsolute);

        [UIView beginAnimations:nil context:NULL];
        [UIView setAnimationDuration:[[userInfo objectForKey:UIKeyboardAnimationDurationUserInfoKey] doubleValue]];
        [UIView setAnimationCurve:[[userInfo objectForKey:UIKeyboardAnimationCurveUserInfoKey] intValue]];
        _tableView.frame = frame;
        [UIView commitAnimations];

        UITableViewCell *textFieldCell = (id)((UITextField *)self.currentFirstResponder).superview.superview;
        NSIndexPath *textFieldIndexPath = [_tableView indexPathForCell:textFieldCell];

        // iOS 3 sends hide and show notifications right after each other
        // when switching between textFields, so cancel -scrollToOldPosition requests
        [NSObject cancelPreviousPerformRequestsWithTarget:self];

        [_tableView scrollToRowAtIndexPath:textFieldIndexPath atScrollPosition:UITableViewScrollPositionMiddle animated:YES];
    }
}

- (void) scrollToOldPosition {
  [_tableView scrollToRowAtIndexPath:_topmostRowBeforeKeyboardWasShown atScrollPosition:UITableViewScrollPositionTop animated:YES];
}

- (void)_keyboardWillHide:(NSNotification*)notification {
    if (self.navigationController.topViewController == self) {
        NSDictionary* userInfo = [notification userInfo];

        [UIView beginAnimations:nil context:NULL];
        [UIView setAnimationDuration:[[userInfo objectForKey:UIKeyboardAnimationDurationUserInfoKey] doubleValue]];
        [UIView setAnimationCurve:[[userInfo objectForKey:UIKeyboardAnimationCurveUserInfoKey] intValue]];
        _tableView.frame = self.view.bounds;
        [UIView commitAnimations];

        [self performSelector:@selector(scrollToOldPosition) withObject:nil afterDelay:0.1];
    }
}   

Iată codul complet al clasei în InAppSettingsKit. Pentru a testa, utilizați „Lista completă“ în cazul în care panoul de copil vă puteți testa scenariile menționate mai sus.

Publicat 13/12/2010 la 17:01
sursa de către utilizator

voturi
34

Cred că am venit cu soluția pentru a se potrivi comportamentul de aplicații Apple.

În primul rând, în viewWillAppear dumneavoastră: abona la notificările de la tastatură, astfel încât să știi când tastatura va afișa și ascunde, iar sistemul vă va spune dimensiunea tastaturii, dar dont“uita să te retragi în viewWillDisappear ta :.

[[NSNotificationCenter defaultCenter]
    addObserver:self
       selector:@selector(keyboardWillShow:)
           name:UIKeyboardWillShowNotification
         object:nil];
[[NSNotificationCenter defaultCenter]
    addObserver:self
       selector:@selector(keyboardWillHide:)
           name:UIKeyboardWillHideNotification
         object:nil];

Punerea în aplicare a metodelor similare cu mai jos, astfel încât să ajustați dimensiunea tableView pentru a se potrivi zona vizibilă o dată arată tastatură. Aici am de urmărire starea tastaturii separat, astfel încât să pot alege când pentru a seta tableView înapoi la înălțime completă mine, din moment ce obține aceste notificări la fiecare schimbare de teren. Nu uitați să pună în aplicare keyboardWillHide: și alegeți undeva necesar să se stabilească dimensiunea tableView.

-(void) keyboardWillShow:(NSNotification *)note
{
    CGRect keyboardBounds;
    [[note.userInfo valueForKey:UIKeyboardBoundsUserInfoKey] getValue: &keyboardBounds];
    keyboardHeight = keyboardBounds.size.height;
    if (keyboardIsShowing == NO)
    {
        keyboardIsShowing = YES;
        CGRect frame = self.view.frame;
        frame.size.height -= keyboardHeight;

        [UIView beginAnimations:nil context:NULL];
        [UIView setAnimationBeginsFromCurrentState:YES];
        [UIView setAnimationDuration:0.3f];
        self.view.frame = frame;
        [UIView commitAnimations];
    }
}

Acum, aici e bitul de defilare, vom lucra câteva dimensiuni mai întâi, apoi vom vedea unde ne aflăm în zona vizibilă, și setați rect dorim să defila la a fi fie o jumătate de vedere de mai sus sau mai jos mijlocul câmpului bazat pe text pe unde se află în punctul de vedere. În acest caz, avem o serie de UITextFields și un enum care ține evidența acestora, astfel încât înmulțirea rowHeight cu numărul rândului ne oferă reale de offset a cadrului în cadrul acestui punct de vedere exterior.

- (void) textFieldDidBeginEditing:(UITextField *)textField
{
    CGRect frame = textField.frame;
    CGFloat rowHeight = self.tableView.rowHeight;
    if (textField == textFields[CELL_FIELD_ONE])
    {
        frame.origin.y += rowHeight * CELL_FIELD_ONE;
    }
    else if (textField == textFields[CELL_FIELD_TWO])
    {
        frame.origin.y += rowHeight * CELL_FIELD_TWO;
    }
    else if (textField == textFields[CELL_FIELD_THREE])
    {
        frame.origin.y += rowHeight * CELL_FIELD_THREE;
    }
    else if (textField == textFields[CELL_FIELD_FOUR])
    {
        frame.origin.y += rowHeight * CELL_FIELD_FOUR;
    }
    CGFloat viewHeight = self.tableView.frame.size.height;
    CGFloat halfHeight = viewHeight / 2;
    CGFloat midpoint = frame.origin.y + (textField.frame.size.height / 2);
    if (midpoint < halfHeight)
    {
        frame.origin.y = 0;
        frame.size.height = midpoint;
    }
    else
    {
        frame.origin.y = midpoint;
        frame.size.height = midpoint;
    }
    [self.tableView scrollRectToVisible:frame animated:YES];
}

Acest lucru pare să funcționeze destul de bine.

Publicat 23/03/2009 la 02:49
sursa de către utilizator

voturi
22

Cea mai simplă soluție pentru Swift :

override func viewDidLoad() {
    super.viewDidLoad()

    searchBar?.becomeFirstResponder()
    NSNotificationCenter.defaultCenter().addObserver(self, selector: #selector(MyViewController.keyboardWillShow(_:)), name: UIKeyboardDidShowNotification, object: nil)
    NSNotificationCenter.defaultCenter().addObserver(self, selector: #selector(MyViewController.keyboardWillHide(_:)), name: UIKeyboardDidHideNotification, object: nil)
}

deinit {
    NSNotificationCenter.defaultCenter().removeObserver(self)
}

func keyboardWillShow(notification: NSNotification) {
    if let userInfo = notification.userInfo {
        if let keyboardHeight = userInfo[UIKeyboardFrameEndUserInfoKey]?.CGRectValue.size.height {
            tableView.contentInset = UIEdgeInsetsMake(0, 0, keyboardHeight, 0)
        }
    }
}

func keyboardWillHide(notification: NSNotification) {
    UIView.animateWithDuration(0.2, animations: { self.table_create_issue.contentInset = UIEdgeInsetsMake(0, 0, 0, 0) })
    // For some reason adding inset in keyboardWillShow is animated by itself but removing is not, that's why we have to use animateWithDuration here
    }
Publicat 25/08/2015 la 06:42
sursa de către utilizator

voturi
6

Sper că voi aveți deja o soluție pentru a citi toate acestea. Dar am găsit soluția mea , după cum urmează. Mă aștept că aveți deja o celulă cu UITextField. Deci , la pregătirea păstra doar indexul rând în eticheta câmpul textului.

cell.textField.tag = IndexPath.row;

Creați o activeTextField, de exemplu , UITextFieldcu domeniu de aplicare la nivel mondial ca mai jos:

@interface EditViewController (){

    UITextField *activeTextField;

}

Deci, acum copiați pur și simplu inserați codul meu la sfârșitul anului. Și, de asemenea, nu uitați să adăugațiUITextFieldDelegate

#pragma mark - TextField Delegation

- (BOOL)textFieldShouldBeginEditing:(UITextField *)textField{

    activeTextField = textField;

    return YES;
}

- (void)textFieldDidEndEditing:(UITextField *)textField{

    activeTextField = nil;

}

Registrele tastatură notifications

#pragma mark - Keyboard Activity

- (void)registerForKeyboardNotifications

{

    [[NSNotificationCenter defaultCenter] addObserver:self

                                         selector:@selector(keyboardWasShown:)

                                             name:UIKeyboardDidShowNotification object:nil];



    [[NSNotificationCenter defaultCenter] addObserver:self

                                         selector:@selector(keyboardWillBeHidden:)

                                             name:UIKeyboardWillHideNotification object:nil];



}

Manere Tastatură Notifications:

Apelată când UIKeyboardDidShowNotificationeste trimis.

- (void)keyboardWasShown:(NSNotification*)aNotification

{

    NSDictionary* info = [aNotification userInfo];

    CGSize kbSize = [[info objectForKey:UIKeyboardFrameBeginUserInfoKey] CGRectValue].size;

    UIEdgeInsets contentInsets = UIEdgeInsetsMake(0.0, 0.0, kbSize.height, 0.0);

    [self.tableView setContentInset:contentInsets];

    [self.tableView setScrollIndicatorInsets:contentInsets];

    NSIndexPath *currentRowIndex = [NSIndexPath indexPathForRow:activeTextField.tag inSection:0];

    [self.tableView scrollToRowAtIndexPath:currentRowIndex atScrollPosition:UITableViewScrollPositionTop animated:YES];

}

Apelată când UIKeyboardWillHideNotificationeste trimis

- (void)keyboardWillBeHidden:(NSNotification*)aNotification

{

    UIEdgeInsets contentInsets = UIEdgeInsetsZero;

    [self.tableView setContentInset:contentInsets];

    [self.tableView setScrollIndicatorInsets:contentInsets];

}

Acum , un singur lucru este lăsat, apelați registerForKeyboardNotificationsmetoda la ViewDidLoadmetoda după cum urmează:

- (void)viewDidLoad {

    [super viewDidLoad];

    // Registering keyboard notification

    [self registerForKeyboardNotifications];

    // Your codes here...

}

Ați terminat, speranța ta textFieldsnu va mai ascuns de tastatura.

Publicat 03/01/2015 la 21:36
sursa de către utilizator

voturi
6

Combinarea și completând spațiile libere din mai multe răspunsuri (în special Ortwin Gentz, utilizator 98013) și un alt post, aceasta va funcționa din cutie pentru SDK 4.3 pe un iPad în modul Portret sau Vedere:

@implementation UIView (FindFirstResponder)
- (UIResponder *)findFirstResponder
{
  if (self.isFirstResponder) {        
    return self;     
  }

  for (UIView *subView in self.subviews) {
    UIResponder *firstResponder = [subView findFirstResponder];
    if (firstResponder != nil) {
      return firstResponder;
    }
  }

  return nil;
}
@end

@implementation MyViewController

- (UIResponder *)currentFirstResponder {
  return [self.view findFirstResponder];
}

- (IBAction)editingEnded:sender {
  [sender resignFirstResponder];
}

- (BOOL)textFieldShouldReturn:(UITextField *)textField {
  [textField resignFirstResponder];
  return NO;
}

- (void)textFieldDidBeginEditing:(UITextField *)textField {
  UITableViewCell *cell = (UITableViewCell*) [[textField superview] superview];
  [_tableView scrollToRowAtIndexPath:[_tableView indexPathForCell:cell] atScrollPosition:UITableViewScrollPositionTop animated:YES];
}

- (void)keyboardWillShow:(NSNotification*)notification {
  if ([self currentFirstResponder] != nil) {
    NSDictionary* userInfo = [notification userInfo];

    // we don't use SDK constants here to be universally compatible with all SDKs ≥ 3.0
    NSValue* keyboardFrameValue = [userInfo objectForKey:@"UIKeyboardBoundsUserInfoKey"];
    if (!keyboardFrameValue) {
      keyboardFrameValue = [userInfo objectForKey:@"UIKeyboardFrameEndUserInfoKey"];
    }

    // Reduce the tableView height by the part of the keyboard that actually covers the tableView
    CGRect windowRect = [[UIApplication sharedApplication] keyWindow].bounds;
    CGRect viewRectAbsolute = [_tableView convertRect:_tableView.bounds toView:[[UIApplication sharedApplication] keyWindow]];
    CGRect frame = _tableView.frame;
    if (UIInterfaceOrientationLandscapeLeft == self.interfaceOrientation ||UIInterfaceOrientationLandscapeRight == self.interfaceOrientation ) {
      windowRect = CGRectMake(windowRect.origin.y, windowRect.origin.x, windowRect.size.height, windowRect.size.width);
      viewRectAbsolute = CGRectMake(viewRectAbsolute.origin.y, viewRectAbsolute.origin.x, viewRectAbsolute.size.height, viewRectAbsolute.size.width);
    }
    frame.size.height -= [keyboardFrameValue CGRectValue].size.height - CGRectGetMaxY(windowRect) + CGRectGetMaxY(viewRectAbsolute);

    [UIView beginAnimations:nil context:NULL];
    [UIView setAnimationDuration:[[userInfo objectForKey:UIKeyboardAnimationDurationUserInfoKey] doubleValue]];
    [UIView setAnimationCurve:[[userInfo objectForKey:UIKeyboardAnimationCurveUserInfoKey] intValue]];
    _tableView.frame = frame;
    [UIView commitAnimations];

    UITableViewCell *textFieldCell = (id)((UITextField *)self.currentFirstResponder).superview.superview;
    NSIndexPath *textFieldIndexPath = [_tableView indexPathForCell:textFieldCell];

    // iOS 3 sends hide and show notifications right after each other
    // when switching between textFields, so cancel -scrollToOldPosition requests
    [NSObject cancelPreviousPerformRequestsWithTarget:self];
    _topmostRowBeforeKeyboardWasShown = [[_tableView indexPathsForVisibleRows] objectAtIndex:0];
    [_tableView scrollToRowAtIndexPath:textFieldIndexPath atScrollPosition:UITableViewScrollPositionMiddle animated:YES];
  }
}

- (void) scrollToOldPosition {
  [_tableView scrollToRowAtIndexPath:_topmostRowBeforeKeyboardWasShown atScrollPosition:UITableViewScrollPositionTop animated:YES];
}

- (void)keyboardWillHide:(NSNotification*)notification {
  if ([self currentFirstResponder] != nil) {

    NSDictionary* userInfo = [notification userInfo];

    [UIView beginAnimations:nil context:NULL];
    [UIView setAnimationDuration:[[userInfo objectForKey:UIKeyboardAnimationDurationUserInfoKey] doubleValue]];
    [UIView setAnimationCurve:[[userInfo objectForKey:UIKeyboardAnimationCurveUserInfoKey] intValue]];
    _tableView.frame = self.view.bounds;
    [UIView commitAnimations];

    [self performSelector:@selector(scrollToOldPosition) withObject:nil afterDelay:0.1];
  }
}   

@end
Publicat 03/08/2011 la 03:35
sursa de către utilizator

voturi
5

Abordarea mea:

Am subclasa prima UITextField și adăugați o proprietate indexPath. În cellFor ... Metoda i preda proprietatea indexPath.

Apoi am adăuga următorul cod:

UITableViewCell *cell = [self.tableView cellForRowAtIndexPath:textField.indexPath];

CGPoint cellPoint = [cell convertPoint:textField.center toView:self.tableView];
[UIView animateWithDuration:0.3 animations:^(void){self.tableView.contentOffset = CGPointMake(0, cellPoint.y-50);}];

la textFieldShould / WillBegin ... etc.

Când tastatura dispare, trebuie să-l inversa cu:

[UIView animateWithDuration:0.3 animations:^(void){self.tableView.contentOffset = CGPointMake(0, 0);}];
Publicat 29/09/2012 la 13:03
sursa de către utilizator

voturi
4

Utilizați UITextField's delegatemetoda:

Rapid

func textFieldShouldBeginEditing(textField: UITextField) -> bool {
  let txtFieldPosition = textField.convertPoint(textField.bounds.origin, toView: yourTableViewHere)
  let indexPath = yourTablViewHere.indexPathForRowAtPoint(txtFieldPosition)
  if indexPath != nil {
     yourTablViewHere.scrollToRowAtIndexPath(indexPath!, atScrollPosition: .Top, animated: true)
  }
  return true
}

Obiectiv-C

- (BOOL)textFieldShouldBeginEditing:(UITextField *)textField
{
  CGPoint txtFieldPosition = [textField convertPoint:CGPointZero toView: yourTablViewHere];
  NSLog(@"Begin txtFieldPosition : %@",NSStringFromCGPoint(txtFieldPosition));
  NSIndexPath *indexPath = [yourTablViewHere indexPathForRowAtPoint:txtFieldPosition];

  if (indexPath != nil) {
     [yourTablViewHere scrollToRowAtIndexPath:indexPath atScrollPosition:UITableViewScrollPositionMiddle animated:YES];
  }
  return YES;
}
Publicat 20/03/2015 la 07:00
sursa de către utilizator

voturi
4

RĂSPUNS CORECT este răspunsul lui Sam Ho:

„Dacă utilizați UITableViewController în loc de UIViewController, se va face automat acest lucru.“.

Doar asigurați-vă că pentru a conecta UITableView la proprietatea TableView a UITableViewController (de exemplu, astfel încât să nu-l adăugați ca subview a View proprietatea UITableViewController).

De asemenea, asigurați-vă că pentru a seta proprietatea AutoresizingMask a UITableView la FlexibleHeight

Publicat 09/12/2010 la 11:28
sursa de către utilizator

voturi
4

Dacă utilizați Three20, apoi utilizați autoresizesForKeyboardproprietatea. Trebuie doar să setați în vederea controlerului dumneavoastră -initWithNibName:bundlemetoda

self.autoresizesForKeyboard = YES

Acest lucru are grijă de:

  1. Ascultarea de notificări de la tastatură și ajustarea cadrului afișarea tabelului de
  2. Derulând la prima responder

Gata si gata.

Publicat 21/09/2010 la 14:19
sursa de către utilizator

voturi
4

notificări de la tastatură locul de muncă, dar mostre de cod Apple pentru că presupune că ecranul de parcurgere este punctul de vedere al ferestrei rădăcină. Acest lucru nu se întâmplă de obicei. Trebuie să compenseze pentru baruri fila, etc., pentru a obține dreptul de compensare.

Este mai ușor decât pare. Aici este codul am folosi într-un UITableViewController. Ea are două variabile de exemplu, hiddenRect și keyboardShown.

// Called when the UIKeyboardDidShowNotification is sent.
- (void)keyboardWasShown:(NSNotification*)aNotification {
    if (keyboardShown)
        return;

    NSDictionary* info = [aNotification userInfo];

    // Get the frame of the keyboard.
    NSValue *centerValue = [info objectForKey:UIKeyboardCenterEndUserInfoKey];
    NSValue *boundsValue = [info objectForKey:UIKeyboardBoundsUserInfoKey];
    CGPoint keyboardCenter = [centerValue CGPointValue];
    CGRect keyboardBounds = [boundsValue CGRectValue];
    CGPoint keyboardOrigin = CGPointMake(keyboardCenter.x - keyboardBounds.size.width / 2.0,
                                         keyboardCenter.y - keyboardBounds.size.height / 2.0);
    CGRect keyboardScreenFrame = { keyboardOrigin, keyboardBounds.size };


    // Resize the scroll view.
    UIScrollView *scrollView = (UIScrollView *) self.tableView;
    CGRect viewFrame = scrollView.frame;
    CGRect keyboardFrame = [scrollView.superview convertRect:keyboardScreenFrame fromView:nil];
    hiddenRect = CGRectIntersection(viewFrame, keyboardFrame);

    CGRect remainder, slice;
    CGRectDivide(viewFrame, &slice, &remainder, CGRectGetHeight(hiddenRect), CGRectMaxYEdge);
    scrollView.frame = remainder;

    // Scroll the active text field into view.
    CGRect textFieldRect = [/* selected cell */ frame];
    [scrollView scrollRectToVisible:textFieldRect animated:YES];

    keyboardShown = YES;
}


// Called when the UIKeyboardDidHideNotification is sent
- (void)keyboardWasHidden:(NSNotification*)aNotification
{
    // Reset the height of the scroll view to its original value
    UIScrollView *scrollView = (UIScrollView *) self.tableView;
    CGRect viewFrame = [scrollView frame];
    scrollView.frame = CGRectUnion(viewFrame, hiddenRect);

    keyboardShown = NO;
}
Publicat 11/07/2009 la 23:01
sursa de către utilizator

voturi
4

Dacă utilizați un uitableview pentru a plasa dvs. Câmpuri de text ( de la Jeff Lamarche ), puteți derula doar tableview folosind metoda delegat ca acest lucru.

(Notă: câmpurile mele de text sunt stocate într-o matrice cu același index, deoarece există rând în tableview)

- (void) textFieldDidBeginEditing:(UITextField *)textField
    {

        int index;
        for(UITextField *aField in textFields){

            if (textField == aField){
                index = [textFields indexOfObject:aField]-1;
            }
        }

         if(index >= 0) 
            [self.tableView scrollToRowAtIndexPath:[NSIndexPath indexPathForRow:index inSection:0] atScrollPosition:UITableViewScrollPositionTop animated:YES];

        [super textFieldDidBeginEditing:textField];
    }
Publicat 01/05/2009 la 07:09
sursa de către utilizator

voturi
3

O soluție mai căptușită flux. Acesta alunecă în metodele delegatului UITextField, deci nu are nevoie de încurcați w / notificări UIKeyboard.

Notele de implementare:

kSettingsRowHeight - înălțimea unei UITableViewCell.

offsetTarget și offsetThreshold sunt baed off de kSettingsRowHeight. Dacă utilizați o înălțime de alt rând, setați aceste valori pentru proprietatea y punctul lui. [Alt: calculează șirul de compensare într-un mod diferit.]

- (BOOL)textFieldShouldBeginEditing:(UITextField *)textField {
CGFloat offsetTarget    = 113.0f; // 3rd row
CGFloat offsetThreshold = 248.0f; // 6th row (i.e. 2nd-to-last row)

CGPoint point = [self.tableView convertPoint:CGPointZero fromView:textField];

[UIView beginAnimations:nil context:nil];
[UIView setAnimationDuration:0.2];
[UIView setAnimationCurve:UIViewAnimationCurveEaseOut];

CGRect frame = self.tableView.frame;
if (point.y > offsetThreshold) {
    self.tableView.frame = CGRectMake(0.0f,
                      offsetTarget - point.y + kSettingsRowHeight,
                      frame.size.width,
                      frame.size.height);
} else if (point.y > offsetTarget) {
    self.tableView.frame = CGRectMake(0.0f,
                      offsetTarget - point.y,
                      frame.size.width,
                      frame.size.height);
} else {
    self.tableView.frame = CGRectMake(0.0f,
                      0.0f,
                      frame.size.width,
                      frame.size.height);
}

[UIView commitAnimations];

return YES;

}

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

[UIView beginAnimations:nil context:nil];
[UIView setAnimationBeginsFromCurrentState:YES];
[UIView setAnimationDuration:0.2];
[UIView setAnimationCurve:UIViewAnimationCurveEaseOut];

CGRect frame = self.tableView.frame;
self.tableView.frame = CGRectMake(0.0f,
                  0.0f,
                  frame.size.width,
                  frame.size.height);

[UIView commitAnimations];

return YES;

}

Publicat 04/08/2009 la 08:18
sursa de către utilizator

voturi
3

Am fugit în ceva de genul problema ta (am vrut un ecran similar cu settings.app iPhone-ului cu o grămadă de celule care se pot modifica stivuite pe partea de sus a unui alt) și a constatat că această abordare a lucrat bine:

uitextfields alunecare în jurul pentru a evita

Publicat 27/02/2009 la 15:17
sursa de către utilizator

voturi
2

Un exemplu în Swift, folosind punctul exact al câmpului de text de la Get indexPath de UITextField în UITableViewCell cu Swift :

func textFieldDidBeginEditing(textField: UITextField) {
    let pointInTable = textField.convertPoint(textField.bounds.origin, toView: self.accountsTableView)
    let textFieldIndexPath = self.accountsTableView.indexPathForRowAtPoint(pointInTable)
    accountsTableView.scrollToRowAtIndexPath(textFieldIndexPath!, atScrollPosition: .Top, animated: true)
}
Publicat 21/05/2015 la 06:34
sursa de către utilizator

voturi
2

fir de discuție foarte interesant, de asemenea, am confruntat cu aceeași problemă poate fi mai rău, deoarece unul

  1. Am fost folosind o celulă personalizat și câmpul text a fost în interiorul acelui.
  2. A trebuit să folosesc UIViewController pentru a satisface cerințele mele poate juca să profite de UITableViewController.
  3. Am avut filtru de criterii / sortare în celula mea tabel, adică ur celule continuă schimbare și păstrarea evidența indexpath și tot nu va ajuta.

Deci , citiți firele de aici și puse în aplicare versiunea mea, care ma ajutat în împingând în sus conținutul meu în iPad în peisaj modul. Aici este codul (acest lucru nu este prost dovada și toate, dar fix problema mea) În primul rând u trebuie să aibă un delegat în clasă de celule personalizat, care începe la editare, trimite la ur viewcontroller câmpul text și setați activefield = theTextField acolo

// IMPLEMENTATĂ să se ocupe de PEISAJ MOD DOAR

- (void)keyboardWasShown:(NSNotification*)aNotification
{
    NSDictionary* info = [aNotification userInfo];
    CGSize kbValue = [[info objectForKey:UIKeyboardFrameBeginUserInfoKey] CGRectValue].size;
    CGRect aRect = myTable.frame;

    CGSize kbSize = CGSizeMake(kbValue.height, kbValue.width);

    aRect.size.height -= kbSize.height+50;
// This will the exact rect in which your textfield is present
        CGRect rect =  [myTable convertRect:activeField.bounds fromView:activeField];
// Scroll up only if required
    if (!CGRectContainsPoint(aRect, rect.origin) ) {


            [myTable setContentOffset:CGPointMake(0.0, rect.origin.y) animated:YES];

    }


}

// apelat atunci când este trimis UIKeyboardWillHideNotification

- (void)keyboardWillHide:(NSNotification*)aNotification
{
    UIEdgeInsets contentInsets = UIEdgeInsetsZero;
    myTable.contentInset = contentInsets;
    myTable.scrollIndicatorInsets = contentInsets;
    NSDictionary* info = [aNotification userInfo];
    CGSize kbValue = [[info objectForKey:UIKeyboardFrameBeginUserInfoKey] CGRectValue].size;
    CGSize kbSize = CGSizeMake(kbValue.height, kbValue.width);
    CGRect bkgndRect = activeField.superview.frame;
    bkgndRect.size.height += kbSize.height;
    [activeField.superview setFrame:bkgndRect];
    [myTable setContentOffset:CGPointMake(0.0, 10.0) animated:YES];
}

-anoop4real

Publicat 17/07/2012 la 18:11
sursa de către utilizator

voturi
2

Acest soluton funcționează pentru mine, vă rugăm să rețineți linia

[tableView setContentOffset:CGPointMake(0.0, activeField.frame.origin.y-kbSize.height+160) animated:YES];

Puteți schimba valoarea de 160 pentru a se potrivi-l lucra cu tine

- (void)keyboardWasShown:(NSNotification*)aNotification
{
    NSDictionary* info = [aNotification userInfo];
    CGSize kbSize = [[info objectForKey:UIKeyboardFrameBeginUserInfoKey] CGRectValue].size;
    CGRect bkgndRect = activeField.superview.frame;
                        bkgndRect.size.height += kbSize.height;
     [activeField.superview setFrame:bkgndRect];
     [tableView setContentOffset:CGPointMake(0.0, activeField.frame.origin.y-kbSize.height+160) animated:YES];
}

- (void)textFieldDidBeginEditing:(UITextField *)textField
{
   activeField = textField;
}
-(void)textFieldDidEndEditing:(UITextField *)textField
 {
     activeField = nil;
 }
// Called when the UIKeyboardWillHideNotification is sent
- (void)keyboardWillBeHidden:(NSNotification*)aNotification
{
    UIEdgeInsets contentInsets = UIEdgeInsetsZero;
    tableView.contentInset = contentInsets;
    tableView.scrollIndicatorInsets = contentInsets;
    NSDictionary* info = [aNotification userInfo];
    CGSize kbSize = [[info objectForKey:UIKeyboardFrameBeginUserInfoKey] CGRectValue].size;
    CGRect bkgndRect = activeField.superview.frame;
    //bkgndRect.size.height += kbSize.height;
    [activeField.superview setFrame:bkgndRect];
    [tableView setContentOffset:CGPointMake(0.0, activeField.frame.origin.y-kbSize.height) animated:YES];
}
Publicat 02/12/2011 la 19:28
sursa de către utilizator

voturi
2

Din moment ce aveți într-un tabel Câmpuri de text, într-adevăr cel mai bun mod este de a redimensiona masa - trebuie să setați tableView.frame să fie mai mic în înălțime de mărimea tastaturii (cred că în jurul valorii de 165 pixeli) și apoi extindeți-l din nou atunci când tastatura este respinsă.

Opțional, puteți, de asemenea, interacțiunea cu utilizatorul de dezactivare pentru tableView la acel moment, precum și, în cazul în care nu doriți derularea de utilizator.

Publicat 28/02/2009 la 19:37
sursa de către utilizator

voturi
1

Variație mică cu Swift 4.2 ...

Pe UITableView mea am avut multe secțiuni , dar am avut de a evita efectul de antet plutitor asa ca am folosit o „ dummyViewHeight abordare“ , așa cum se vede în altă parte aici , pe Stack Overflow ... Deci , aceasta este soluția mea pentru această problemă (funcționează , de asemenea , pentru tastatura + sugestii bara de instrumente +):

Declare ca constantă de clasă:

let dummyViewHeight: CGFloat = 40.0

Atunci

override func viewDidLoad() {
    super.viewDidLoad()
    //... some stuff here, not needed for this example

    // Create non floating header
    tableView.tableHeaderView = UIView(frame: CGRect(x: 0, y: 0, width: tableView.bounds.size.width, height: dummyViewHeight))
    tableView.contentInset = UIEdgeInsets(top: -dummyViewHeight, left: 0, bottom: 0, right: 0)

    addObservers()
}

override func viewWillDisappear(_ animated: Bool) {
    super.viewWillDisappear(animated)
    removeObservers()
}

Și aici toată magia ...

@objc func keyboardWillShow(notification: NSNotification) {
    if let userInfo = notification.userInfo {
        let keyboardHeight = (userInfo[UIResponder.keyboardFrameEndUserInfoKey] as AnyObject).cgRectValue.size.height
        tableView.tableHeaderView = UIView(frame: CGRect(x: 0, y: 0, width: self.tableView.bounds.size.width, height: dummyViewHeight))
        tableView.contentInset = UIEdgeInsets(top: -dummyViewHeight, left: 0, bottom: keyboardHeight, right: 0)
    }
}

@objc func keyboardWillHide(notification: NSNotification) {
    UIView.animate(withDuration: 0.25) {
        self.tableView.tableHeaderView = UIView(frame: CGRect(x: 0, y: 0, width: self.tableView.bounds.size.width, height: self.dummyViewHeight))
        self.tableView.contentInset = UIEdgeInsets(top: -self.dummyViewHeight, left: 0, bottom: 0, right: 0)
    }
}
Publicat 08/10/2018 la 10:45
sursa de către utilizator

voturi
1

în viewdidload

-(void)viewdidload{

[super viewdidload];

    [[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(keyboardWillChange:) name:UIKeyboardWillChangeFrameNotification object:nil];
}

    -(void)keyboardWillChange:(NSNotification*)sender{

        NSLog(@"keyboardwillchange sender %@",sender);

float margin=0  // set your own topmargin


        CGFloat originY = [[sender.userInfo objectForKey:UIKeyboardFrameEndUserInfoKey] CGRectValue].origin.y;


        if (originY >= self.view.frame.size.height){

            NSLog(@"keyboardclose");



            [tb_ setFrame:CGRectMake(0, margin, self.view.frame.size.width, self.view.frame.size.height-margin)];

        }else{

            NSLog(@"keyobard on");

            float adjustedHeight = self.view.frame.size.height - margin - (self.view.frame.size.height-originY);

            [tb_ setFrame:CGRectMake(0, margin, self.view.frame.size.width, adjustedHeight)];
        }







    }
Publicat 12/02/2016 la 09:14
sursa de către utilizator

voturi
1

Sunt folosind aceste și lucrează ca un farmec:

BSKeyboardControls - BSKeyboardControls github

TPKeyboardAvoiding - TPKeyboardAvoiding github

Publicat 13/02/2014 la 09:30
sursa de către utilizator

voturi
1

Eu folosesc adesea acest lucru în proiectele mele. Această soluție funcționează cu scrollviews, tableviews sau collectionviews și este ușor de instalat. De asemenea, cârlige automat butoane sus „Next“ de pe tastatură pentru a trece prin câmpurile de text.

Verifică - l aici

Publicat 12/02/2014 la 21:27
sursa de către utilizator

voturi
1

Voi arunca soluția mea (Sau QuickDialog lui, care este) în pălărie. Practic, așteptați pentru a anima la derularea. Ar fi frumos pentru a obține JIT animație tastatura în loc de numărul magic.

-(void)textFieldDidBeginEditing:(UITextField *)textField
{
    if (textField == self.emailTextField) {
        NSIndexPath *indexPath = [NSIndexPath indexPathForRow:0 inSection:0];
        dispatch_time_t popTime = dispatch_time(DISPATCH_TIME_NOW, 50 * USEC_PER_SEC);
        dispatch_after(popTime, dispatch_get_main_queue(), ^(void){
            [self.tableView scrollToRowAtIndexPath:indexPath atScrollPosition:UITableViewScrollPositionTop animated:YES];
        });
    }
}
Publicat 28/01/2014 la 19:05
sursa de către utilizator

voturi
1

soluția cea mai ușoară și rapidă.

Tocmai am defila la celula din dreapta ori de câte ori se întâmplă defilare

    - (void)scrollViewDidScroll:(UIScrollView *)scrollView 

Presupunând că știu tabelul de acum este în acest mod „_keepMyCellOnTop“ & știu de celule selectat „_selectedCellIndex“ sau derulați la celula selectată

- (void)scrollViewDidScroll:(UIScrollView *)scrollView 
{

    if (_keepMyCellOnTop)
    {
        [self.tableView scrollToRowAtIndexPath:_selectedCellIndex atScrollPosition:UITableViewScrollPositionTop animated:NO];
    }
}

Acest lucru va preveni defilare.

Plasarea codul în -(void) scrollViewDidEndScrollingAnimation:(UIScrollView *)scrollView va avea ca rezultat un sul în sus și în jos

Publicat 31/12/2013 la 13:37
sursa de către utilizator

voturi
1

Am rezolvat doar o astfel de problemă de mine după ce am menționat o masă de soluții găsite prin intermediul Google și Stack Overflow.

În primul rând, vă rugăm să vă asigur că ați configurat un IBOutlet de UIScrollView, atunci vă rugăm să aruncați o privire atentă la Apple a Doc: Managementul tastatură . În cele din urmă, în cazul în care puteți derula în fundal, dar tastatura acoperă încă câmpuri text, vă rugăm să aruncați o privire la această bucată de cod:

// If active text field is hidden by keyboard, scroll it so it's visible
// Your application might not need or want this behavior.
CGRect aRect = self.view.frame;
aRect.size.height -= kbSize.height;

if (aRect.size.height < activeField.frame.origin.y+activeField.frame.size.height) {

    CGPoint scrollPoint = CGPointMake(0.0, activeField.frame.origin.y+activeField.frame.size.height-aRect.size.height);

    [scrollView setContentOffset:scrollPoint animated:YES];

Principala diferență dintre această piesă și minciuni Apple în cazul în care starea. Cred că calcul Apple a distanței de parcurgere și starea dacă câmp text acoperit de tastatură nu sunt corecte, așa că am făcut modificarea mea ca mai sus.

Lasă-mă să știu dacă funcționează

Publicat 18/08/2012 la 11:10
sursa de către utilizator

voturi
1

Iată cum am făcut acest lucru, care este un amestec de Sam Ho și răspunsurile lui Marcel W, iar unele dintre propriile mele remedieri de erori făcute la codul meu de doi bani. Am fost folosind un UITableViewController. Tabelul redimensionează acum corect când este afișată tastatura.

1) viewDidLoadam adăugat:

self.tableView.autoresizingMask = UIViewAutoresizingFlexibleHeight;

2) Am uitat să chem superechivalentul în viewWillAppearși awakeFromNib. Am adăugat astea înapoi.

Publicat 26/07/2012 la 18:18
sursa de către utilizator

voturi
1

Dacă UITableView este gestionat de o subclasă de UITableViewController și nu UITableView, iar delegatul câmp text este UITableViewController, acesta ar trebui să gestioneze toate derularea automată - toate aceste observații sunt foarte dificil de pus în practică.

Pentru un bun exemplu a se vedea proiectul de cod exemplu de mere: TaggedLocations.

Puteți vedea că aceasta se va derula în mod automat, dar nu pare a fi nici un cod care face acest lucru. Acest proiect are, de asemenea, celule de vizualizare tabel personalizat, așa că, dacă vă construiți aplicația cu ea ca un ghid, ar trebui să obțineți rezultatul dorit.

Publicat 05/03/2012 la 07:09
sursa de către utilizator

voturi
1

O altă metodă ușoară (funcționează numai cu o singură secțiune)

//cellForRowAtIndexPath
UItextField *tf;
[cell addSubview:tf];
tf.tag = indexPath.row;
tf.delegate = self;

//textFieldDidBeginEditing:(UITextField *)text
[[self.tableView scrollToRowsAtIndexPath:[NSIndexPath indexPathForRow:text.tag in section:SECTIONINTEGER] animated:YES];
Publicat 23/11/2011 la 17:25
sursa de către utilizator

voturi
1

Deci , după ore de muncă istovitoare încercarea de a utiliza aceste soluții curente (și cu totul a eșuat) am avut în sfârșit lucrurile de lucru bine, și să le actualizate pentru a utiliza noile blocuri de animație. Răspunsul meu se bazează în întregime pe răspunsul lui Ortwin de mai sus .

Deci, pentru orice motiv codul de mai sus a fost pur și simplu nu lucrează pentru mine. Configurarea mea părea destul de asemănătoare altora, dar poate pentru că am fost pe un iPad sau 4.3 ... nici o idee. A fost de a face unele matematica trăsnite și fotografiere tableview mea de pe ecran.

A se vedea rezultatul final soluția mea: http://screencast.com/t/hjBCuRrPC (Vă rugăm să ignorați fotografia :-P.)

Așa că m-am dus cu esența a ceea ce făcea Ortwin, dar a schimbat modul în care aceasta a fost a face unele matematica pentru a adăuga până origin.y & size.height din punctul meu de vedere de masă cu înălțimea tastaturii. Când am scade înălțimea ferestrei din acel rezultat, îmi spune cât de mult intersecție am merge mai departe. În cazul în care sa mai mare de 0 (aka există unele suprapuneri) Efectuez animația din înălțimea cadrului.

În plus, au existat unele redesenarea probleme care au fost rezolvate prin 1) În așteptare pentru a defila la celula până când a fost făcut animația și 2) folosind opțiunea UIViewAnimationOptionBeginFromCurrentState atunci când ascunde tastatura.

Câteva lucruri de reținut.

  • _topmostRowBeforeKeyboardWasShown & _originalFrame sunt variabile de instanta declarate în antet.
  • self.guestEntryTableView este tableView mea (eu sunt într-un fișier extern)
  • IASKCGRectSwap este metoda Ortwin pentru flipping coordonatele unui cadru
  • Am actualiza numai înălțimea tableView în cazul în care cel puțin 50px din ea va fi afișat
  • Din moment ce eu nu sunt într-un UIViewController nu am self.view, asa ca am returna tableView la cadrul său original

Din nou, nu aș fi ajuns aproape de acest răspuns, dacă am Ortwin nu a furnizat Punctul crucial al acesteia. Iată codul:

- (IBAction)textFieldDidBeginEditing:(UITextField *)textField
{
    self.activeTextField = textField;

    if ([self.guestEntryTableView indexPathsForVisibleRows].count) {
        _topmostRowBeforeKeyboardWasShown = (NSIndexPath*)[[self.guestEntryTableView indexPathsForVisibleRows] objectAtIndex:0];
    } else {
        // this should never happen
        _topmostRowBeforeKeyboardWasShown = [NSIndexPath indexPathForRow:0 inSection:0];
        [textField resignFirstResponder];
    }
}

- (IBAction)textFieldDidEndEditing:(UITextField *)textField
{
    self.activeTextField = nil;
}

- (void)keyboardWillShow:(NSNotification*)notification {
    NSDictionary* userInfo = [notification userInfo];

    NSValue* keyboardFrameValue = [userInfo objectForKey:UIKeyboardFrameEndUserInfoKey];

    // Reduce the tableView height by the part of the keyboard that actually covers the tableView
    UIInterfaceOrientation orientation = [[UIApplication sharedApplication] statusBarOrientation];
    CGRect windowRect = [[UIApplication sharedApplication] keyWindow].bounds;
    CGRect viewRectAbsolute = [self.guestEntryTableView convertRect:self.guestEntryTableView.bounds toView:[[UIApplication sharedApplication] keyWindow]];
    CGRect keyboardFrame = [keyboardFrameValue CGRectValue];
    if (UIInterfaceOrientationLandscapeLeft == orientation ||UIInterfaceOrientationLandscapeRight == orientation ) {
        windowRect = IASKCGRectSwap(windowRect);
        viewRectAbsolute = IASKCGRectSwap(viewRectAbsolute);
        keyboardFrame = IASKCGRectSwap(keyboardFrame);
    }

    // fix the coordinates of our rect to have a top left origin 0,0
    viewRectAbsolute = FixOriginRotation(viewRectAbsolute, orientation, windowRect.size.width, windowRect.size.height);

    CGRect frame = self.guestEntryTableView.frame;
    _originalFrame = self.guestEntryTableView.frame;

    int remainder = (viewRectAbsolute.origin.y + viewRectAbsolute.size.height + keyboardFrame.size.height) - windowRect.size.height;

    if (remainder > 0 && !(remainder > frame.size.height + 50)) {
        frame.size.height = frame.size.height - remainder;
        float duration = [[userInfo objectForKey:UIKeyboardAnimationDurationUserInfoKey] doubleValue];
        [UIView animateWithDuration: duration
                        animations:^{
                            self.guestEntryTableView.frame = frame;
                        }
                        completion:^(BOOL finished){
                            UITableViewCell *textFieldCell = (UITableViewCell*) [[self.activeTextField superview] superview];
                            NSIndexPath *textFieldIndexPath = [self.guestEntryTableView indexPathForCell:textFieldCell];
                            [self.guestEntryTableView scrollToRowAtIndexPath:textFieldIndexPath atScrollPosition:UITableViewScrollPositionMiddle animated:YES];
                        }];
    }

}

- (void)keyboardWillHide:(NSNotification*)notification {
    NSDictionary* userInfo = [notification userInfo];
    float duration = [[userInfo objectForKey:UIKeyboardAnimationDurationUserInfoKey] doubleValue];
    [UIView animateWithDuration: duration
                          delay: 0.0
                        options: (UIViewAnimationOptionBeginFromCurrentState)
                     animations:^{
                         self.guestEntryTableView.frame = _originalFrame;
                     }
                     completion:^(BOOL finished){
                         [self.guestEntryTableView scrollToRowAtIndexPath:_topmostRowBeforeKeyboardWasShown atScrollPosition:UITableViewScrollPositionTop animated:YES];
                     }];

}   

#pragma mark CGRect Utility function
CGRect IASKCGRectSwap(CGRect rect) {
    CGRect newRect;
    newRect.origin.x = rect.origin.y;
    newRect.origin.y = rect.origin.x;
    newRect.size.width = rect.size.height;
    newRect.size.height = rect.size.width;
    return newRect;
}

CGRect FixOriginRotation(CGRect rect, UIInterfaceOrientation orientation, int parentWidth, int parentHeight) {
    CGRect newRect;
    switch(orientation)
    {
        case UIInterfaceOrientationLandscapeLeft:
            newRect = CGRectMake(parentWidth - (rect.size.width + rect.origin.x), rect.origin.y, rect.size.width, rect.size.height);
            break;
        case UIInterfaceOrientationLandscapeRight:
            newRect = CGRectMake(rect.origin.x, parentHeight - (rect.size.height + rect.origin.y), rect.size.width, rect.size.height);
            break;
        case UIInterfaceOrientationPortrait:
            newRect = rect;
            break;
        case UIInterfaceOrientationPortraitUpsideDown:
            newRect = CGRectMake(parentWidth - (rect.size.width + rect.origin.x), parentHeight - (rect.size.height + rect.origin.y), rect.size.width, rect.size.height);
            break;
    }
    return newRect;
}
Publicat 18/07/2011 la 09:45
sursa de către utilizator

voturi
1

Am încercat aproape aceeași abordare și a venit cu un cod mai simplu și mai mic pentru același lucru. Am creat un IBOutlet iTextView și asociat cu UITextView în IB.

 -(void)keyboardWillShow:(NSNotification *)notification
    {
        NSLog(@"Keyboard");
        CGRect keyFrame = [[[notification userInfo]objectForKey:UIKeyboardFrameEndUserInfoKey]CGRectValue];

        [UIView beginAnimations:@"resize view" context:nil];
        [UIView setAnimationCurve:1];
        [UIView setAnimationDuration:1.0];
        CGRect frame = iTableView.frame;
        frame.size.height = frame.size.height -  keyFrame.size.height;
        iTableView.frame = frame;
        [iTableView scrollRectToVisible:frame animated:YES];
        [UIView commitAnimations];

    }
Publicat 13/05/2011 la 06:00
sursa de către utilizator

voturi
1

Acest lucru funcționează perfect, și pe iPad prea.

- (BOOL)textFieldShouldReturn:(UITextField *)textField 
{

    if(textField == textfield1){
            [accountName1TextField becomeFirstResponder];
        }else if(textField == textfield2){
            [self.tableView scrollToRowAtIndexPath:[NSIndexPath indexPathForRow:0 inSection:1] atScrollPosition:UITableViewScrollPositionTop animated:YES];
            [textfield3 becomeFirstResponder];

        }else if(textField == textfield3){
            [self.tableView scrollToRowAtIndexPath:[NSIndexPath indexPathForRow:1 inSection:1] atScrollPosition:UITableViewScrollPositionTop animated:YES];
            [textfield4 becomeFirstResponder];

        }else if(textField == textfield4){
            [self.tableView scrollToRowAtIndexPath:[NSIndexPath indexPathForRow:2 inSection:1] atScrollPosition:UITableViewScrollPositionTop animated:YES];
            [textfield5 becomeFirstResponder];

        }else if(textField == textfield5){
            [self.tableView scrollToRowAtIndexPath:[NSIndexPath indexPathForRow:3 inSection:1] atScrollPosition:UITableViewScrollPositionTop animated:YES];
            [textfield6 becomeFirstResponder];

        }else if(textField == textfield6){
            [self.tableView scrollToRowAtIndexPath:[NSIndexPath indexPathForRow:4 inSection:1] atScrollPosition:UITableViewScrollPositionTop animated:YES];
            [textfield7 becomeFirstResponder];

        }else if(textField == textfield7){
            [self.tableView scrollToRowAtIndexPath:[NSIndexPath indexPathForRow:5 inSection:1] atScrollPosition:UITableViewScrollPositionTop animated:YES];
            [textfield8 becomeFirstResponder];

        }else if(textField == textfield8){
            [self.tableView scrollToRowAtIndexPath:[NSIndexPath indexPathForRow:6 inSection:1] atScrollPosition:UITableViewScrollPositionTop animated:YES];
            [textfield9 becomeFirstResponder];

        }else if(textField == textfield9){
            [self.tableView scrollToRowAtIndexPath:[NSIndexPath indexPathForRow:7 inSection:1] atScrollPosition:UITableViewScrollPositionTop animated:YES];
            [textField resignFirstResponder];
        }
Publicat 23/10/2010 la 08:11
sursa de către utilizator

voturi
0

Tocmai am descoperit un alt bug atunci când se utilizează UITableViewController. Acesta nu a fost defilare automat când tastatura apărut. Am observat că a fost din cauza contentInsetAdjustmentBehavior = .never pe UITableView.

Publicat 03/07/2019 la 21:30
sursa de către utilizator

voturi
0

Soluție Swift 3-4 cu animatii si rama tastatura schimbare:

În primul rând, creați un Bool:

// MARK: - Private Properties
private var isKeyboardShowing = false

În al doilea rând, se adaugă observatori la tastatură Notificări de sistem:

// MARK: - Overriding ViewController Life Cycle Methods
override func viewWillAppear(_ animated: Bool) {
    super.viewWillAppear(animated)

    NotificationCenter.default.addObserver(self, selector: #selector(keyboardWillShow), name: .UIKeyboardWillShow, object: nil)

    NotificationCenter.default.addObserver(self, selector: #selector(keyboardWillHide), name: .UIKeyboardWillHide, object: nil)

    NotificationCenter.default.addObserver(self, selector: #selector(keyboardWillChangeFrame), name: .UIKeyboardWillChangeFrame, object: nil)
}

În al treilea rând, se pregătească funcția de animație:

func adjustTableViewInsets(keyboardHeight: CGFloat, duration: NSNumber, curve: NSNumber){
    var extraHeight: CGFloat = 0
    if keyboardHeight > 0 {
        extraHeight = 20
        isKeyboardShowing = true
    } else {
        isKeyboardShowing = false
    }

    let contentInset = UIEdgeInsets(top: 0, left: 0, bottom: keyboardHeight + extraHeight, right: 0)
    func animateFunc() {
        //refresh constraints
        //self.view.layoutSubviews()
        tableView.contentInset = contentInset
    }

    UIView.animate(withDuration: TimeInterval(duration), delay: 0, options: [UIViewAnimationOptions(rawValue: UInt(curve))], animations: animateFunc, completion: nil)
}

Apoi se adaugă metodele țintă / acțiune (numit de către observatori):

// MARK: - Target/Selector Actions
func keyboardWillShow(notification: NSNotification) {
    if !isKeyboardShowing {
        if let keyboardSize = (notification.userInfo?[UIKeyboardFrameBeginUserInfoKey] as? NSValue)?.cgRectValue {
            let keyboardHeight = keyboardSize.height

            let duration = notification.userInfo?[UIKeyboardAnimationDurationUserInfoKey] as! NSNumber
            let curve = notification.userInfo?[UIKeyboardAnimationCurveUserInfoKey] as! NSNumber

            adjustTableViewInsets(keyboardHeight: keyboardHeight, duration: duration, curve: curve)
        }
    }
}

func keyboardWillHide(notification: NSNotification) {
    let duration = notification.userInfo?[UIKeyboardAnimationDurationUserInfoKey] as! NSNumber
    let curve = notification.userInfo?[UIKeyboardAnimationCurveUserInfoKey] as! NSNumber
    adjustTableViewInsets(keyboardHeight: 0, duration: duration, curve: curve)
}

func keyboardWillChangeFrame(notification: NSNotification) {
    if isKeyboardShowing {
        let duration = notification.userInfo?[UIKeyboardAnimationDurationUserInfoKey] as! NSNumber
        let curve = notification.userInfo?[UIKeyboardAnimationCurveUserInfoKey] as! NSNumber

        if let newKeyboardSize = (notification.userInfo?[UIKeyboardFrameEndUserInfoKey] as? NSValue)?.cgRectValue {
            let keyboardHeight = newKeyboardSize.height
            adjustTableViewInsets(keyboardHeight: keyboardHeight, duration: duration, curve: curve)
        }
    }
}

În cele din urmă, nu uitați să eliminați observatori în deinit sau în viewWillDisappear:

deinit {
    NotificationCenter.default.removeObserver(self)
}
Publicat 10/06/2018 la 15:48
sursa de către utilizator

voturi
0

Nu este nevoie orice calcule, utilizați codul de mai jos va funcționa: Acest cod am folosit în mea personalizată UITableviewcell, Este de lucru:

override func viewDidLoad() {
super.viewDidLoad()

NotificationCenter.default.addObserver(self, selector: #selector(ViewController.keyboardWillShow), name: NSNotification.Name.UIKeyboardWillShow, object: nil)

NotificationCenter.default.addObserver(self, selector: #selector(ViewController.keyboardWillHide), name: NSNotification.Name.UIKeyboardWillHide, object: nil)}


func keyboardWillShow(_ notification:Notification) {

if let keyboardSize = (notification.userInfo?[UIKeyboardFrameBeginUserInfoKey] as? NSValue)?.cgRectValue {
    tableView.contentInset = UIEdgeInsetsMake(0, 0, keyboardSize.height, 0)
}}


func keyboardWillHide(_ notification:Notification) {

if let keyboardSize = (notification.userInfo?[UIKeyboardFrameBeginUserInfoKey] as? NSValue)?.cgRectValue {
    tableView.contentInset = UIEdgeInsetsMake(0, 0, 0, 0)
}}
Publicat 22/02/2018 la 07:47
sursa de către utilizator

voturi
0

Swift 4 soluție completă:

  • Funcționează corect cu modificări cadru de tastatură (de exemplu, înălțimea tastaturii se schimba ca emojii → tastatura normala).
  • sprijin TabBar & ToolBar, de exemplu, UITableView (în alte exemple pe care le primiți Focare incorecte).
  • Durata de animație dinamică (nu codificate).
  • Protocol orientat, astfel încât să puteți utiliza cu ușurință în orice situație.
  • Focare de derulare funcționează prea.

Am scris protocolul ajutor (îl puteți descărca ca GIST , deoarece este prea mare pentru a posta pe StackOverflow), astfel încât opinia dumneavoastră trebuie doar să:

  1. Adoptarea KeyboardChangeFrameObserverprotocolului:

    func willChangeKeyboardFrame(height: CGFloat, animationDuration: TimeInterval, animationOptions: UIViewAnimationOptions)
    
  2. Apel observeKeyboardFrameChanges()pe par.

Exemplu de implementare a acestui protocol pentru tableView:

class TestViewController: UITableViewController, KeyboardChangeFrameObserver {

    override func viewWillAppear(_ animated: Bool) {
        super.viewWillAppear(animated)

        observeKeyboardFrameChanges()
    }

    func willChangeKeyboardFrame(height: CGFloat, animationDuration: TimeInterval, animationOptions: UIViewAnimationOptions) {
        var adjustedHeight = height

        if let tabBarHeight = self.tabBarController?.tabBar.frame.height {
            adjustedHeight -= tabBarHeight
        } else if let toolbarHeight = navigationController?.toolbar.frame.height, navigationController?.isToolbarHidden == false {
            adjustedHeight -= toolbarHeight
        }

        if adjustedHeight < 0 { adjustedHeight = 0 }

        UIView.animate(withDuration: animationDuration, animations: {
            let newInsets = UIEdgeInsets(top: 0, left: 0, bottom: adjustedHeight, right: 0)
            self.tableView.contentInset = newInsets
            self.tableView.scrollIndicatorInsets = newInsets
        })
    }

}
Publicat 12/01/2018 la 00:10
sursa de către utilizator

voturi
0
// scroll tableview so content ends at the middle of the tableview (out of the way of the keyboard)
CGPoint newContentOffset = CGPointMake(0, [self.tableView contentSize].height - (self.tableView.bounds.size.height / 2));
[self.tableView setContentOffset:newContentOffset animated:YES];
Publicat 27/06/2017 la 21:12
sursa de către utilizator

voturi
0

Uită-te la versiunea mea :)

    - (void)keyboardWasShown:(NSNotification *)aNotification
{
    NSDictionary* info = [aNotification userInfo];
    CGSize kbSize = [[info objectForKey:UIKeyboardFrameBeginUserInfoKey] CGRectValue].size;
    CGRect bkgndRect = cellSelected.superview.frame;
    bkgndRect.size.height += kbSize.height;
    [cellSelected.superview setFrame:bkgndRect];
    [tableView setContentOffset:CGPointMake(0.0, cellSelected.frame.origin.y-kbSize.height) animated:YES];
}


- (void)keyboardWasHidden:(NSNotification *)aNotification
{
    [tableView setContentOffset:CGPointMake(0.0, 0.0) animated:YES];
}
Publicat 02/07/2016 la 20:32
sursa de către utilizator

voturi
0

Aici este soluția mea inspirată de „edita eveniment“ ecran din iOS7 Calendar app.

Unul dintre punctele cheie ale acestei soluții este faptul că tastatura este respinsă atunci când utilizatorul derulează tabelul.

Implementare:

1) Adăugați proprietatea care va stoca textfield selectate:

@property (strong) UITextField *currentTextField;

și BOOL variabile pe care le vom folosi pentru a verifica dacă avem nevoie pentru a ascunde tastatura atunci când utilizatorul derulează tabel.

BOOL hideKeyboardOnScroll;

2) Mâner UITextField callbacks delegare:

#pragma mark - UITextFieldDelegate

- (void) textFieldDidBeginEditing: (UITextField *) textField {
    self.currentTextField = textField;
}

- (void) textFieldDidEndEditing: (UITextField *) textField {
    self.currentTextField = nil;
}

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

    CGPoint newContentOffset = CGPointZero;
    if (tableView.contentSize.height > tableView.frame.size.height) {
        newContentOffset.y = MIN(tableView.contentOffset.y, tableView.contentSize.height - tableView.frame.size.height);
    }
    [tableView setContentOffset: newContentOffset animated: YES];

    return YES;
}

3) Mâner metoda UIScrollViewDelegate pentru a verifica vizualizarea parcurgere utilizator.

#pragma mark - UIScrollViewDelegate

- (void) scrollViewDidScroll: (UIScrollView *) scrollView {
    if (hideKeyboardOnScroll == YES) {
        [self.currentTextField resignFirstResponder];
    }
}

4) Abonare la notificări tastatură în [viewWillAppear] Metoda viewcontroller și dezabona în [viewWillDisappear] metodă.

- (void) viewWillAppear: (BOOL) animated {
    [super viewWillAppear: animated];

    [ [NSNotificationCenter defaultCenter] addObserver: self selector: @selector(keyboardWillShow:)
                                                  name: UIKeyboardWillShowNotification object: nil];
    [ [NSNotificationCenter defaultCenter] addObserver: self selector: @selector(keyboardWillHide:)
                                                  name: UIKeyboardWillHideNotification object: nil];
}

- (void) viewWillDisappear: (BOOL) animated {
    [super viewWillDisappear: animated];

    [ [NSNotificationCenter defaultCenter] removeObserver: self name: UIKeyboardDidShowNotification object: nil];
    [ [NSNotificationCenter defaultCenter] removeObserver: self name: UIKeyboardWillHideNotification object: nil];    
}

5) Mâner notificările de la tastatură:

- (void) keyboardWillShow: (NSNotification *) notification {
    CGRect keyboardFrame = [ [ [notification userInfo] objectForKey: UIKeyboardFrameBeginUserInfoKey] CGRectValue];

    // Find cell with textfield.
    CGRect textFieldFrame = [tableView convertRect: self.currentTextField.frame fromView: self.currentTextField];
    NSIndexPath *indexPath = [tableView indexPathForRowAtPoint: textFieldFrame.origin];
    UITableViewCell *cell = [tableView cellForRowAtIndexPath: indexPath];
    //

    // Shrink tableView size.
    CGRect tableViewFrame = tableView.frame;
    tableView.frame = CGRectMake(tableView.frame.origin.x, tableView.frame.origin.y, tableView.frame.size.width,
                             self.view.frame.size.height - tableView.frame.origin.y - keyboardFrame.size.height);
    //

    // Check if cell is visible in shrinked table size.
    BOOL cellIsFullyVisible = YES;
    if ( cell.frame.origin.y < tableView.contentOffset.y ||
        (cell.frame.origin.y + cell.frame.size.height) > (tableView.contentOffset.y + tableView.frame.size.height) ) {
        cellIsFullyVisible = NO;
    }
    //

    // If cell is not fully visible when scroll table to show cell;
    if (cellIsFullyVisible == NO) {
        CGPoint contentOffset = CGPointMake(tableView.contentOffset.x, CGRectGetMaxY(cell.frame) - tableView.frame.size.height);
        if (cell.frame.origin.y < tableView.contentOffset.y) {
            contentOffset.y = cell.frame.origin.y;
        }
        contentOffset.y = MAX(0, contentOffset.y);

        // For some reason [setContentOffset] is called without delay then
        // this code may not work for some cells. That why we call it with brief delay.
        dispatch_time_t popTime = dispatch_time(DISPATCH_TIME_NOW, (int64_t)(0.1 * NSEC_PER_SEC));
        dispatch_after(popTime, dispatch_get_main_queue(), ^(void){
            [UIView animateWithDuration: 0.5 animations:^{
                [tableView setContentOffset: contentOffset animated: NO];
            } completion: ^(BOOL finished) {
                hideKeyboardOnScroll = YES;
            }];
        });
    } else {
        hideKeyboardOnScroll = YES;
    }
    //

    // Finally restore original table frame.
    tableView.frame = tableViewFrame;
    //
}

- (void) keyboardWillHide: (NSNotification *) notification {
    [super keyboardWillHide: notification];

    hideKeyboardOnScroll = NO;
}
Publicat 21/08/2014 la 15:43
sursa de către utilizator

voturi
0

Cred că cea mai bună cale este prin UITableViewController.

Dacă doriți o UITableView într - un UIViewController , doar face un ContentView cu un UITableViewController încorporat și a pus următoarele linii în viedDidLoad de UIViewController:

self.tableView = ((UITableViewController*)self.childViewControllers[0]).tableView;
self.tableView.delegate = self;
self.tableView.dataSource = self;

Simplu;)

Publicat 06/06/2014 la 16:29
sursa de către utilizator

voturi
0

Cred că nu există nici un „drept“ mod de a face acest lucru. Trebuie să alegeți cea mai bună soluție potrivită pentru dvs. de utilizare. În meu iPad App am o UIViewControllercare este prezentată modal ca UIModalPresentationFormSheetși constă dintr - un UITableView. Acest tabel conține două UITextFieldsper celulă. Doar apel scrollToRowAtIndexPath:atScrollPosition:animated:în textFieldDidBeginEditing:metoda nu funcționează pentru mine. De aceea , am creat un tableFooterView:

- (void)viewDidLoad
{
    [super viewDidLoad];

    m_footerView = [[UIView alloc] initWithFrame:CGRectMake(0.0f, 0.0f, m_tableView.frame.size.width, 300.0f)];
    [m_footerView setBackgroundColor:[UIColor clearColor]];
    [m_tableView setTableFooterView:m_footerView];
    [m_footerView release];
}

Ideea este că , tastatura , ascunde tableFooterViewși nu UITextFields. Deci, tableFooterViewtrebuie să fie suficient de mare. După care le puteți utiliza scrollToRowAtIndexPath:atScrollPosition:animated:în textFieldDidBeginEditing:metoda.

Cred că este , de asemenea , posibil să apară și ascunde tableFooterViewdinamic prin adăugarea observatorilor pentru notificările de la tastatură , dar nu am încercat -o încă:

- (void)viewWillAppear:(BOOL)animated
{
    [super viewWillAppear:animated];

    [[NSNotificationCenter defaultCenter] addObserver:self 
                                             selector:@selector(keyboardWillShow:) 
                                                 name:UIKeyboardWillShowNotification 
                                               object:nil];
    [[NSNotificationCenter defaultCenter] addObserver:self 
                                             selector:@selector(keyboardWillHide:) 
                                                 name:UIKeyboardWillHideNotification 
                                               object:nil];
}

- (void)keyboardWillShow:(NSNotification *)notification 
{
     [m_tableView setTableFooterView:m_footerView];
}

- (void)keyboardWillHide:(NSNotification *)notification 
{
     [m_tableView setTableFooterView:nil];
}

- (void)viewWillDisappear:(BOOL)animated
{
    [super viewWillDisappear:animated];

    [[NSNotificationCenter defaultCenter] removeObserver:self name:UIKeyboardWillShowNotification object:nil];
    [[NSNotificationCenter defaultCenter] removeObserver:self name:UIKeyboardWillHideNotification object:nil];
}
Publicat 15/09/2012 la 08:51
sursa de către utilizator

voturi
0

Am făcut crea un mic proiect care rezolvă această problemă cu tastatura, în cazul meu am nevoie doar pentru a face vizualizarea tabel merge în sus când tastatura apare.

Sper că acest lucru vă ajută!

http://git.io/BrH9eQ

Publicat 19/11/2011 la 21:21
sursa de către utilizator

voturi
0

M-am uitat din nou în iOS 5.0 de referință lib și a găsit această secțiune intitulată „Mutarea conținutului care se află sub tastatură“: TextAndWebiPhoneOS KeyboardManagement

Este acest nou deoarece iOS 5, poate? Eu nu am citit în ea încă așa cum eu sunt în mijlocul de altceva, dar poate că alții știu mai multe și eu și alții pot lumina aici.

Are doc Apple a înlocui ceea ce a fost discutat aici sau este informațiile de aici încă utile pentru utilizatorii iOS 5 SDK?

Publicat 26/10/2011 la 12:07
sursa de către utilizator

voturi
0

UITableViewControllerface în mod automat derulând, într - adevăr. Diferența față de utilizarea unui UIViewControllereste, că trebuie să creați Navbar-Buttonitems programatică prin folosind NavigationController, atunci când se utilizează o TableViewController.

Publicat 20/03/2011 la 20:59
sursa de către utilizator

Cookies help us deliver our services. By using our services, you agree to our use of cookies. Learn more