| | |
| | | static NSInteger const kAnimationOptionCurveIOS7 = (7 << 16); |
| | | |
| | | KLCPopupLayout KLCPopupLayoutMake(KLCPopupHorizontalLayout horizontal, KLCPopupVerticalLayout vertical){ |
| | | KLCPopupLayout layout; |
| | | layout.horizontal = horizontal; |
| | | layout.vertical = vertical; |
| | | return layout; |
| | | KLCPopupLayout layout; |
| | | layout.horizontal = horizontal; |
| | | layout.vertical = vertical; |
| | | return layout; |
| | | } |
| | | |
| | | const KLCPopupLayout KLCPopupLayoutCenter = { KLCPopupHorizontalLayoutCenter, KLCPopupVerticalLayoutCenter }; |
| | |
| | | |
| | | |
| | | @interface KLCPopup () { |
| | | // views |
| | | UIView* _backgroundView; |
| | | UIView* _containerView; |
| | | |
| | | // state flags |
| | | BOOL _isBeingShown; |
| | | BOOL _isShowing; |
| | | BOOL _isBeingDismissed; |
| | | // views |
| | | UIView* _backgroundView; |
| | | UIView* _containerView; |
| | | |
| | | // state flags |
| | | BOOL _isBeingShown; |
| | | BOOL _isShowing; |
| | | BOOL _isBeingDismissed; |
| | | } |
| | | |
| | | - (void)updateForInterfaceOrientation; |
| | |
| | | |
| | | |
| | | - (void)dealloc { |
| | | [NSObject cancelPreviousPerformRequestsWithTarget:self]; |
| | | |
| | | // stop listening to notifications |
| | | [[NSNotificationCenter defaultCenter] removeObserver:self]; |
| | | [NSObject cancelPreviousPerformRequestsWithTarget:self]; |
| | | |
| | | // stop listening to notifications |
| | | [[NSNotificationCenter defaultCenter] removeObserver:self]; |
| | | } |
| | | |
| | | |
| | | - (id)init { |
| | | return [self initWithFrame:[[UIScreen mainScreen] bounds]]; |
| | | return [self initWithFrame:[[UIScreen mainScreen] bounds]]; |
| | | } |
| | | |
| | | |
| | | - (id)initWithFrame:(CGRect)frame { |
| | | self = [super initWithFrame:frame]; |
| | | if (self) { |
| | | |
| | | self.userInteractionEnabled = YES; |
| | | self.backgroundColor = [UIColor clearColor]; |
| | | self.alpha = 0; |
| | | self.autoresizingMask = UIViewAutoresizingFlexibleWidth | UIViewAutoresizingFlexibleHeight; |
| | | self.autoresizesSubviews = YES; |
| | | |
| | | self.shouldDismissOnBackgroundTouch = YES; |
| | | self.shouldDismissOnContentTouch = NO; |
| | | |
| | | self.showType = KLCPopupShowTypeShrinkIn; |
| | | self.dismissType = KLCPopupDismissTypeShrinkOut; |
| | | self.maskType = KLCPopupMaskTypeDimmed; |
| | | self.dimmedMaskAlpha = 0.5; |
| | | |
| | | _isBeingShown = NO; |
| | | _isShowing = NO; |
| | | _isBeingDismissed = NO; |
| | | |
| | | _backgroundView = [[UIView alloc] init]; |
| | | _backgroundView.backgroundColor = [UIColor clearColor]; |
| | | _backgroundView.userInteractionEnabled = NO; |
| | | _backgroundView.autoresizingMask = UIViewAutoresizingFlexibleWidth | UIViewAutoresizingFlexibleHeight; |
| | | _backgroundView.frame = self.bounds; |
| | | |
| | | _containerView = [[UIView alloc] init]; |
| | | _containerView.autoresizesSubviews = NO; |
| | | _containerView.userInteractionEnabled = YES; |
| | | _containerView.backgroundColor = [UIColor clearColor]; |
| | | |
| | | [self addSubview:_backgroundView]; |
| | | [self addSubview:_containerView]; |
| | | |
| | | // register for notifications |
| | | [[NSNotificationCenter defaultCenter] addObserver:self |
| | | selector:@selector(didChangeStatusBarOrientation:) |
| | | name:UIApplicationDidChangeStatusBarFrameNotification |
| | | object:nil]; |
| | | } |
| | | return self; |
| | | self = [super initWithFrame:frame]; |
| | | if (self) { |
| | | |
| | | self.userInteractionEnabled = YES; |
| | | self.backgroundColor = [UIColor clearColor]; |
| | | self.alpha = 0; |
| | | self.autoresizingMask = UIViewAutoresizingFlexibleWidth | UIViewAutoresizingFlexibleHeight; |
| | | self.autoresizesSubviews = YES; |
| | | |
| | | self.shouldDismissOnBackgroundTouch = YES; |
| | | self.shouldDismissOnContentTouch = NO; |
| | | |
| | | self.showType = KLCPopupShowTypeShrinkIn; |
| | | self.dismissType = KLCPopupDismissTypeShrinkOut; |
| | | self.maskType = KLCPopupMaskTypeDimmed; |
| | | self.dimmedMaskAlpha = 0.5; |
| | | |
| | | _isBeingShown = NO; |
| | | _isShowing = NO; |
| | | _isBeingDismissed = NO; |
| | | |
| | | _backgroundView = [[UIView alloc] init]; |
| | | _backgroundView.backgroundColor = [UIColor clearColor]; |
| | | _backgroundView.userInteractionEnabled = NO; |
| | | _backgroundView.autoresizingMask = UIViewAutoresizingFlexibleWidth | UIViewAutoresizingFlexibleHeight; |
| | | _backgroundView.frame = self.bounds; |
| | | |
| | | _containerView = [[UIView alloc] init]; |
| | | _containerView.autoresizesSubviews = NO; |
| | | _containerView.userInteractionEnabled = YES; |
| | | _containerView.backgroundColor = [UIColor clearColor]; |
| | | |
| | | [self addSubview:_backgroundView]; |
| | | [self addSubview:_containerView]; |
| | | |
| | | // register for notifications |
| | | [[NSNotificationCenter defaultCenter] addObserver:self |
| | | selector:@selector(didChangeStatusBarOrientation:) |
| | | name:UIApplicationDidChangeStatusBarFrameNotification |
| | | object:nil]; |
| | | } |
| | | return self; |
| | | } |
| | | |
| | | |
| | | #pragma mark - UIView |
| | | |
| | | - (UIView *)hitTest:(CGPoint)point withEvent:(UIEvent *)event { |
| | | |
| | | UIView* hitView = [super hitTest:point withEvent:event]; |
| | | if (hitView == self) { |
| | | |
| | | // Try to dismiss if backgroundTouch flag set. |
| | | if (_shouldDismissOnBackgroundTouch) { |
| | | [self dismiss:YES]; |
| | | } |
| | | |
| | | // If no mask, then return nil so touch passes through to underlying views. |
| | | if (_maskType == KLCPopupMaskTypeNone) { |
| | | return nil; |
| | | UIView* hitView = [super hitTest:point withEvent:event]; |
| | | if (hitView == self) { |
| | | |
| | | // Try to dismiss if backgroundTouch flag set. |
| | | if (_shouldDismissOnBackgroundTouch) { |
| | | [self dismiss:YES]; |
| | | } |
| | | |
| | | // If no mask, then return nil so touch passes through to underlying views. |
| | | if (_maskType == KLCPopupMaskTypeNone) { |
| | | return nil; |
| | | } else { |
| | | return hitView; |
| | | } |
| | | |
| | | } else { |
| | | return hitView; |
| | | |
| | | // If view is within containerView and contentTouch flag set, then try to hide. |
| | | if ([hitView isDescendantOfView:_containerView]) { |
| | | if (_shouldDismissOnContentTouch) { |
| | | [self dismiss:YES]; |
| | | } |
| | | } |
| | | return hitView; |
| | | } |
| | | |
| | | } else { |
| | | |
| | | // If view is within containerView and contentTouch flag set, then try to hide. |
| | | if ([hitView isDescendantOfView:_containerView]) { |
| | | if (_shouldDismissOnContentTouch) { |
| | | [self dismiss:YES]; |
| | | } |
| | | } |
| | | return hitView; |
| | | } |
| | | } |
| | | |
| | | |
| | |
| | | |
| | | + (KLCPopup*)popupWithContentView:(UIView*)contentView |
| | | { |
| | | KLCPopup* popup = [[[self class] alloc] init]; |
| | | popup.contentView = contentView; |
| | | return popup; |
| | | KLCPopup* popup = [[[self class] alloc] init]; |
| | | popup.contentView = contentView; |
| | | return popup; |
| | | } |
| | | |
| | | |
| | |
| | | dismissOnBackgroundTouch:(BOOL)shouldDismissOnBackgroundTouch |
| | | dismissOnContentTouch:(BOOL)shouldDismissOnContentTouch |
| | | { |
| | | KLCPopup* popup = [[[self class] alloc] init]; |
| | | popup.contentView = contentView; |
| | | popup.showType = showType; |
| | | popup.dismissType = dismissType; |
| | | popup.maskType = maskType; |
| | | popup.shouldDismissOnBackgroundTouch = shouldDismissOnBackgroundTouch; |
| | | popup.shouldDismissOnContentTouch = shouldDismissOnContentTouch; |
| | | return popup; |
| | | KLCPopup* popup = [[[self class] alloc] init]; |
| | | popup.contentView = contentView; |
| | | popup.showType = showType; |
| | | popup.dismissType = dismissType; |
| | | popup.maskType = maskType; |
| | | popup.shouldDismissOnBackgroundTouch = shouldDismissOnBackgroundTouch; |
| | | popup.shouldDismissOnContentTouch = shouldDismissOnContentTouch; |
| | | return popup; |
| | | } |
| | | |
| | | |
| | | + (void)dismissAllPopups { |
| | | NSArray* windows = [[UIApplication sharedApplication] windows]; |
| | | for (UIWindow* window in windows) { |
| | | [window forEachPopupDoBlock:^(KLCPopup *popup) { |
| | | [popup dismiss:NO]; |
| | | }]; |
| | | } |
| | | NSArray* windows = [[UIApplication sharedApplication] windows]; |
| | | for (UIWindow* window in windows) { |
| | | [window forEachPopupDoBlock:^(KLCPopup *popup) { |
| | | [popup dismiss:NO]; |
| | | }]; |
| | | } |
| | | } |
| | | |
| | | |
| | | #pragma mark - Public |
| | | |
| | | - (void)show { |
| | | [self showWithLayout:KLCPopupLayoutCenter]; |
| | | [self showWithLayout:KLCPopupLayoutCenter]; |
| | | } |
| | | |
| | | |
| | | - (void)showWithLayout:(KLCPopupLayout)layout { |
| | | [self showWithLayout:layout duration:0.0]; |
| | | [self showWithLayout:layout duration:0.0]; |
| | | } |
| | | |
| | | |
| | | - (void)showWithDuration:(NSTimeInterval)duration { |
| | | [self showWithLayout:KLCPopupLayoutCenter duration:duration]; |
| | | [self showWithLayout:KLCPopupLayoutCenter duration:duration]; |
| | | } |
| | | |
| | | |
| | | - (void)showWithLayout:(KLCPopupLayout)layout duration:(NSTimeInterval)duration { |
| | | NSDictionary* parameters = @{@"layout" : [NSValue valueWithKLCPopupLayout:layout], |
| | | @"duration" : @(duration)}; |
| | | [self showWithParameters:parameters]; |
| | | NSDictionary* parameters = @{@"layout" : [NSValue valueWithKLCPopupLayout:layout], |
| | | @"duration" : @(duration)}; |
| | | [self showWithParameters:parameters]; |
| | | } |
| | | |
| | | |
| | | - (void)showAtCenter:(CGPoint)center inView:(UIView*)view { |
| | | [self showAtCenter:center inView:view withDuration:0.0]; |
| | | [self showAtCenter:center inView:view withDuration:0.0]; |
| | | } |
| | | |
| | | |
| | | - (void)showAtCenter:(CGPoint)center inView:(UIView *)view withDuration:(NSTimeInterval)duration { |
| | | NSMutableDictionary* parameters = [NSMutableDictionary dictionary]; |
| | | [parameters setValue:[NSValue valueWithCGPoint:center] forKey:@"center"]; |
| | | [parameters setValue:@(duration) forKey:@"duration"]; |
| | | [parameters setValue:view forKey:@"view"]; |
| | | [self showWithParameters:[NSDictionary dictionaryWithDictionary:parameters]]; |
| | | NSMutableDictionary* parameters = [NSMutableDictionary dictionary]; |
| | | [parameters setValue:[NSValue valueWithCGPoint:center] forKey:@"center"]; |
| | | [parameters setValue:@(duration) forKey:@"duration"]; |
| | | [parameters setValue:view forKey:@"view"]; |
| | | [self showWithParameters:[NSDictionary dictionaryWithDictionary:parameters]]; |
| | | } |
| | | |
| | | |
| | | - (void)dismiss:(BOOL)animated { |
| | | |
| | | if (_isShowing && !_isBeingDismissed) { |
| | | _isBeingShown = NO; |
| | | _isShowing = NO; |
| | | _isBeingDismissed = YES; |
| | | |
| | | // cancel previous dismiss requests (i.e. the dismiss after duration call). |
| | | [NSObject cancelPreviousPerformRequestsWithTarget:self selector:@selector(dismiss) object:nil]; |
| | | |
| | | [self willStartDismissing]; |
| | | |
| | | if (self.willStartDismissingCompletion != nil) { |
| | | self.willStartDismissingCompletion(); |
| | | } |
| | | |
| | | dispatch_async( dispatch_get_main_queue(), ^{ |
| | | |
| | | // Animate background if needed |
| | | void (^backgroundAnimationBlock)(void) = ^(void) { |
| | | _backgroundView.alpha = 0.0; |
| | | }; |
| | | |
| | | if (animated && (_showType != KLCPopupShowTypeNone)) { |
| | | // Make fade happen faster than motion. Use linear for fades. |
| | | [UIView animateWithDuration:0.15 |
| | | delay:0 |
| | | options:UIViewAnimationOptionCurveLinear |
| | | animations:backgroundAnimationBlock |
| | | completion:NULL]; |
| | | } else { |
| | | backgroundAnimationBlock(); |
| | | } |
| | | |
| | | // Setup completion block |
| | | void (^completionBlock)(BOOL) = ^(BOOL finished) { |
| | | |
| | | [self removeFromSuperview]; |
| | | |
| | | if (_isShowing && !_isBeingDismissed) { |
| | | _isBeingShown = NO; |
| | | _isShowing = NO; |
| | | _isBeingDismissed = NO; |
| | | _isBeingDismissed = YES; |
| | | |
| | | [self didFinishDismissing]; |
| | | // cancel previous dismiss requests (i.e. the dismiss after duration call). |
| | | [NSObject cancelPreviousPerformRequestsWithTarget:self selector:@selector(dismiss) object:nil]; |
| | | |
| | | if (self.didFinishDismissingCompletion != nil) { |
| | | self.didFinishDismissingCompletion(); |
| | | [self willStartDismissing]; |
| | | |
| | | if (self.willStartDismissingCompletion != nil) { |
| | | self.willStartDismissingCompletion(); |
| | | } |
| | | }; |
| | | |
| | | NSTimeInterval bounce1Duration = 0.13; |
| | | NSTimeInterval bounce2Duration = (bounce1Duration * 2.0); |
| | | |
| | | // Animate content if needed |
| | | if (animated) { |
| | | switch (_dismissType) { |
| | | case KLCPopupDismissTypeFadeOut: { |
| | | [UIView animateWithDuration:0.15 |
| | | delay:0 |
| | | options:UIViewAnimationOptionCurveLinear |
| | | animations:^{ |
| | | _containerView.alpha = 0.0; |
| | | } completion:completionBlock]; |
| | | break; |
| | | } |
| | | |
| | | dispatch_async( dispatch_get_main_queue(), ^{ |
| | | |
| | | case KLCPopupDismissTypeGrowOut: { |
| | | [UIView animateWithDuration:0.15 |
| | | delay:0 |
| | | options:kAnimationOptionCurveIOS7 |
| | | animations:^{ |
| | | _containerView.alpha = 0.0; |
| | | _containerView.transform = CGAffineTransformMakeScale(1.1, 1.1); |
| | | } completion:completionBlock]; |
| | | break; |
| | | } |
| | | // Animate background if needed |
| | | void (^backgroundAnimationBlock)(void) = ^(void) { |
| | | self->_backgroundView.alpha = 0.0; |
| | | }; |
| | | |
| | | case KLCPopupDismissTypeShrinkOut: { |
| | | [UIView animateWithDuration:0.15 |
| | | delay:0 |
| | | options:kAnimationOptionCurveIOS7 |
| | | animations:^{ |
| | | _containerView.alpha = 0.0; |
| | | _containerView.transform = CGAffineTransformMakeScale(0.8, 0.8); |
| | | } completion:completionBlock]; |
| | | break; |
| | | } |
| | | if (animated && (self->_showType != KLCPopupShowTypeNone)) { |
| | | // Make fade happen faster than motion. Use linear for fades. |
| | | [UIView animateWithDuration:0.15 |
| | | delay:0 |
| | | options:UIViewAnimationOptionCurveLinear |
| | | animations:backgroundAnimationBlock |
| | | completion:NULL]; |
| | | } else { |
| | | backgroundAnimationBlock(); |
| | | } |
| | | |
| | | case KLCPopupDismissTypeSlideOutToTop: { |
| | | [UIView animateWithDuration:0.30 |
| | | delay:0 |
| | | options:kAnimationOptionCurveIOS7 |
| | | animations:^{ |
| | | CGRect finalFrame = _containerView.frame; |
| | | finalFrame.origin.y = -CGRectGetHeight(finalFrame); |
| | | _containerView.frame = finalFrame; |
| | | } |
| | | completion:completionBlock]; |
| | | break; |
| | | } |
| | | // Setup completion block |
| | | void (^completionBlock)(BOOL) = ^(BOOL finished) { |
| | | |
| | | [self removeFromSuperview]; |
| | | |
| | | self->_isBeingShown = NO; |
| | | self->_isShowing = NO; |
| | | self->_isBeingDismissed = NO; |
| | | |
| | | [self didFinishDismissing]; |
| | | |
| | | if (self.didFinishDismissingCompletion != nil) { |
| | | self.didFinishDismissingCompletion(); |
| | | } |
| | | }; |
| | | |
| | | case KLCPopupDismissTypeSlideOutToBottom: { |
| | | [UIView animateWithDuration:0.30 |
| | | delay:0 |
| | | options:kAnimationOptionCurveIOS7 |
| | | animations:^{ |
| | | CGRect finalFrame = _containerView.frame; |
| | | finalFrame.origin.y = CGRectGetHeight(self.bounds); |
| | | _containerView.frame = finalFrame; |
| | | } |
| | | completion:completionBlock]; |
| | | break; |
| | | } |
| | | NSTimeInterval bounce1Duration = 0.13; |
| | | NSTimeInterval bounce2Duration = (bounce1Duration * 2.0); |
| | | |
| | | case KLCPopupDismissTypeSlideOutToLeft: { |
| | | [UIView animateWithDuration:0.30 |
| | | delay:0 |
| | | options:kAnimationOptionCurveIOS7 |
| | | animations:^{ |
| | | CGRect finalFrame = _containerView.frame; |
| | | finalFrame.origin.x = -CGRectGetWidth(finalFrame); |
| | | _containerView.frame = finalFrame; |
| | | } |
| | | completion:completionBlock]; |
| | | break; |
| | | } |
| | | // Animate content if needed |
| | | if (animated) { |
| | | switch (self.dismissType) { |
| | | case KLCPopupDismissTypeFadeOut: { |
| | | [UIView animateWithDuration:0.15 |
| | | delay:0 |
| | | options:UIViewAnimationOptionCurveLinear |
| | | animations:^{ |
| | | self->_containerView.alpha = 0.0; |
| | | } completion:completionBlock]; |
| | | break; |
| | | } |
| | | |
| | | case KLCPopupDismissTypeGrowOut: { |
| | | [UIView animateWithDuration:0.15 |
| | | delay:0 |
| | | options:kAnimationOptionCurveIOS7 |
| | | animations:^{ |
| | | self->_containerView.alpha = 0.0; |
| | | self->_containerView.transform = CGAffineTransformMakeScale(1.1, 1.1); |
| | | } completion:completionBlock]; |
| | | break; |
| | | } |
| | | |
| | | case KLCPopupDismissTypeShrinkOut: { |
| | | [UIView animateWithDuration:0.15 |
| | | delay:0 |
| | | options:kAnimationOptionCurveIOS7 |
| | | animations:^{ |
| | | self->_containerView.alpha = 0.0; |
| | | self->_containerView.transform = CGAffineTransformMakeScale(0.8, 0.8); |
| | | } completion:completionBlock]; |
| | | break; |
| | | } |
| | | |
| | | case KLCPopupDismissTypeSlideOutToTop: { |
| | | [UIView animateWithDuration:0.30 |
| | | delay:0 |
| | | options:kAnimationOptionCurveIOS7 |
| | | animations:^{ |
| | | CGRect finalFrame = self->_containerView.frame; |
| | | finalFrame.origin.y = -CGRectGetHeight(finalFrame); |
| | | self->_containerView.frame = finalFrame; |
| | | } |
| | | completion:completionBlock]; |
| | | break; |
| | | } |
| | | |
| | | case KLCPopupDismissTypeSlideOutToBottom: { |
| | | [UIView animateWithDuration:0.30 |
| | | delay:0 |
| | | options:kAnimationOptionCurveIOS7 |
| | | animations:^{ |
| | | CGRect finalFrame = self->_containerView.frame; |
| | | finalFrame.origin.y = CGRectGetHeight(self.bounds); |
| | | self->_containerView.frame = finalFrame; |
| | | } |
| | | completion:completionBlock]; |
| | | break; |
| | | } |
| | | |
| | | case KLCPopupDismissTypeSlideOutToLeft: { |
| | | [UIView animateWithDuration:0.30 |
| | | delay:0 |
| | | options:kAnimationOptionCurveIOS7 |
| | | animations:^{ |
| | | CGRect finalFrame = self->_containerView.frame; |
| | | finalFrame.origin.x = -CGRectGetWidth(finalFrame); |
| | | self->_containerView.frame = finalFrame; |
| | | } |
| | | completion:completionBlock]; |
| | | break; |
| | | } |
| | | |
| | | case KLCPopupDismissTypeSlideOutToRight: { |
| | | [UIView animateWithDuration:0.30 |
| | | delay:0 |
| | | options:kAnimationOptionCurveIOS7 |
| | | animations:^{ |
| | | CGRect finalFrame = self->_containerView.frame; |
| | | finalFrame.origin.x = CGRectGetWidth(self.bounds); |
| | | self->_containerView.frame = finalFrame; |
| | | } |
| | | completion:completionBlock]; |
| | | |
| | | break; |
| | | } |
| | | |
| | | case KLCPopupDismissTypeBounceOut: { |
| | | [UIView animateWithDuration:bounce1Duration |
| | | delay:0 |
| | | options:UIViewAnimationOptionCurveEaseOut |
| | | animations:^(void){ |
| | | self->_containerView.transform = CGAffineTransformMakeScale(1.1, 1.1); |
| | | } |
| | | completion:^(BOOL finished){ |
| | | |
| | | [UIView animateWithDuration:bounce2Duration |
| | | delay:0 |
| | | options:UIViewAnimationOptionCurveEaseIn |
| | | animations:^(void){ |
| | | self->_containerView.alpha = 0.0; |
| | | self->_containerView.transform = CGAffineTransformMakeScale(0.1, 0.1); |
| | | } |
| | | completion:completionBlock]; |
| | | }]; |
| | | |
| | | break; |
| | | } |
| | | |
| | | case KLCPopupDismissTypeBounceOutToTop: { |
| | | [UIView animateWithDuration:bounce1Duration |
| | | delay:0 |
| | | options:UIViewAnimationOptionCurveEaseOut |
| | | animations:^(void){ |
| | | CGRect finalFrame = self->_containerView.frame; |
| | | finalFrame.origin.y += 40.0; |
| | | self->_containerView.frame = finalFrame; |
| | | } |
| | | completion:^(BOOL finished){ |
| | | |
| | | [UIView animateWithDuration:bounce2Duration |
| | | delay:0 |
| | | options:UIViewAnimationOptionCurveEaseIn |
| | | animations:^(void){ |
| | | CGRect finalFrame = self->_containerView.frame; |
| | | finalFrame.origin.y = -CGRectGetHeight(finalFrame); |
| | | self->_containerView.frame = finalFrame; |
| | | } |
| | | completion:completionBlock]; |
| | | }]; |
| | | |
| | | break; |
| | | } |
| | | |
| | | case KLCPopupDismissTypeBounceOutToBottom: { |
| | | [UIView animateWithDuration:bounce1Duration |
| | | delay:0 |
| | | options:UIViewAnimationOptionCurveEaseOut |
| | | animations:^(void){ |
| | | CGRect finalFrame = self->_containerView.frame; |
| | | finalFrame.origin.y -= 40.0; |
| | | self->_containerView.frame = finalFrame; |
| | | } |
| | | completion:^(BOOL finished){ |
| | | |
| | | [UIView animateWithDuration:bounce2Duration |
| | | delay:0 |
| | | options:UIViewAnimationOptionCurveEaseIn |
| | | animations:^(void){ |
| | | CGRect finalFrame = self->_containerView.frame; |
| | | finalFrame.origin.y = CGRectGetHeight(self.bounds); |
| | | self->_containerView.frame = finalFrame; |
| | | } |
| | | completion:completionBlock]; |
| | | }]; |
| | | |
| | | break; |
| | | } |
| | | |
| | | case KLCPopupDismissTypeBounceOutToLeft: { |
| | | [UIView animateWithDuration:bounce1Duration |
| | | delay:0 |
| | | options:UIViewAnimationOptionCurveEaseOut |
| | | animations:^(void){ |
| | | CGRect finalFrame = self->_containerView.frame; |
| | | finalFrame.origin.x += 40.0; |
| | | self->_containerView.frame = finalFrame; |
| | | } |
| | | completion:^(BOOL finished){ |
| | | |
| | | [UIView animateWithDuration:bounce2Duration |
| | | delay:0 |
| | | options:UIViewAnimationOptionCurveEaseIn |
| | | animations:^(void){ |
| | | CGRect finalFrame = self->_containerView.frame; |
| | | finalFrame.origin.x = -CGRectGetWidth(finalFrame); |
| | | self->_containerView.frame = finalFrame; |
| | | } |
| | | completion:completionBlock]; |
| | | }]; |
| | | break; |
| | | } |
| | | |
| | | case KLCPopupDismissTypeBounceOutToRight: { |
| | | [UIView animateWithDuration:bounce1Duration |
| | | delay:0 |
| | | options:UIViewAnimationOptionCurveEaseOut |
| | | animations:^(void){ |
| | | CGRect finalFrame = self->_containerView.frame; |
| | | finalFrame.origin.x -= 40.0; |
| | | self->_containerView.frame = finalFrame; |
| | | } |
| | | completion:^(BOOL finished){ |
| | | |
| | | [UIView animateWithDuration:bounce2Duration |
| | | delay:0 |
| | | options:UIViewAnimationOptionCurveEaseIn |
| | | animations:^(void){ |
| | | CGRect finalFrame = self->_containerView.frame; |
| | | finalFrame.origin.x = CGRectGetWidth(self.bounds); |
| | | self->_containerView.frame = finalFrame; |
| | | } |
| | | completion:completionBlock]; |
| | | }]; |
| | | break; |
| | | } |
| | | |
| | | default: { |
| | | self.containerView.alpha = 0.0; |
| | | completionBlock(YES); |
| | | break; |
| | | } |
| | | } |
| | | } else { |
| | | self.containerView.alpha = 0.0; |
| | | completionBlock(YES); |
| | | } |
| | | |
| | | case KLCPopupDismissTypeSlideOutToRight: { |
| | | [UIView animateWithDuration:0.30 |
| | | delay:0 |
| | | options:kAnimationOptionCurveIOS7 |
| | | animations:^{ |
| | | CGRect finalFrame = _containerView.frame; |
| | | finalFrame.origin.x = CGRectGetWidth(self.bounds); |
| | | _containerView.frame = finalFrame; |
| | | } |
| | | completion:completionBlock]; |
| | | |
| | | break; |
| | | } |
| | | |
| | | case KLCPopupDismissTypeBounceOut: { |
| | | [UIView animateWithDuration:bounce1Duration |
| | | delay:0 |
| | | options:UIViewAnimationOptionCurveEaseOut |
| | | animations:^(void){ |
| | | _containerView.transform = CGAffineTransformMakeScale(1.1, 1.1); |
| | | } |
| | | completion:^(BOOL finished){ |
| | | |
| | | [UIView animateWithDuration:bounce2Duration |
| | | delay:0 |
| | | options:UIViewAnimationOptionCurveEaseIn |
| | | animations:^(void){ |
| | | _containerView.alpha = 0.0; |
| | | _containerView.transform = CGAffineTransformMakeScale(0.1, 0.1); |
| | | } |
| | | completion:completionBlock]; |
| | | }]; |
| | | |
| | | break; |
| | | } |
| | | |
| | | case KLCPopupDismissTypeBounceOutToTop: { |
| | | [UIView animateWithDuration:bounce1Duration |
| | | delay:0 |
| | | options:UIViewAnimationOptionCurveEaseOut |
| | | animations:^(void){ |
| | | CGRect finalFrame = _containerView.frame; |
| | | finalFrame.origin.y += 40.0; |
| | | _containerView.frame = finalFrame; |
| | | } |
| | | completion:^(BOOL finished){ |
| | | |
| | | [UIView animateWithDuration:bounce2Duration |
| | | delay:0 |
| | | options:UIViewAnimationOptionCurveEaseIn |
| | | animations:^(void){ |
| | | CGRect finalFrame = _containerView.frame; |
| | | finalFrame.origin.y = -CGRectGetHeight(finalFrame); |
| | | _containerView.frame = finalFrame; |
| | | } |
| | | completion:completionBlock]; |
| | | }]; |
| | | |
| | | break; |
| | | } |
| | | |
| | | case KLCPopupDismissTypeBounceOutToBottom: { |
| | | [UIView animateWithDuration:bounce1Duration |
| | | delay:0 |
| | | options:UIViewAnimationOptionCurveEaseOut |
| | | animations:^(void){ |
| | | CGRect finalFrame = _containerView.frame; |
| | | finalFrame.origin.y -= 40.0; |
| | | _containerView.frame = finalFrame; |
| | | } |
| | | completion:^(BOOL finished){ |
| | | |
| | | [UIView animateWithDuration:bounce2Duration |
| | | delay:0 |
| | | options:UIViewAnimationOptionCurveEaseIn |
| | | animations:^(void){ |
| | | CGRect finalFrame = _containerView.frame; |
| | | finalFrame.origin.y = CGRectGetHeight(self.bounds); |
| | | _containerView.frame = finalFrame; |
| | | } |
| | | completion:completionBlock]; |
| | | }]; |
| | | |
| | | break; |
| | | } |
| | | |
| | | case KLCPopupDismissTypeBounceOutToLeft: { |
| | | [UIView animateWithDuration:bounce1Duration |
| | | delay:0 |
| | | options:UIViewAnimationOptionCurveEaseOut |
| | | animations:^(void){ |
| | | CGRect finalFrame = _containerView.frame; |
| | | finalFrame.origin.x += 40.0; |
| | | _containerView.frame = finalFrame; |
| | | } |
| | | completion:^(BOOL finished){ |
| | | |
| | | [UIView animateWithDuration:bounce2Duration |
| | | delay:0 |
| | | options:UIViewAnimationOptionCurveEaseIn |
| | | animations:^(void){ |
| | | CGRect finalFrame = _containerView.frame; |
| | | finalFrame.origin.x = -CGRectGetWidth(finalFrame); |
| | | _containerView.frame = finalFrame; |
| | | } |
| | | completion:completionBlock]; |
| | | }]; |
| | | break; |
| | | } |
| | | |
| | | case KLCPopupDismissTypeBounceOutToRight: { |
| | | [UIView animateWithDuration:bounce1Duration |
| | | delay:0 |
| | | options:UIViewAnimationOptionCurveEaseOut |
| | | animations:^(void){ |
| | | CGRect finalFrame = _containerView.frame; |
| | | finalFrame.origin.x -= 40.0; |
| | | _containerView.frame = finalFrame; |
| | | } |
| | | completion:^(BOOL finished){ |
| | | |
| | | [UIView animateWithDuration:bounce2Duration |
| | | delay:0 |
| | | options:UIViewAnimationOptionCurveEaseIn |
| | | animations:^(void){ |
| | | CGRect finalFrame = _containerView.frame; |
| | | finalFrame.origin.x = CGRectGetWidth(self.bounds); |
| | | _containerView.frame = finalFrame; |
| | | } |
| | | completion:completionBlock]; |
| | | }]; |
| | | break; |
| | | } |
| | | |
| | | default: { |
| | | self.containerView.alpha = 0.0; |
| | | completionBlock(YES); |
| | | break; |
| | | } |
| | | } |
| | | } else { |
| | | self.containerView.alpha = 0.0; |
| | | completionBlock(YES); |
| | | } |
| | | |
| | | }); |
| | | } |
| | | }); |
| | | } |
| | | } |
| | | |
| | | |
| | | #pragma mark - Private |
| | | |
| | | - (void)showWithParameters:(NSDictionary*)parameters { |
| | | |
| | | // If popup can be shown |
| | | if (!_isBeingShown && !_isShowing && !_isBeingDismissed) { |
| | | _isBeingShown = YES; |
| | | _isShowing = NO; |
| | | _isBeingDismissed = NO; |
| | | |
| | | [self willStartShowing]; |
| | | |
| | | dispatch_async( dispatch_get_main_queue(), ^{ |
| | | |
| | | // Prepare by adding to the top window. |
| | | if(!self.superview){ |
| | | NSEnumerator *frontToBackWindows = [[[UIApplication sharedApplication] windows] reverseObjectEnumerator]; |
| | | |
| | | for (UIWindow *window in frontToBackWindows) { |
| | | if (window.windowLevel == UIWindowLevelNormal) { |
| | | [window addSubview:self]; |
| | | |
| | | break; |
| | | } |
| | | } |
| | | } |
| | | |
| | | // Before we calculate layout for containerView, make sure we are transformed for current orientation. |
| | | [self updateForInterfaceOrientation]; |
| | | |
| | | // Make sure we're not hidden |
| | | self.hidden = NO; |
| | | self.alpha = 1.0; |
| | | |
| | | // Setup background view |
| | | _backgroundView.alpha = 0.0; |
| | | if (_maskType == KLCPopupMaskTypeDimmed) { |
| | | _backgroundView.backgroundColor = [UIColor colorWithRed:(0.0/255.0f) green:(0.0/255.0f) blue:(0.0/255.0f) alpha:self.dimmedMaskAlpha]; |
| | | } else { |
| | | _backgroundView.backgroundColor = [UIColor clearColor]; |
| | | } |
| | | |
| | | // Animate background if needed |
| | | void (^backgroundAnimationBlock)(void) = ^(void) { |
| | | _backgroundView.alpha = 1.0; |
| | | }; |
| | | |
| | | if (_showType != KLCPopupShowTypeNone) { |
| | | // Make fade happen faster than motion. Use linear for fades. |
| | | [UIView animateWithDuration:0.15 |
| | | delay:0 |
| | | options:UIViewAnimationOptionCurveLinear |
| | | animations:backgroundAnimationBlock |
| | | completion:NULL]; |
| | | } else { |
| | | backgroundAnimationBlock(); |
| | | } |
| | | |
| | | // Determine duration. Default to 0 if none provided. |
| | | NSTimeInterval duration; |
| | | NSNumber* durationNumber = [parameters valueForKey:@"duration"]; |
| | | if (durationNumber != nil) { |
| | | duration = [durationNumber doubleValue]; |
| | | } else { |
| | | duration = 0.0; |
| | | } |
| | | |
| | | // Setup completion block |
| | | void (^completionBlock)(BOOL) = ^(BOOL finished) { |
| | | _isBeingShown = NO; |
| | | _isShowing = YES; |
| | | // If popup can be shown |
| | | if (!_isBeingShown && !_isShowing && !_isBeingDismissed) { |
| | | _isBeingShown = YES; |
| | | _isShowing = NO; |
| | | _isBeingDismissed = NO; |
| | | |
| | | [self didFinishShowing]; |
| | | [self willStartShowing]; |
| | | |
| | | if (self.didFinishShowingCompletion != nil) { |
| | | self.didFinishShowingCompletion(); |
| | | } |
| | | |
| | | // Set to hide after duration if greater than zero. |
| | | if (duration > 0.0) { |
| | | [self performSelector:@selector(dismiss) withObject:nil afterDelay:duration]; |
| | | } |
| | | }; |
| | | |
| | | // Add contentView to container |
| | | if (self.contentView.superview != _containerView) { |
| | | [_containerView addSubview:self.contentView]; |
| | | } |
| | | |
| | | // Re-layout (this is needed if the contentView is using autoLayout) |
| | | [self.contentView layoutIfNeeded]; |
| | | |
| | | // Size container to match contentView |
| | | CGRect containerFrame = _containerView.frame; |
| | | containerFrame.size = self.contentView.frame.size; |
| | | _containerView.frame = containerFrame; |
| | | // Position contentView to fill it |
| | | CGRect contentViewFrame = self.contentView.frame; |
| | | contentViewFrame.origin = CGPointZero; |
| | | self.contentView.frame = contentViewFrame; |
| | | |
| | | // Reset _containerView's constraints in case contentView is uaing autolayout. |
| | | UIView* contentView = _contentView; |
| | | NSDictionary* views = NSDictionaryOfVariableBindings(contentView); |
| | | |
| | | [_containerView removeConstraints:_containerView.constraints]; |
| | | [_containerView addConstraints: |
| | | [NSLayoutConstraint constraintsWithVisualFormat:@"V:|[contentView]|" |
| | | options:0 |
| | | metrics:nil |
| | | views:views]]; |
| | | |
| | | [_containerView addConstraints: |
| | | [NSLayoutConstraint constraintsWithVisualFormat:@"H:|[contentView]|" |
| | | options:0 |
| | | metrics:nil |
| | | views:views]]; |
| | | |
| | | // Determine final position and necessary autoresizingMask for container. |
| | | CGRect finalContainerFrame = containerFrame; |
| | | UIViewAutoresizing containerAutoresizingMask = UIViewAutoresizingNone; |
| | | |
| | | // Use explicit center coordinates if provided. |
| | | NSValue* centerValue = [parameters valueForKey:@"center"]; |
| | | if (centerValue != nil) { |
| | | |
| | | CGPoint centerInView = [centerValue CGPointValue]; |
| | | CGPoint centerInSelf; |
| | | |
| | | // Convert coordinates from provided view to self. Otherwise use as-is. |
| | | UIView* fromView = [parameters valueForKey:@"view"]; |
| | | if (fromView != nil) { |
| | | centerInSelf = [self convertPoint:centerInView fromView:fromView]; |
| | | } else { |
| | | centerInSelf = centerInView; |
| | | } |
| | | |
| | | finalContainerFrame.origin.x = (centerInSelf.x - CGRectGetWidth(finalContainerFrame)/2.0); |
| | | finalContainerFrame.origin.y = (centerInSelf.y - CGRectGetHeight(finalContainerFrame)/2.0); |
| | | containerAutoresizingMask = UIViewAutoresizingFlexibleLeftMargin | UIViewAutoresizingFlexibleRightMargin | UIViewAutoresizingFlexibleBottomMargin | UIViewAutoresizingFlexibleTopMargin; |
| | | } |
| | | |
| | | // Otherwise use relative layout. Default to center if none provided. |
| | | else { |
| | | |
| | | NSValue* layoutValue = [parameters valueForKey:@"layout"]; |
| | | KLCPopupLayout layout; |
| | | if (layoutValue != nil) { |
| | | layout = [layoutValue KLCPopupLayoutValue]; |
| | | } else { |
| | | layout = KLCPopupLayoutCenter; |
| | | } |
| | | |
| | | switch (layout.horizontal) { |
| | | dispatch_async( dispatch_get_main_queue(), ^{ |
| | | |
| | | case KLCPopupHorizontalLayoutLeft: { |
| | | finalContainerFrame.origin.x = 0.0; |
| | | containerAutoresizingMask = containerAutoresizingMask | UIViewAutoresizingFlexibleRightMargin; |
| | | break; |
| | | } |
| | | // Prepare by adding to the top window. |
| | | if(!self.superview){ |
| | | NSEnumerator *frontToBackWindows = [[[UIApplication sharedApplication] windows] reverseObjectEnumerator]; |
| | | |
| | | for (UIWindow *window in frontToBackWindows) { |
| | | if (window.windowLevel == UIWindowLevelNormal) { |
| | | [window addSubview:self]; |
| | | |
| | | break; |
| | | } |
| | | } |
| | | } |
| | | |
| | | case KLCPopupHorizontalLayoutLeftOfCenter: { |
| | | finalContainerFrame.origin.x = floorf(CGRectGetWidth(self.bounds)/3.0 - CGRectGetWidth(containerFrame)/2.0); |
| | | containerAutoresizingMask = containerAutoresizingMask | UIViewAutoresizingFlexibleLeftMargin | UIViewAutoresizingFlexibleRightMargin; |
| | | break; |
| | | } |
| | | // Before we calculate layout for containerView, make sure we are transformed for current orientation. |
| | | [self updateForInterfaceOrientation]; |
| | | |
| | | case KLCPopupHorizontalLayoutCenter: { |
| | | finalContainerFrame.origin.x = floorf((CGRectGetWidth(self.bounds) - CGRectGetWidth(containerFrame))/2.0); |
| | | containerAutoresizingMask = containerAutoresizingMask | UIViewAutoresizingFlexibleLeftMargin | UIViewAutoresizingFlexibleRightMargin; |
| | | break; |
| | | } |
| | | // Make sure we're not hidden |
| | | self.hidden = NO; |
| | | self.alpha = 1.0; |
| | | |
| | | case KLCPopupHorizontalLayoutRightOfCenter: { |
| | | finalContainerFrame.origin.x = floorf(CGRectGetWidth(self.bounds)*2.0/3.0 - CGRectGetWidth(containerFrame)/2.0); |
| | | containerAutoresizingMask = containerAutoresizingMask | UIViewAutoresizingFlexibleLeftMargin | UIViewAutoresizingFlexibleRightMargin; |
| | | break; |
| | | } |
| | | // Setup background view |
| | | self.backgroundView.alpha = 0.0; |
| | | |
| | | case KLCPopupHorizontalLayoutRight: { |
| | | finalContainerFrame.origin.x = CGRectGetWidth(self.bounds) - CGRectGetWidth(containerFrame); |
| | | containerAutoresizingMask = containerAutoresizingMask | UIViewAutoresizingFlexibleLeftMargin; |
| | | break; |
| | | } |
| | | if (self.maskType == KLCPopupMaskTypeDimmed) { |
| | | |
| | | self.backgroundView.backgroundColor = [UIColor colorWithRed:(0.0/255.0f) green:(0.0/255.0f) blue:(0.0/255.0f) alpha:self.dimmedMaskAlpha]; |
| | | } else { |
| | | self.backgroundView.backgroundColor = [UIColor clearColor]; |
| | | } |
| | | |
| | | default: |
| | | break; |
| | | } |
| | | |
| | | // Vertical |
| | | switch (layout.vertical) { |
| | | // Animate background if needed |
| | | void (^backgroundAnimationBlock)(void) = ^(void) { |
| | | self.backgroundView.alpha = 1.0; |
| | | }; |
| | | |
| | | case KLCPopupVerticalLayoutTop: { |
| | | finalContainerFrame.origin.y = 0; |
| | | containerAutoresizingMask = containerAutoresizingMask | UIViewAutoresizingFlexibleBottomMargin; |
| | | break; |
| | | } |
| | | if (self.showType != KLCPopupShowTypeNone) { |
| | | // Make fade happen faster than motion. Use linear for fades. |
| | | [UIView animateWithDuration:0.15 |
| | | delay:0 |
| | | options:UIViewAnimationOptionCurveLinear |
| | | animations:backgroundAnimationBlock |
| | | completion:NULL]; |
| | | } else { |
| | | backgroundAnimationBlock(); |
| | | } |
| | | |
| | | case KLCPopupVerticalLayoutAboveCenter: { |
| | | finalContainerFrame.origin.y = floorf(CGRectGetHeight(self.bounds)/3.0 - CGRectGetHeight(containerFrame)/2.0); |
| | | containerAutoresizingMask = containerAutoresizingMask | UIViewAutoresizingFlexibleTopMargin | UIViewAutoresizingFlexibleBottomMargin; |
| | | break; |
| | | } |
| | | // Determine duration. Default to 0 if none provided. |
| | | NSTimeInterval duration; |
| | | NSNumber* durationNumber = [parameters valueForKey:@"duration"]; |
| | | if (durationNumber != nil) { |
| | | duration = [durationNumber doubleValue]; |
| | | } else { |
| | | duration = 0.0; |
| | | } |
| | | |
| | | case KLCPopupVerticalLayoutCenter: { |
| | | finalContainerFrame.origin.y = floorf((CGRectGetHeight(self.bounds) - CGRectGetHeight(containerFrame))/2.0); |
| | | containerAutoresizingMask = containerAutoresizingMask | UIViewAutoresizingFlexibleTopMargin | UIViewAutoresizingFlexibleBottomMargin; |
| | | break; |
| | | } |
| | | // Setup completion block |
| | | void (^completionBlock)(BOOL) = ^(BOOL finished) { |
| | | self->_isBeingShown = NO; |
| | | self->_isShowing = YES; |
| | | self->_isBeingDismissed = NO; |
| | | |
| | | [self didFinishShowing]; |
| | | |
| | | if (self.didFinishShowingCompletion != nil) { |
| | | self.didFinishShowingCompletion(); |
| | | } |
| | | |
| | | // Set to hide after duration if greater than zero. |
| | | if (duration > 0.0) { |
| | | [self performSelector:@selector(dismiss) withObject:nil afterDelay:duration]; |
| | | } |
| | | }; |
| | | |
| | | case KLCPopupVerticalLayoutBelowCenter: { |
| | | finalContainerFrame.origin.y = floorf(CGRectGetHeight(self.bounds)*2.0/3.0 - CGRectGetHeight(containerFrame)/2.0); |
| | | containerAutoresizingMask = containerAutoresizingMask | UIViewAutoresizingFlexibleTopMargin | UIViewAutoresizingFlexibleBottomMargin; |
| | | break; |
| | | } |
| | | // Add contentView to container |
| | | if (self.contentView.superview != self->_containerView) { |
| | | [self->_containerView addSubview:self.contentView]; |
| | | } |
| | | |
| | | case KLCPopupVerticalLayoutBottom: { |
| | | finalContainerFrame.origin.y = CGRectGetHeight(self.bounds) - CGRectGetHeight(containerFrame); |
| | | containerAutoresizingMask = containerAutoresizingMask | UIViewAutoresizingFlexibleTopMargin; |
| | | break; |
| | | } |
| | | // Re-layout (this is needed if the contentView is using autoLayout) |
| | | [self.contentView layoutIfNeeded]; |
| | | |
| | | default: |
| | | break; |
| | | } |
| | | } |
| | | |
| | | _containerView.autoresizingMask = containerAutoresizingMask; |
| | | |
| | | // Animate content if needed |
| | | switch (_showType) { |
| | | case KLCPopupShowTypeFadeIn: { |
| | | |
| | | _containerView.alpha = 0.0; |
| | | _containerView.transform = CGAffineTransformIdentity; |
| | | CGRect startFrame = finalContainerFrame; |
| | | _containerView.frame = startFrame; |
| | | |
| | | [UIView animateWithDuration:0.15 |
| | | delay:0 |
| | | options:UIViewAnimationOptionCurveLinear |
| | | animations:^{ |
| | | _containerView.alpha = 1.0; |
| | | } |
| | | completion:completionBlock]; |
| | | break; |
| | | } |
| | | |
| | | case KLCPopupShowTypeGrowIn: { |
| | | |
| | | _containerView.alpha = 0.0; |
| | | // set frame before transform here... |
| | | CGRect startFrame = finalContainerFrame; |
| | | _containerView.frame = startFrame; |
| | | _containerView.transform = CGAffineTransformMakeScale(0.85, 0.85); |
| | | |
| | | [UIView animateWithDuration:0.15 |
| | | delay:0 |
| | | options:kAnimationOptionCurveIOS7 // note: this curve ignores durations |
| | | animations:^{ |
| | | _containerView.alpha = 1.0; |
| | | // set transform before frame here... |
| | | _containerView.transform = CGAffineTransformIdentity; |
| | | _containerView.frame = finalContainerFrame; |
| | | } |
| | | completion:completionBlock]; |
| | | |
| | | break; |
| | | } |
| | | |
| | | case KLCPopupShowTypeShrinkIn: { |
| | | _containerView.alpha = 0.0; |
| | | // set frame before transform here... |
| | | CGRect startFrame = finalContainerFrame; |
| | | _containerView.frame = startFrame; |
| | | _containerView.transform = CGAffineTransformMakeScale(1.25, 1.25); |
| | | |
| | | [UIView animateWithDuration:0.15 |
| | | delay:0 |
| | | options:kAnimationOptionCurveIOS7 // note: this curve ignores durations |
| | | animations:^{ |
| | | _containerView.alpha = 1.0; |
| | | // set transform before frame here... |
| | | _containerView.transform = CGAffineTransformIdentity; |
| | | _containerView.frame = finalContainerFrame; |
| | | } |
| | | completion:completionBlock]; |
| | | break; |
| | | } |
| | | |
| | | case KLCPopupShowTypeSlideInFromTop: { |
| | | _containerView.alpha = 1.0; |
| | | _containerView.transform = CGAffineTransformIdentity; |
| | | CGRect startFrame = finalContainerFrame; |
| | | startFrame.origin.y = -CGRectGetHeight(finalContainerFrame); |
| | | _containerView.frame = startFrame; |
| | | |
| | | [UIView animateWithDuration:0.30 |
| | | delay:0 |
| | | options:kAnimationOptionCurveIOS7 // note: this curve ignores durations |
| | | animations:^{ |
| | | _containerView.frame = finalContainerFrame; |
| | | } |
| | | completion:completionBlock]; |
| | | break; |
| | | } |
| | | |
| | | case KLCPopupShowTypeSlideInFromBottom: { |
| | | _containerView.alpha = 1.0; |
| | | _containerView.transform = CGAffineTransformIdentity; |
| | | CGRect startFrame = finalContainerFrame; |
| | | startFrame.origin.y = CGRectGetHeight(self.bounds); |
| | | _containerView.frame = startFrame; |
| | | |
| | | [UIView animateWithDuration:0.30 |
| | | delay:0 |
| | | options:kAnimationOptionCurveIOS7 // note: this curve ignores durations |
| | | animations:^{ |
| | | _containerView.frame = finalContainerFrame; |
| | | } |
| | | completion:completionBlock]; |
| | | break; |
| | | } |
| | | |
| | | case KLCPopupShowTypeSlideInFromLeft: { |
| | | _containerView.alpha = 1.0; |
| | | _containerView.transform = CGAffineTransformIdentity; |
| | | CGRect startFrame = finalContainerFrame; |
| | | startFrame.origin.x = -CGRectGetWidth(finalContainerFrame); |
| | | _containerView.frame = startFrame; |
| | | |
| | | [UIView animateWithDuration:0.30 |
| | | delay:0 |
| | | options:kAnimationOptionCurveIOS7 // note: this curve ignores durations |
| | | animations:^{ |
| | | _containerView.frame = finalContainerFrame; |
| | | } |
| | | completion:completionBlock]; |
| | | break; |
| | | } |
| | | |
| | | case KLCPopupShowTypeSlideInFromRight: { |
| | | _containerView.alpha = 1.0; |
| | | _containerView.transform = CGAffineTransformIdentity; |
| | | CGRect startFrame = finalContainerFrame; |
| | | startFrame.origin.x = CGRectGetWidth(self.bounds); |
| | | _containerView.frame = startFrame; |
| | | |
| | | [UIView animateWithDuration:0.30 |
| | | delay:0 |
| | | options:kAnimationOptionCurveIOS7 // note: this curve ignores durations |
| | | animations:^{ |
| | | _containerView.frame = finalContainerFrame; |
| | | } |
| | | completion:completionBlock]; |
| | | |
| | | break; |
| | | } |
| | | |
| | | case KLCPopupShowTypeBounceIn: { |
| | | _containerView.alpha = 0.0; |
| | | // set frame before transform here... |
| | | CGRect startFrame = finalContainerFrame; |
| | | _containerView.frame = startFrame; |
| | | _containerView.transform = CGAffineTransformMakeScale(0.1, 0.1); |
| | | |
| | | [UIView animateWithDuration:0.6 |
| | | delay:0.0 |
| | | usingSpringWithDamping:0.8 |
| | | initialSpringVelocity:15.0 |
| | | options:0 |
| | | animations:^{ |
| | | _containerView.alpha = 1.0; |
| | | _containerView.transform = CGAffineTransformIdentity; |
| | | } |
| | | completion:completionBlock]; |
| | | |
| | | break; |
| | | } |
| | | |
| | | case KLCPopupShowTypeBounceInFromTop: { |
| | | _containerView.alpha = 1.0; |
| | | _containerView.transform = CGAffineTransformIdentity; |
| | | CGRect startFrame = finalContainerFrame; |
| | | startFrame.origin.y = -CGRectGetHeight(finalContainerFrame); |
| | | _containerView.frame = startFrame; |
| | | |
| | | [UIView animateWithDuration:0.6 |
| | | delay:0.0 |
| | | usingSpringWithDamping:0.8 |
| | | initialSpringVelocity:10.0 |
| | | options:0 |
| | | animations:^{ |
| | | _containerView.frame = finalContainerFrame; |
| | | } |
| | | completion:completionBlock]; |
| | | break; |
| | | } |
| | | |
| | | case KLCPopupShowTypeBounceInFromBottom: { |
| | | _containerView.alpha = 1.0; |
| | | _containerView.transform = CGAffineTransformIdentity; |
| | | CGRect startFrame = finalContainerFrame; |
| | | startFrame.origin.y = CGRectGetHeight(self.bounds); |
| | | _containerView.frame = startFrame; |
| | | |
| | | [UIView animateWithDuration:0.6 |
| | | delay:0.0 |
| | | usingSpringWithDamping:0.8 |
| | | initialSpringVelocity:10.0 |
| | | options:0 |
| | | animations:^{ |
| | | _containerView.frame = finalContainerFrame; |
| | | } |
| | | completion:completionBlock]; |
| | | break; |
| | | } |
| | | |
| | | case KLCPopupShowTypeBounceInFromLeft: { |
| | | _containerView.alpha = 1.0; |
| | | _containerView.transform = CGAffineTransformIdentity; |
| | | CGRect startFrame = finalContainerFrame; |
| | | startFrame.origin.x = -CGRectGetWidth(finalContainerFrame); |
| | | _containerView.frame = startFrame; |
| | | |
| | | [UIView animateWithDuration:0.6 |
| | | delay:0.0 |
| | | usingSpringWithDamping:0.8 |
| | | initialSpringVelocity:10.0 |
| | | options:0 |
| | | animations:^{ |
| | | _containerView.frame = finalContainerFrame; |
| | | } |
| | | completion:completionBlock]; |
| | | break; |
| | | } |
| | | |
| | | case KLCPopupShowTypeBounceInFromRight: { |
| | | _containerView.alpha = 1.0; |
| | | _containerView.transform = CGAffineTransformIdentity; |
| | | CGRect startFrame = finalContainerFrame; |
| | | startFrame.origin.x = CGRectGetWidth(self.bounds); |
| | | _containerView.frame = startFrame; |
| | | |
| | | [UIView animateWithDuration:0.6 |
| | | delay:0.0 |
| | | usingSpringWithDamping:0.8 |
| | | initialSpringVelocity:10.0 |
| | | options:0 |
| | | animations:^{ |
| | | _containerView.frame = finalContainerFrame; |
| | | } |
| | | completion:completionBlock]; |
| | | break; |
| | | } |
| | | |
| | | default: { |
| | | self.containerView.alpha = 1.0; |
| | | self.containerView.transform = CGAffineTransformIdentity; |
| | | self.containerView.frame = finalContainerFrame; |
| | | |
| | | completionBlock(YES); |
| | | |
| | | break; |
| | | } |
| | | } |
| | | |
| | | }); |
| | | } |
| | | // Size container to match contentView |
| | | CGRect containerFrame = self->_containerView.frame; |
| | | containerFrame.size = self.contentView.frame.size; |
| | | self->_containerView.frame = containerFrame; |
| | | // Position contentView to fill it |
| | | CGRect contentViewFrame = self.contentView.frame; |
| | | contentViewFrame.origin = CGPointZero; |
| | | self.contentView.frame = contentViewFrame; |
| | | |
| | | // Reset _containerView's constraints in case contentView is uaing autolayout. |
| | | UIView *contentView = self->_contentView; |
| | | NSDictionary* views = NSDictionaryOfVariableBindings(contentView); |
| | | |
| | | [self->_containerView removeConstraints:self->_containerView.constraints]; |
| | | [self->_containerView addConstraints: |
| | | [NSLayoutConstraint constraintsWithVisualFormat:@"V:|[contentView]|" |
| | | options:0 |
| | | metrics:nil |
| | | views:views]]; |
| | | |
| | | [self->_containerView addConstraints: |
| | | [NSLayoutConstraint constraintsWithVisualFormat:@"H:|[contentView]|" |
| | | options:0 |
| | | metrics:nil |
| | | views:views]]; |
| | | |
| | | // Determine final position and necessary autoresizingMask for container. |
| | | CGRect finalContainerFrame = containerFrame; |
| | | UIViewAutoresizing containerAutoresizingMask = UIViewAutoresizingNone; |
| | | |
| | | // Use explicit center coordinates if provided. |
| | | NSValue* centerValue = [parameters valueForKey:@"center"]; |
| | | if (centerValue != nil) { |
| | | |
| | | CGPoint centerInView = [centerValue CGPointValue]; |
| | | CGPoint centerInSelf; |
| | | |
| | | // Convert coordinates from provided view to self. Otherwise use as-is. |
| | | UIView* fromView = [parameters valueForKey:@"view"]; |
| | | if (fromView != nil) { |
| | | centerInSelf = [self convertPoint:centerInView fromView:fromView]; |
| | | } else { |
| | | centerInSelf = centerInView; |
| | | } |
| | | |
| | | finalContainerFrame.origin.x = (centerInSelf.x - CGRectGetWidth(finalContainerFrame)/2.0); |
| | | finalContainerFrame.origin.y = (centerInSelf.y - CGRectGetHeight(finalContainerFrame)/2.0); |
| | | containerAutoresizingMask = UIViewAutoresizingFlexibleLeftMargin | UIViewAutoresizingFlexibleRightMargin | UIViewAutoresizingFlexibleBottomMargin | UIViewAutoresizingFlexibleTopMargin; |
| | | } |
| | | |
| | | // Otherwise use relative layout. Default to center if none provided. |
| | | else { |
| | | |
| | | NSValue* layoutValue = [parameters valueForKey:@"layout"]; |
| | | KLCPopupLayout layout; |
| | | if (layoutValue != nil) { |
| | | layout = [layoutValue KLCPopupLayoutValue]; |
| | | } else { |
| | | layout = KLCPopupLayoutCenter; |
| | | } |
| | | |
| | | switch (layout.horizontal) { |
| | | |
| | | case KLCPopupHorizontalLayoutLeft: { |
| | | finalContainerFrame.origin.x = 0.0; |
| | | containerAutoresizingMask = containerAutoresizingMask | UIViewAutoresizingFlexibleRightMargin; |
| | | break; |
| | | } |
| | | |
| | | case KLCPopupHorizontalLayoutLeftOfCenter: { |
| | | finalContainerFrame.origin.x = floorf(CGRectGetWidth(self.bounds)/3.0 - CGRectGetWidth(containerFrame)/2.0); |
| | | containerAutoresizingMask = containerAutoresizingMask | UIViewAutoresizingFlexibleLeftMargin | UIViewAutoresizingFlexibleRightMargin; |
| | | break; |
| | | } |
| | | |
| | | case KLCPopupHorizontalLayoutCenter: { |
| | | finalContainerFrame.origin.x = floorf((CGRectGetWidth(self.bounds) - CGRectGetWidth(containerFrame))/2.0); |
| | | containerAutoresizingMask = containerAutoresizingMask | UIViewAutoresizingFlexibleLeftMargin | UIViewAutoresizingFlexibleRightMargin; |
| | | break; |
| | | } |
| | | |
| | | case KLCPopupHorizontalLayoutRightOfCenter: { |
| | | finalContainerFrame.origin.x = floorf(CGRectGetWidth(self.bounds)*2.0/3.0 - CGRectGetWidth(containerFrame)/2.0); |
| | | containerAutoresizingMask = containerAutoresizingMask | UIViewAutoresizingFlexibleLeftMargin | UIViewAutoresizingFlexibleRightMargin; |
| | | break; |
| | | } |
| | | |
| | | case KLCPopupHorizontalLayoutRight: { |
| | | finalContainerFrame.origin.x = CGRectGetWidth(self.bounds) - CGRectGetWidth(containerFrame); |
| | | containerAutoresizingMask = containerAutoresizingMask | UIViewAutoresizingFlexibleLeftMargin; |
| | | break; |
| | | } |
| | | |
| | | default: |
| | | break; |
| | | } |
| | | |
| | | // Vertical |
| | | switch (layout.vertical) { |
| | | |
| | | case KLCPopupVerticalLayoutTop: { |
| | | finalContainerFrame.origin.y = 0; |
| | | containerAutoresizingMask = containerAutoresizingMask | UIViewAutoresizingFlexibleBottomMargin; |
| | | break; |
| | | } |
| | | |
| | | case KLCPopupVerticalLayoutAboveCenter: { |
| | | finalContainerFrame.origin.y = floorf(CGRectGetHeight(self.bounds)/3.0 - CGRectGetHeight(containerFrame)/2.0); |
| | | containerAutoresizingMask = containerAutoresizingMask | UIViewAutoresizingFlexibleTopMargin | UIViewAutoresizingFlexibleBottomMargin; |
| | | break; |
| | | } |
| | | |
| | | case KLCPopupVerticalLayoutCenter: { |
| | | finalContainerFrame.origin.y = floorf((CGRectGetHeight(self.bounds) - CGRectGetHeight(containerFrame))/2.0); |
| | | containerAutoresizingMask = containerAutoresizingMask | UIViewAutoresizingFlexibleTopMargin | UIViewAutoresizingFlexibleBottomMargin; |
| | | break; |
| | | } |
| | | |
| | | case KLCPopupVerticalLayoutBelowCenter: { |
| | | finalContainerFrame.origin.y = floorf(CGRectGetHeight(self.bounds)*2.0/3.0 - CGRectGetHeight(containerFrame)/2.0); |
| | | containerAutoresizingMask = containerAutoresizingMask | UIViewAutoresizingFlexibleTopMargin | UIViewAutoresizingFlexibleBottomMargin; |
| | | break; |
| | | } |
| | | |
| | | case KLCPopupVerticalLayoutBottom: { |
| | | finalContainerFrame.origin.y = CGRectGetHeight(self.bounds) - CGRectGetHeight(containerFrame); |
| | | containerAutoresizingMask = containerAutoresizingMask | UIViewAutoresizingFlexibleTopMargin; |
| | | break; |
| | | } |
| | | |
| | | default: |
| | | break; |
| | | } |
| | | } |
| | | |
| | | self->_containerView.autoresizingMask = containerAutoresizingMask; |
| | | |
| | | // Animate content if needed |
| | | switch (self.showType) { |
| | | case KLCPopupShowTypeFadeIn: { |
| | | |
| | | self->_containerView.alpha = 0.0; |
| | | self->_containerView.transform = CGAffineTransformIdentity; |
| | | CGRect startFrame = finalContainerFrame; |
| | | self->_containerView.frame = startFrame; |
| | | |
| | | [UIView animateWithDuration:0.15 |
| | | delay:0 |
| | | options:UIViewAnimationOptionCurveLinear |
| | | animations:^{ |
| | | self->_containerView.alpha = 1.0; |
| | | } |
| | | completion:completionBlock]; |
| | | break; |
| | | } |
| | | |
| | | case KLCPopupShowTypeGrowIn: { |
| | | |
| | | self->_containerView.alpha = 0.0; |
| | | // set frame before transform here... |
| | | CGRect startFrame = finalContainerFrame; |
| | | self->_containerView.frame = startFrame; |
| | | self->_containerView.transform = CGAffineTransformMakeScale(0.85, 0.85); |
| | | |
| | | [UIView animateWithDuration:0.15 |
| | | delay:0 |
| | | options:kAnimationOptionCurveIOS7 // note: this curve ignores durations |
| | | animations:^{ |
| | | self->_containerView.alpha = 1.0; |
| | | // set transform before frame here... |
| | | self->_containerView.transform = CGAffineTransformIdentity; |
| | | self->_containerView.frame = finalContainerFrame; |
| | | } |
| | | completion:completionBlock]; |
| | | |
| | | break; |
| | | } |
| | | |
| | | case KLCPopupShowTypeShrinkIn: { |
| | | self->_containerView.alpha = 0.0; |
| | | // set frame before transform here... |
| | | CGRect startFrame = finalContainerFrame; |
| | | self->_containerView.frame = startFrame; |
| | | self->_containerView.transform = CGAffineTransformMakeScale(1.25, 1.25); |
| | | |
| | | [UIView animateWithDuration:0.15 |
| | | delay:0 |
| | | options:kAnimationOptionCurveIOS7 // note: this curve ignores durations |
| | | animations:^{ |
| | | self->_containerView.alpha = 1.0; |
| | | // set transform before frame here... |
| | | self->_containerView.transform = CGAffineTransformIdentity; |
| | | self->_containerView.frame = finalContainerFrame; |
| | | } |
| | | completion:completionBlock]; |
| | | break; |
| | | } |
| | | |
| | | case KLCPopupShowTypeSlideInFromTop: { |
| | | self->_containerView.alpha = 1.0; |
| | | self->_containerView.transform = CGAffineTransformIdentity; |
| | | CGRect startFrame = finalContainerFrame; |
| | | startFrame.origin.y = -CGRectGetHeight(finalContainerFrame); |
| | | self->_containerView.frame = startFrame; |
| | | |
| | | [UIView animateWithDuration:0.30 |
| | | delay:0 |
| | | options:kAnimationOptionCurveIOS7 // note: this curve ignores durations |
| | | animations:^{ |
| | | self->_containerView.frame = finalContainerFrame; |
| | | } |
| | | completion:completionBlock]; |
| | | break; |
| | | } |
| | | |
| | | case KLCPopupShowTypeSlideInFromBottom: { |
| | | self->_containerView.alpha = 1.0; |
| | | self->_containerView.transform = CGAffineTransformIdentity; |
| | | CGRect startFrame = finalContainerFrame; |
| | | startFrame.origin.y = CGRectGetHeight(self.bounds); |
| | | self->_containerView.frame = startFrame; |
| | | |
| | | [UIView animateWithDuration:0.30 |
| | | delay:0 |
| | | options:kAnimationOptionCurveIOS7 // note: this curve ignores durations |
| | | animations:^{ |
| | | self->_containerView.frame = finalContainerFrame; |
| | | } |
| | | completion:completionBlock]; |
| | | break; |
| | | } |
| | | |
| | | case KLCPopupShowTypeSlideInFromLeft: { |
| | | self->_containerView.alpha = 1.0; |
| | | self->_containerView.transform = CGAffineTransformIdentity; |
| | | CGRect startFrame = finalContainerFrame; |
| | | startFrame.origin.x = -CGRectGetWidth(finalContainerFrame); |
| | | self->_containerView.frame = startFrame; |
| | | |
| | | [UIView animateWithDuration:0.30 |
| | | delay:0 |
| | | options:kAnimationOptionCurveIOS7 // note: this curve ignores durations |
| | | animations:^{ |
| | | self->_containerView.frame = finalContainerFrame; |
| | | } |
| | | completion:completionBlock]; |
| | | break; |
| | | } |
| | | |
| | | case KLCPopupShowTypeSlideInFromRight: { |
| | | self->_containerView.alpha = 1.0; |
| | | self->_containerView.transform = CGAffineTransformIdentity; |
| | | CGRect startFrame = finalContainerFrame; |
| | | startFrame.origin.x = CGRectGetWidth(self.bounds); |
| | | self->_containerView.frame = startFrame; |
| | | |
| | | [UIView animateWithDuration:0.30 |
| | | delay:0 |
| | | options:kAnimationOptionCurveIOS7 // note: this curve ignores durations |
| | | animations:^{ |
| | | self->_containerView.frame = finalContainerFrame; |
| | | } |
| | | completion:completionBlock]; |
| | | |
| | | break; |
| | | } |
| | | |
| | | case KLCPopupShowTypeBounceIn: { |
| | | self->_containerView.alpha = 0.0; |
| | | // set frame before transform here... |
| | | CGRect startFrame = finalContainerFrame; |
| | | self->_containerView.frame = startFrame; |
| | | self->_containerView.transform = CGAffineTransformMakeScale(0.1, 0.1); |
| | | |
| | | [UIView animateWithDuration:0.6 |
| | | delay:0.0 |
| | | usingSpringWithDamping:0.8 |
| | | initialSpringVelocity:15.0 |
| | | options:0 |
| | | animations:^{ |
| | | self->_containerView.alpha = 1.0; |
| | | self->_containerView.transform = CGAffineTransformIdentity; |
| | | } |
| | | completion:completionBlock]; |
| | | |
| | | break; |
| | | } |
| | | |
| | | case KLCPopupShowTypeBounceInFromTop: { |
| | | self->_containerView.alpha = 1.0; |
| | | self->_containerView.transform = CGAffineTransformIdentity; |
| | | CGRect startFrame = finalContainerFrame; |
| | | startFrame.origin.y = -CGRectGetHeight(finalContainerFrame); |
| | | self->_containerView.frame = startFrame; |
| | | |
| | | [UIView animateWithDuration:0.6 |
| | | delay:0.0 |
| | | usingSpringWithDamping:0.8 |
| | | initialSpringVelocity:10.0 |
| | | options:0 |
| | | animations:^{ |
| | | self->_containerView.frame = finalContainerFrame; |
| | | } |
| | | completion:completionBlock]; |
| | | break; |
| | | } |
| | | |
| | | case KLCPopupShowTypeBounceInFromBottom: { |
| | | self->_containerView.alpha = 1.0; |
| | | self->_containerView.transform = CGAffineTransformIdentity; |
| | | CGRect startFrame = finalContainerFrame; |
| | | startFrame.origin.y = CGRectGetHeight(self.bounds); |
| | | self->_containerView.frame = startFrame; |
| | | |
| | | [UIView animateWithDuration:0.6 |
| | | delay:0.0 |
| | | usingSpringWithDamping:0.8 |
| | | initialSpringVelocity:10.0 |
| | | options:0 |
| | | animations:^{ |
| | | self->_containerView.frame = finalContainerFrame; |
| | | } |
| | | completion:completionBlock]; |
| | | break; |
| | | } |
| | | |
| | | case KLCPopupShowTypeBounceInFromLeft: { |
| | | self->_containerView.alpha = 1.0; |
| | | self->_containerView.transform = CGAffineTransformIdentity; |
| | | CGRect startFrame = finalContainerFrame; |
| | | startFrame.origin.x = -CGRectGetWidth(finalContainerFrame); |
| | | self->_containerView.frame = startFrame; |
| | | |
| | | [UIView animateWithDuration:0.6 |
| | | delay:0.0 |
| | | usingSpringWithDamping:0.8 |
| | | initialSpringVelocity:10.0 |
| | | options:0 |
| | | animations:^{ |
| | | self->_containerView.frame = finalContainerFrame; |
| | | } |
| | | completion:completionBlock]; |
| | | break; |
| | | } |
| | | |
| | | case KLCPopupShowTypeBounceInFromRight: { |
| | | self->_containerView.alpha = 1.0; |
| | | self->_containerView.transform = CGAffineTransformIdentity; |
| | | CGRect startFrame = finalContainerFrame; |
| | | startFrame.origin.x = CGRectGetWidth(self.bounds); |
| | | self->_containerView.frame = startFrame; |
| | | |
| | | [UIView animateWithDuration:0.6 |
| | | delay:0.0 |
| | | usingSpringWithDamping:0.8 |
| | | initialSpringVelocity:10.0 |
| | | options:0 |
| | | animations:^{ |
| | | self->_containerView.frame = finalContainerFrame; |
| | | } |
| | | completion:completionBlock]; |
| | | break; |
| | | } |
| | | |
| | | default: { |
| | | self.containerView.alpha = 1.0; |
| | | self.containerView.transform = CGAffineTransformIdentity; |
| | | self.containerView.frame = finalContainerFrame; |
| | | |
| | | completionBlock(YES); |
| | | |
| | | break; |
| | | } |
| | | } |
| | | |
| | | }); |
| | | } |
| | | } |
| | | |
| | | |
| | | - (void)dismiss { |
| | | [self dismiss:YES]; |
| | | |
| | | [self dismiss:YES]; |
| | | } |
| | | |
| | | |
| | | - (void)updateForInterfaceOrientation { |
| | | |
| | | // We must manually fix orientation prior to iOS 8 |
| | | if (([[[UIDevice currentDevice] systemVersion] compare:@"8.0" options:NSNumericSearch] == NSOrderedAscending)) { |
| | | |
| | | UIInterfaceOrientation orientation = [[UIApplication sharedApplication] statusBarOrientation]; |
| | | CGFloat angle; |
| | | |
| | | switch (orientation) { |
| | | case UIInterfaceOrientationPortraitUpsideDown: |
| | | angle = M_PI; |
| | | break; |
| | | case UIInterfaceOrientationLandscapeLeft: |
| | | angle = -M_PI/2.0f;; |
| | | // We must manually fix orientation prior to iOS 8 |
| | | if (([[[UIDevice currentDevice] systemVersion] compare:@"8.0" options:NSNumericSearch] == NSOrderedAscending)) { |
| | | |
| | | break; |
| | | case UIInterfaceOrientationLandscapeRight: |
| | | angle = M_PI/2.0f; |
| | | UIInterfaceOrientation orientation = [[UIApplication sharedApplication] statusBarOrientation]; |
| | | CGFloat angle; |
| | | |
| | | break; |
| | | default: // as UIInterfaceOrientationPortrait |
| | | angle = 0.0; |
| | | break; |
| | | switch (orientation) { |
| | | case UIInterfaceOrientationPortraitUpsideDown: |
| | | angle = M_PI; |
| | | break; |
| | | case UIInterfaceOrientationLandscapeLeft: |
| | | angle = -M_PI/2.0f;; |
| | | |
| | | break; |
| | | case UIInterfaceOrientationLandscapeRight: |
| | | angle = M_PI/2.0f; |
| | | |
| | | break; |
| | | default: // as UIInterfaceOrientationPortrait |
| | | angle = 0.0; |
| | | break; |
| | | } |
| | | |
| | | self.transform = CGAffineTransformMakeRotation(angle); |
| | | } |
| | | |
| | | self.transform = CGAffineTransformMakeRotation(angle); |
| | | } |
| | | |
| | | self.frame = self.window.bounds; |
| | | self.frame = self.window.bounds; |
| | | } |
| | | |
| | | |
| | | #pragma mark - Notification handlers |
| | | |
| | | - (void)didChangeStatusBarOrientation:(NSNotification*)notification { |
| | | [self updateForInterfaceOrientation]; |
| | | [self updateForInterfaceOrientation]; |
| | | } |
| | | |
| | | |
| | | #pragma mark - Subclassing |
| | | |
| | | - (void)willStartShowing { |
| | | |
| | | |
| | | } |
| | | |
| | | |
| | | - (void)didFinishShowing { |
| | | |
| | | |
| | | } |
| | | |
| | | |
| | | - (void)willStartDismissing { |
| | | |
| | | |
| | | } |
| | | |
| | | |
| | | - (void)didFinishDismissing { |
| | | |
| | | |
| | | } |
| | | |
| | | @end |
| | |
| | | |
| | | |
| | | - (void)forEachPopupDoBlock:(void (^)(KLCPopup* popup))block { |
| | | for (UIView *subview in self.subviews) |
| | | { |
| | | if ([subview isKindOfClass:[KLCPopup class]]) |
| | | for (UIView *subview in self.subviews) |
| | | { |
| | | block((KLCPopup *)subview); |
| | | } else { |
| | | [subview forEachPopupDoBlock:block]; |
| | | if ([subview isKindOfClass:[KLCPopup class]]) |
| | | { |
| | | block((KLCPopup *)subview); |
| | | } else { |
| | | [subview forEachPopupDoBlock:block]; |
| | | } |
| | | } |
| | | } |
| | | } |
| | | |
| | | |
| | | - (void)dismissPresentingPopup { |
| | | |
| | | // Iterate over superviews until you find a KLCPopup and dismiss it, then gtfo |
| | | UIView* view = self; |
| | | while (view != nil) { |
| | | if ([view isKindOfClass:[KLCPopup class]]) { |
| | | [(KLCPopup*)view dismiss:YES]; |
| | | break; |
| | | |
| | | // Iterate over superviews until you find a KLCPopup and dismiss it, then gtfo |
| | | UIView* view = self; |
| | | while (view != nil) { |
| | | if ([view isKindOfClass:[KLCPopup class]]) { |
| | | [(KLCPopup*)view dismiss:YES]; |
| | | break; |
| | | } |
| | | view = [view superview]; |
| | | } |
| | | view = [view superview]; |
| | | } |
| | | } |
| | | |
| | | @end |
| | |
| | | |
| | | + (NSValue *)valueWithKLCPopupLayout:(KLCPopupLayout)layout |
| | | { |
| | | return [NSValue valueWithBytes:&layout objCType:@encode(KLCPopupLayout)]; |
| | | return [NSValue valueWithBytes:&layout objCType:@encode(KLCPopupLayout)]; |
| | | } |
| | | |
| | | - (KLCPopupLayout)KLCPopupLayoutValue |
| | | { |
| | | KLCPopupLayout layout; |
| | | |
| | | [self getValue:&layout]; |
| | | |
| | | return layout; |
| | | KLCPopupLayout layout; |
| | | |
| | | [self getValue:&layout]; |
| | | |
| | | return layout; |
| | | } |
| | | |
| | | @end |