UITableView прокручивает слишком далеко при редактировании встроенного UITextView - PullRequest
4 голосов
/ 12 июля 2011

Я успешно встроил UITextView в UITableViewCell, и большая часть таблицы работает нормально.Однако, когда я включаю редактирование в UITextView и начинаю редактирование, таблица сдвигается слишком далеко, скрывая курсор.Есть ли способ контролировать, как далеко прокручивается табличное представление?Ручная прокрутка представления к ячейке работает, но представление все еще прокручивается вверх перед прокруткой назад вниз и в представление.

Вот пример того, что я имею в виду: редактирование UITextField - поле аккуратно помещается непосредственно надклавиатура.http://imageshack.us/photo/my-images/13/textfield.png/

редактирование UITextView - поле расположено значительно выше клавиатуры, удаление панели инструментов с клавиатуры ни на что не влияет) http://imageshack.us/photo/my-images/809/textview.png/

Вот весь код, который имеет отношение кUITextView в объекте UITableViewController:

- (void)viewDidLoad
{
    [super viewDidLoad];    

    self.navigationItem.rightBarButtonItem = self.editButtonItem;

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

- (BOOL)textViewShouldBeginEditing:(UITextView *)textView
{
    viewTargetedForEditing = (UIView *)textView;
    return YES;
}

- (void)textViewDidBeginEditing:(UITextView *)textView
{
    [self.navigationController setNavigationBarHidden:YES animated:YES];


    // shrink the textView to fit on-screen
    originalTextViewFrame = textView.frame;
    CGRect keyboardRect = [[keyboardUserinfo objectForKey:UIKeyboardFrameEndUserInfoKey] CGRectValue];
    CGFloat keyboardHeight = keyboardRect.size.height;


    CGRect newViewFrame = textView.frame;
    CGFloat spaceAboveKeyboard = self.containerView.frame.size.height - keyboardHeight;
    newViewFrame.size.height = (spaceAboveKeyboard < textView.frame.size.height) ? spaceAboveKeyboard : textView.frame.size.height;


    /* animate the calculations */

    [UIView beginAnimations:nil context:NULL];
    [UIView setAnimationDuration:[[keyboardUserinfo objectForKey:UIKeyboardAnimationDurationUserInfoKey] doubleValue]];

    textView.frame = newViewFrame;

    [UIView commitAnimations];



    // recalculate the keyboard height, in case we aren't in portrait mode
    CGFloat toolbarHeight;
    if (UIInterfaceOrientationIsPortrait(self.interfaceOrientation)) {
        toolbarHeight = 44.0;
    } else {
        toolbarHeight = 32.0;
    }

    CGRect frame = textView.inputAccessoryView.frame;
    frame.size.height = toolbarHeight;
}

- (void)endTextViewEditing
{
    [viewTargetedForEditing resignFirstResponder];
}

- (void)textViewDidEndEditing:(UITextView *)textView
{
    [self.navigationController setNavigationBarHidden:NO animated:YES];
}

#pragma mark - Keyboard Notifications

- (void)keyboardWillShow:(NSNotification *)notification
{
    [keyboardUserinfo release];
    keyboardUserinfo = [[notification userInfo] retain];
    [self viewDidBeginEditing:viewTargetedForEditing];
}
- (void)keyboardWillHide:(NSNotification *)notification
{
    [keyboardUserinfo release];
    keyboardUserinfo = [[notification userInfo] retain];
    [self viewDidEndEditing:viewTargetedForEditing];
}

- (void)viewDidBeginEditing:(id)aView
{
    // called 2nd

    UITableViewCell *cell = (UITableViewCell *)[aView superview];
    [self.tableView scrollToRowAtIndexPath:[self.tableView indexPathForCell:cell] atScrollPosition:UITableViewScrollPositionTop animated:YES];
}
- (void)viewDidEndEditing:(id)aView
{   
    NSIndexPath *indexPath = [self.tableView indexPathForCell:(UITableViewCell *)[viewTargetedForEditing superview]];

    gallupAppDelegate *appDelegate = (gallupAppDelegate *)[[UIApplication sharedApplication] delegate];

    switch (indexPath.section) {
        case SectionDescription:
            if (![[(UITextField *)aView text] isEqualToString:self.plan.Description]) {
                self.plan.Description = [(UITextField *)aView text];
                [appDelegate saveManagedContext];
            }
            break;

        case SectionNotes:
            if (![[(UITextView *)aView text] isEqualToString:self.plan.Notes]) {
                self.plan.Notes = [(UITextView *)aView text];
                [appDelegate saveManagedContext];
            }
            break;

        case SectionLocation:
            if (![[(UITextField *)aView text] isEqualToString:self.plan.Location]) {
                self.plan.Location = [(UITextField *)aView text];
                [appDelegate saveManagedContext];
            }
            break;
    }
}

TextViewCell является подклассом UITableViewCell, и именно эта ячейка вызывает у меня проблему с прокруткой. Вот реализация:

@implementation TextViewCell

@synthesize contents=_contents;

- (id)initWithStyle:(UITableViewCellStyle)style reuseIdentifier:(NSString *)reuseIdentifier
{
    self = [super initWithStyle:style reuseIdentifier:reuseIdentifier];
    if (self) {
        _contents = [[UITextView alloc] initWithFrame:CGRectZero];
        [self addSubview:_contents];
        self.contents.font = [UIFont systemFontOfSize:17];
        self.contents.dataDetectorTypes = UIDataDetectorTypeAll;


        CGRect frame = CGRectMake(0, 0, self.window.frame.size.width, 44.0);
        UIBarButtonItem *spacer = [[UIBarButtonItem alloc] initWithBarButtonSystemItem:UIBarButtonSystemItemFlexibleSpace target:nil action:nil];
        UIBarButtonItem *done = [[UIBarButtonItem alloc] initWithTitle:@"Done" style:UIBarButtonItemStyleDone target:self action:@selector(endTextViewEditing)];
        UIToolbar *textViewToolbar = [[UIToolbar alloc] initWithFrame:frame];
        textViewToolbar.barStyle = UIBarStyleBlackOpaque;
        [textViewToolbar setItems:[NSArray arrayWithObjects:spacer, done, nil]];

        self.contents.inputAccessoryView = textViewToolbar;
    }
    return self;
}

- (void)endTextViewEditing
{
    [self.contents resignFirstResponder];
}

#define LEFT_MARGIN 15
#define TOP_MARGIN 5
- (void)layoutSubviews
{
    [super layoutSubviews];

    CGFloat width = self.frame.size.width - (LEFT_MARGIN *2);
    CGFloat height = self.frame.size.height - (TOP_MARGIN *2);
    self.contents.frame = CGRectMake(LEFT_MARGIN, TOP_MARGIN, width, height);
}

- (void)setSelected:(BOOL)selected animated:(BOOL)animated
{
    //[super setSelected:selected animated:animated];

    // Configure the view for the selected state
}

- (void)dealloc
{
    [super dealloc];
}

@end

1 Ответ

2 голосов
/ 14 июля 2011

Как оказалось, создание подкласса UITableView и реализация следующего решило проблему:

- (void)setContentOffset:(CGPoint)contentOffset animated:(BOOL)animated
{
    [super setContentOffset:contentOffset animated:animated];
    return;



    static int i = 0;
    if (0 == i) {
        i++;
    } else {
        i = 0;
        [super setContentOffset:contentOffset animated:animated];
    }
    return;
}

По-видимому, -setContentOffset: animated: сообщение было отправлено 2 раза, и, если первый разрешен для запуска во второй раз, он не выполняет свою работу должным образом.

Кто-нибудь знает, почему это решит проблему?

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...