UIScrollView的用法(不定期更新)

先从最基本的研究起,用一个例子来说明,如何创建一个UIScrollView。

在xcode新建一个基于视图的工程,然后打开项目里viewController的xib文件,在view里添加一个uiscrollview,然后安一定间距拖几个button、textfield之类的到scrollview

里,这样ui基本的框架就完成了。

下面就是代码部分了:

UIScrollViewDemoViewController.h

#import <UIKit/UIKit.h>

@interface UIScrollViewDemoViewController : UIViewController<UITextFieldDelegate,UIScrollViewDelegate> {
    IBOutlet UIScrollView * myScrollView;
    UITextField * activeField;
    CGFloat oldContentOffsetValue;
    IBOutlet UITextField * textFieldOne;
    IBOutlet UITextField * textFieldTwo;
    IBOutlet UITextField * textFieldThree;
    IBOutlet UITextField * textFieldFour;
    BOOL keyboardShown;
    BOOL isNeedSetOffset;
    
}
@property (nonatomic,retain) UITextField * activeField;
@end

上面代码里,我xib文件创建了五个iboutlet变量,分别是四个textfield和一个scrollview,然后就可以到xib文件里,把它们和对应的ui相连接赶来。

其它的变量在实现文件里会用到。


UIScrollViewDemoViewController.m


#import "UIScrollViewDemoViewController.h"

@implementation UIScrollViewDemoViewController

@synthesize activeField;

- (void)dealloc
{
    [myScrollView release];
    [activeField release];
    [textFieldOne release];
    [textFieldTwo release];
    [textFieldThree release];
    [textFieldFour release];
    [super dealloc];
}

- (void)didReceiveMemoryWarning
{
    // Releases the view if it doesn't have a superview.
    [super didReceiveMemoryWarning];
    
    // Release any cached data, images, etc that aren't in use.
}

#pragma mark - View lifecycle


// Implement viewDidLoad to do additional setup after loading the view, typically from a nib.
- (void)viewDidLoad
{
    [super viewDidLoad];
    
    textFieldOne.delegate = self;
    textFieldTwo.delegate = self;
    textFieldThree.delegate = self;
    textFieldFour.delegate = self;
    
    
    myScrollView.contentSize = CGSizeMake(myScrollView.frame.size.width, 1400.0f);
    myScrollView.scrollEnabled = YES;
    myScrollView.delegate = self;
    
    keyboardShown = NO;
    [self performSelector:@selector(registerForKeyboardNotifications)];
    
}


- (void)viewDidUnload
{
    [super viewDidUnload];
    // Release any retained subviews of the main view.
    // e.g. self.myOutlet = nil;
}

- (BOOL)shouldAutorotateToInterfaceOrientation:(UIInterfaceOrientation)interfaceOrientation
{
    // Return YES for supported orientations
    return (interfaceOrientation == UIInterfaceOrientationPortrait);
}

#pragma mark - UITextField Delegate
-(void)textFieldDidBeginEditing:(UITextField *)textField
{
    activeField = textField;
}

-(void)textFieldDidEndEditing:(UITextField *)textField
{
    activeField = nil;
}

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

#pragma mark -Keyboard Helper Method
// Call this method somewhere in your view controller setup code.
- (void)registerForKeyboardNotifications
{
    [[NSNotificationCenter defaultCenter] addObserver:self
                                             selector:@selector(keyboardWasShown:)
                                                 name:UIKeyboardDidShowNotification object:nil];
    
    [[NSNotificationCenter defaultCenter] addObserver:self
                                             selector:@selector(keyboardWasHidden:)
                                                 name:UIKeyboardDidHideNotification object:nil];
}

// Called when the UIKeyboardDidShowNotification is sent.
- (void)keyboardWasShown:(NSNotification*)aNotification
{
    NSLog(@"-------");
    if (keyboardShown)
        return;
    
    NSDictionary* info = [aNotification userInfo];
    
    // Get the size of the keyboard.
    NSValue* aValue = [info objectForKey:UIKeyboardBoundsUserInfoKey];
    CGSize keyboardSize = [aValue CGRectValue].size;
    
    // Resize the scroll view (which is the root view of the window)
    CGRect viewFrame = [myScrollView frame];
    viewFrame.size.height -= keyboardSize.height;
    myScrollView.frame = viewFrame;
    
    
    // Scroll the active text field into view.
    CGRect textFieldRect = [activeField frame];
    [myScrollView scrollRectToVisible:textFieldRect animated:YES];
    
    oldContentOffsetValue = [myScrollView contentOffset].y;
    
    
    CGFloat value = (activeField.frame.origin.y+myScrollView.frame.origin.y+activeField.frame.size.height - self.view.frame.size.height + keyboardSize.height)+2.0f;
    if (value > 0) {
        [myScrollView setContentOffset:CGPointMake(0, value) animated:YES];
        isNeedSetOffset = YES;
    }


    keyboardShown = YES;
}


// Called when the UIKeyboardDidHideNotification is sent
- (void)keyboardWasHidden:(NSNotification*)aNotification
{

    NSDictionary* info = [aNotification userInfo];
    
    // Get the size of the keyboard.
    NSValue* aValue = [info objectForKey:UIKeyboardBoundsUserInfoKey];
    CGSize keyboardSize = [aValue CGRectValue].size;
    
    // Reset the height of the scroll view to its original value
    CGRect viewFrame = [myScrollView frame];
    viewFrame.size.height += keyboardSize.height;
    myScrollView.frame = viewFrame;
        
    if (isNeedSetOffset) {
        [myScrollView setContentOffset:CGPointMake(0, oldContentOffsetValue) animated:YES];
    }

    isNeedSetOffset = NO;

    keyboardShown = NO;
}

@end

代码有点长,一步步解析吧。

首先是viewDidLoad方法里进行一些初始化处理:

- (void)viewDidLoad
{
    [super viewDidLoad];
    
    textFieldOne.delegate = self;//设置textField的delegate,主要是为了显示和隐藏弹出的键盘用的
    textFieldTwo.delegate = self;
    textFieldThree.delegate = self;
    textFieldFour.delegate = self;
    
    //使用scrollView很关键的地方,设置contentSize,一般是安你的scrollView的size来设置,后面的height可以适当多个300~400
    myScrollView.contentSize = CGSizeMake(myScrollView.frame.size.width, 1400.0f);
    myScrollView.scrollEnabled = YES;//这个默认就是YES,这里多余了。
    myScrollView.delegate = self;//设置scrollView的delegate,需要监听滚动事件的可以实现它的delegate方法
    
    keyboardShown = NO;//一个状态标志,主要用来标识键盘的显隐状态
    [self performSelector:@selector(registerForKeyboardNotifications)];//这个方法用来处理当textField被自己弹出的键盘挡住时,把它滚动到适当位置
    
}

接着就是相应的

registerForKeyboardNotifications方法,用来把textField滚动到适当的位置。

- (void)registerForKeyboardNotifications
{
    //添加自己做为观察者,以获取键盘显示时的通知
    [[NSNotificationCenter defaultCenter] addObserver:self
                                             selector:@selector(keyboardWasShown:)
                                                 name:UIKeyboardDidShowNotification object:nil];
    //添加自己做为观察者,以获取键盘隐藏时的通知
    [[NSNotificationCenter defaultCenter] addObserver:self
                                             selector:@selector(keyboardWasHidden:)
                                                 name:UIKeyboardDidHideNotification object:nil];
}

// 键盘出现时调用此方法
- (void)keyboardWasShown:(NSNotification*)aNotification
{
    //如果键盘是显示状态,不用做重复的操作
    if (keyboardShown)
        return;
    
    //获得键盘通知的用户信息字典
    NSDictionary* info = [aNotification userInfo];
    
    // 取得键盘尺寸.
    NSValue* aValue = [info objectForKey:UIKeyboardBoundsUserInfoKey];
    CGSize keyboardSize = [aValue CGRectValue].size;
    
    // 重新设置scrollView的size
    CGRect viewFrame = [myScrollView frame];
    viewFrame.size.height -= keyboardSize.height;
    myScrollView.frame = viewFrame;
    
    
    // 把当前被挡住的text field滚动到view中适当的可见位置.
    CGRect textFieldRect = [activeField frame];
    [myScrollView scrollRectToVisible:textFieldRect animated:YES];
    
    
    //记录当前textField的偏移量,方便隐藏键盘时,恢复textField到原来位置
    oldContentOffsetValue = [myScrollView contentOffset].y;
    
    //计算textField滚动到的适当位置
    CGFloat value = (activeField.frame.origin.y+myScrollView.frame.origin.y+activeField.frame.size.height - self.view.frame.size.height + keyboardSize.height)+2.0f;
    
    //value>0则表示需要滚动,小于0表示当前textField没有被挡住,不需要滚动
    if (value > 0) {
        //使textField滚动到适当位置
        [myScrollView setContentOffset:CGPointMake(0, value) animated:YES];
        isNeedSetOffset = YES;//更改状态标志为需要滚动
    }

    //更改键盘状态标志为已显示
    keyboardShown = YES;
}


// 键盘隐藏时调用此方法
- (void)keyboardWasHidden:(NSNotification*)aNotification
{

    
    NSDictionary* info = [aNotification userInfo];
    
    // Get the size of the keyboard.
    NSValue* aValue = [info objectForKey:UIKeyboardBoundsUserInfoKey];
    CGSize keyboardSize = [aValue CGRectValue].size;
    
    // Reset the height of the scroll view to its original value
    CGRect viewFrame = [myScrollView frame];
    viewFrame.size.height += keyboardSize.height;
    myScrollView.frame = viewFrame;
    
    //如果状态标志为需要滚动,则要执行textFiled复位操作
    if (isNeedSetOffset) {
        //oldContentOffsetValue记录了textField原来的位置,复位即可
        [myScrollView setContentOffset:CGPointMake(0, oldContentOffsetValue) animated:YES];
    }

    //复位状态标志
    isNeedSetOffset = NO;
    keyboardShown = NO;
}

这样一个简单的scrollView就做好了,滚动被挡住的内容到适当位置也是很常用的功能。


  • 0
    点赞
  • 5
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值