SORU
21 Kasım 2009, CUMARTESİ


UİTextField: klavye göründüğünde görünümü taşıyın

Şu anda giriş için birden fazla UİTextFields olan tek bir görünüm ile bir iPhone uygulaması üzerinde çalışıyorum. Klavye gösterdiğinde, alt TextField öğeleri kaplamaları. textFieldDidBeginEditing: ilgili yöntem, büyük çalışır, görünüm, taşımak için ekledim:

- (void)textFieldDidBeginEditing:(UITextField *)textField {
    if ( ( textField != inputAmount ) && ( textField != inputAge ) ) {
    	NSTimeInterval animationDuration = 0.300000011920929;
    	CGRect frame = self.view.frame;
    	frame.origin.y -= kOFFSET_FOR_KEYBOARD;
    	frame.size.height  = kOFFSET_FOR_KEYBOARD;
    	[UIView beginAnimations:@"ResizeForKeyboard" context:nil];
    	[UIView setAnimationDuration:animationDuration];
    	self.view.frame = frame;
    	[UIView commitAnimations];		
    }
}

Bu yöntem, kontrol mesajın kaynağı klavye gösterdiğinde görünür TextField öğeleri biridir, ve değilse, bana göre hareket ediyor.

Ben de manzarayı tekrar aşağı taşır textFieldDidEndEnditing: yöntemi, (ve değiştirilen giriş göre bazı model nesneleri güncellemeleri eklendi:

- (void)textFieldDidEndEditing:(UITextField *)textField {
    if ( ( textField != inputMenge ) && ( textField != inputAlter ) ) {
    	NSTimeInterval animationDuration = 0.300000011920929;
    	CGRect frame = self.view.frame;
    	frame.origin.y  = kOFFSET_FOR_KEYBOARD;
    	frame.size.height -= kOFFSET_FOR_KEYBOARD;
    	[UIView beginAnimations:@"ResizeForKeyboard" context:nil];
    	[UIView setAnimationDuration:animationDuration];
    	self.view.frame = frame;
    	[UIView commitAnimations];		
    }
    // Additional Code
}

Ancak, bu çözüm, basit bir kusur: bitince düzenleme bir "gizli" TextField öğeleri ve dokunmatik bir başka özelliği, klavye yok, görünümü gider, görünümü yukarı hareket tekrar ve klavye görünür.

Herhangi bir olasılık için devam klavyeden kaybolan ve geri gelen arasında iki düzenlemeler ("gizli" TextField öğeleri - görünümü sadece hareket ettiğinde seçilen belirsiz değişikliklerden biri olacağını gizli klavye için o olmaz gizli)?

CEVAP
13 EYLÜL 2012, PERŞEMBE


Bu çözüm ComSubVie bir dayanmaktadır.

Avantajları:

  • Aygıt döndürme destekler - tüm yönler için çalışır;
  • Animasyon süre değerlerini koda değil ve eğri, klavye bildirim onları okur;
  • Sync klavye animasyon ve özel eylemler için UIKeyboardDidShowNotification yerine UIKeyboardWillShowNotification kullanır;
  • Kaldırılan UIKeyboardBoundsUserInfoKey; kullanmaz
  • Uluslararası tuşu sayesinde klavye boyutlandırma kolları;
  • Sabit bellek klavye olayları için kaydını silerek sızıntı;
  • Tüm klavye işleme kodu ayrı bir sınıf - KBKeyboardHandler; saklanır
  • - KBKeyboardHandler Sınıf kolay olabilir esneklik / daha iyi özel ihtiyaçlarına uyacak şekilde değiştirilmiş genişletilmiş;

Sınırlamalar:

  • İOS 4 için çalışıyor ve üzerinde küçük değişiklikler eski sürümleri desteği gerekiyor;
  • UIWindow bir tek uygulamalar için çalışır. Eğer birden fazla UİWindows kullanıyorsanız, retrieveFrameFromNotification: yöntemini değiştirmek gerekebilir.

Kullanımı:

KBKeyboardHandler Vardır.h, KBKeyboardHandler.m ve KBKeyboardHandlerDelegate.h projenizde. Klavye gösterilir, gizlenir veya boyutu değiştiğinde görünüm denetleyicisi KBKeyboardHandlerDelegate protokol - adı verilecek tek bir yöntem oluşur uygulamak. KBKeyboardHandler oluşturmak ve temsilci (genellikle kendi kendine) ayarlayın. Örnek MyViewController aşağıya bakın.

KBKeyboardHandler.h:

@protocol KBKeyboardHandlerDelegate;

@interface KBKeyboardHandler : NSObject

- (id)init;

// Put 'weak' instead of 'assign' if you use ARC
@property(nonatomic, assign) id<KBKeyboardHandlerDelegate> delegate; 
@property(nonatomic) CGRect frame;

@end

KBKeyboardHandler.m:

#import "KBKeyboardHandler.h"
#import "KBKeyboardHandlerDelegate.h"

@implementation KBKeyboardHandler

- (id)init
{
    self = [super init];
    if (self)
    {
        [[NSNotificationCenter defaultCenter] addObserver:self
                                                 selector:@selector(keyboardWillShow:)
                                                     name:UIKeyboardWillShowNotification
                                                   object:nil];

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

    return self;
}

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

@synthesize delegate;
@synthesize frame;

- (void)keyboardWillShow:(NSNotification *)notification
{
    CGRect oldFrame = self.frame;    
    [self retrieveFrameFromNotification:notification];

    if (oldFrame.size.height != self.frame.size.height)
    {
        CGSize delta = CGSizeMake(self.frame.size.width - oldFrame.size.width,
                                  self.frame.size.height - oldFrame.size.height);
        if (self.delegate)
            [self notifySizeChanged:delta notification:notification];
    }
}

- (void)keyboardWillHide:(NSNotification *)notification
{
    if (self.frame.size.height > 0.0)
    {
        [self retrieveFrameFromNotification:notification];
        CGSize delta = CGSizeMake(-self.frame.size.width, -self.frame.size.height);

        if (self.delegate)
            [self notifySizeChanged:delta notification:notification];
    }

    self.frame = CGRectZero;
}

- (void)retrieveFrameFromNotification:(NSNotification *)notification
{
    CGRect keyboardRect;
    [[[notification userInfo] objectForKey:UIKeyboardFrameEndUserInfoKey] getValue:&keyboardRect];
    self.frame = [[UIApplication sharedApplication].keyWindow.rootViewController.view convertRect:keyboardRect fromView:nil];
}

- (void)notifySizeChanged:(CGSize)delta notification:(NSNotification *)notification
{
    NSDictionary *info = [notification userInfo];

    UIViewAnimationCurve curve;
    [[info objectForKey:UIKeyboardAnimationCurveUserInfoKey] getValue:&curve];

    NSTimeInterval duration;
    [[info objectForKey:UIKeyboardAnimationDurationUserInfoKey] getValue:&duration];

    void (^action)(void) = ^{
        [self.delegate keyboardSizeChanged:delta];
    };

    [UIView animateWithDuration:duration
                          delay:0.0
                        options:curve
                     animations:action
                     completion:nil];    
}

@end

KBKeyboardHandlerDelegate.h:

@protocol KBKeyboardHandlerDelegate

- (void)keyboardSizeChanged:(CGSize)delta;

@end

ÖrnekMyViewController.h:

@interface MyViewController : UIViewController<KBKeyboardHandlerDelegate>
...
@end

ÖrnekMyViewController.m:

@implementation MyViewController
{
    KBKeyboardHandler *keyboard;
}

- (void)dealloc
{
    keyboard.delegate = nil;
    [keyboard release];
    [super dealloc];
}

- (void)viewDidLoad
{
    [super viewDidLoad];
    keyboard = [[KBKeyboardHandler alloc] init];
    keyboard.delegate = self;
}

- (void)viewDidUnload
{
    [super viewDidUnload];
    keyboard.delegate = nil;
    [keyboard release];
    keyboard = nil;
}

- (void)keyboardSizeChanged:(CGSize)delta
{
    // Resize / reposition your views here. All actions performed here 
    // will appear animated.
    // delta is the difference between the previous size of the keyboard 
    // and the new one.
    // For instance when the keyboard is shown, 
    // delta may has width=768, height=264,
    // when the keyboard is hidden: width=-768, height=-264.
    // Use keyboard.frame.size to get the real keyboard size.

    // Sample:
    CGRect frame = self.view.frame;
    frame.size.height -= delta.height;
    self.view.frame = frame;
}

Bunu Paylaş:
  • Google+
  • E-Posta
Etiketler:

YORUMLAR

SPONSOR VİDEO

Rastgele Yazarlar

  • Christian Atlas

    Christian At

    26 Mart 2009
  • EEVblog

    EEVblog

    4 NİSAN 2009
  • rtisticsdev

    rtisticsdev

    31 Mayıs 2012