popover動畫的實現(xiàn)(一)

版本記錄

版本號 時間
V1.0 2017.05.17

前言

我們app中經(jīng)常用到pop動畫,比較常見的比如微信和QQ的加人等,這些都是pop動畫,oc中有原生的pop動畫類,這里我先給大家舉一個非常簡單的例子,非常簡單幾行代碼就可以搞定。

詳細

我們先看一下代碼結(jié)構(gòu)

代碼結(jié)構(gòu)

下面我們就直接看代碼吧。

1. AppDelegate.m
- (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions
{
    self.window = [[UIWindow alloc] initWithFrame:[UIScreen mainScreen].bounds];
    JJPopoverVC *popVC = [[JJPopoverVC alloc] init];
    self.window.rootViewController = popVC;
    [self.window makeKeyAndVisible];
    return YES;
}

2. JJPopoverVC.h

#import <UIKit/UIKit.h>

@interface JJPopoverVC : UIViewController

@end



3. JJPopoverVC.m
#import "JJPopoverVC.h"
#import "JJSecondVC.h"

@interface JJPopoverVC () <UIPopoverPresentationControllerDelegate>

@property (nonatomic, strong) UIButton *addButton;


@end

@implementation JJPopoverVC

#pragma mark - Override Base Function

- (void)viewDidLoad
{
    [super viewDidLoad];
    
    self.view.backgroundColor = [UIColor whiteColor];
    
    //pop動畫按鈕
    UIButton *popButton = [UIButton buttonWithType:UIButtonTypeCustom];
    [popButton setTitle:@"pop動畫" forState:UIControlStateNormal];
    [popButton addTarget:self action:@selector(popoverAnimation:) forControlEvents:UIControlEventTouchUpInside];
    popButton.center = self.view.center;
    [popButton sizeToFit];
    popButton.backgroundColor = [UIColor magentaColor];
    [self.view addSubview:popButton];
    
    //調(diào)到下個界面按鈕
    UIButton *addButton = [UIButton buttonWithType:UIButtonTypeContactAdd];
    [addButton addTarget:self action:@selector(addButtonClick:) forControlEvents:UIControlEventTouchUpInside];
    self.addButton = addButton;
    addButton.frame = CGRectMake(200, self.view.bounds.origin.y, 100, 100);
    [self.view addSubview:addButton];
}


#pragma mark - Action && Notification

- (void)popoverAnimation:(UIButton *)button
{
    UIViewController *vc = [[UIViewController alloc] init];
    vc.view.backgroundColor = [UIColor greenColor];
    vc.modalPresentationStyle = UIModalPresentationPopover;
    
    //設(shè)置彈窗控制器視圖的大小
    vc.preferredContentSize = CGSizeMake(0, 120);
    vc.popoverPresentationController.delegate = self;
    
    //設(shè)置定位控件
    vc.popoverPresentationController.sourceView = button;
    
    //設(shè)置箭頭方向向上
    vc.popoverPresentationController.permittedArrowDirections = UIPopoverArrowDirectionUp;
    
    //設(shè)置箭頭的位置,原點可以參考某一個控件的尺寸設(shè)置,寬高通常用于設(shè)置附加的偏移量,通常傳入0即可
    CGSize size = button.bounds.size;
    vc.popoverPresentationController.sourceRect = CGRectMake(size.width * 0.5, size.height, 0, 0);
    
    //設(shè)置繞開控件,注意:同一時間只能允許展現(xiàn)一個控制器,這個屬性是設(shè)置當UIPopoverController顯示出來的時候,哪些控件可以繼續(xù)跟用戶進行正常交互,點擊區(qū)域外的控件就不會讓UIPopoverController消失了。
//    vc.popoverPresentationController.passthroughViews = @[self.addButton];//繞開-按鈕可以交互
     vc.popoverPresentationController.passthroughViews = nil;//不繞開-點擊按鈕pop消失,按鈕不能交互

    //展現(xiàn)模態(tài)控制器
    [self presentViewController:vc animated:YES completion:nil];
}

- (void)addButtonClick:(UIButton *)button
{
    JJSecondVC *secondVC = [[JJSecondVC alloc] init];
    [self presentViewController:secondVC animated:YES completion:nil];
}

#pragma mark - UIPopoverPresentationControllerDelegate

- (UIModalPresentationStyle)adaptivePresentationStyleForPresentationController:(UIPresentationController *)controller
{
    //不使用系統(tǒng)樣式
    return UIModalPresentationNone;
}

@end

這里有個參數(shù)需要說一下:vc.popoverPresentationController.passthroughViews

字面意思就是繞開的意思,但是如果真正理解的話,最好寫個demo親測一下就會很清楚了。后面需要傳遞一個數(shù)組參數(shù),我們也可以給nil,就表示不繞開任何視圖。

  • 當傳遞數(shù)組的時候,我這里傳遞的是@[self.addButton],表示的意思就是繞開這個按鈕,也就是說這個按鈕還可以和用戶進行交互,同時點擊這個按鈕不會讓popover動畫隱藏回去??梢钥匆幌孪旅娴膅if圖就很清楚了。
繞開

可見這里點擊按鈕,pop動畫并不收縮回去,但是也沒控制臺打印出了下面這些:

2017-05-17 00:21:23.920 popover[1873:42346] Warning: Attempt to present <JJSecondVC: 0x7fa8b360c170>  on <JJPopoverVC: 0x7fa8b3507760> which is already presenting <UIViewController: 0x7fa8b350cc80>
2017-05-17 00:21:24.121 popover[1873:42346] Warning: Attempt to present <JJSecondVC: 0x7fa8b3427b20>  on <JJPopoverVC: 0x7fa8b3507760> which is already presenting <UIViewController: 0x7fa8b350cc80>
2017-05-17 00:21:24.361 popover[1873:42346] Warning: Attempt to present <JJSecondVC: 0x7fa8b360bd60>  on <JJPopoverVC: 0x7fa8b3507760> which is already presenting <UIViewController: 0x7fa8b350cc80>
2017-05-17 00:21:24.577 popover[1873:42346] Warning: Attempt to present <JJSecondVC: 0x7fa8b6018dc0>  on <JJPopoverVC: 0x7fa8b3507760> which is already presenting <UIViewController: 0x7fa8b350cc80>
2017-05-17 00:21:24.756 popover[1873:42346] Warning: Attempt to present <JJSecondVC: 0x7fa8b60190c0>  on <JJPopoverVC: 0x7fa8b3507760> which is already presenting <UIViewController: 0x7fa8b350cc80>

這個輸出的意思就是pop動畫已經(jīng)存在一個了,點擊button響應(yīng)的事件還是展現(xiàn)另外一個控制器。這是不允許的,因為同一時間只允許存在一個。

  • 當傳遞值為nil的時候,表示不會繞開任何控件,也就是說按鈕不參與交互,點擊按鈕和點擊其他背景一樣,pop動畫都會隱藏回去,可以看下面這個gif圖。
不繞開

后記

今天就先寫個簡單的,后面還會介紹更復雜更有趣的私人定制popover,未完,待續(xù)~~~

宇宙之美
最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請聯(lián)系作者
【社區(qū)內(nèi)容提示】社區(qū)部分內(nèi)容疑似由AI輔助生成,瀏覽時請結(jié)合常識與多方信息審慎甄別。
平臺聲明:文章內(nèi)容(如有圖片或視頻亦包括在內(nèi))由作者上傳并發(fā)布,文章內(nèi)容僅代表作者本人觀點,簡書系信息發(fā)布平臺,僅提供信息存儲服務(wù)。

相關(guān)閱讀更多精彩內(nèi)容

友情鏈接更多精彩內(nèi)容