我在Storyboard中有两个View控制器,我想使用自定义的向下分段(与常规的封面垂直相反)从第一个开始呈现第二个控制器。
我已经用我希望能工作的代码对故事板segue进行了子类化。
但是,在本例中,我没有将Storyboard中的段从一个视图控制器拖动到另一个视图控制器。相反,我在代码中处理Modal表示。
如果在代码中调用第二个视图控制器,是否可以调用自定义segue?或者你必须在你分配自定义类的故事板中有一个实际的段?
如果可能的话,你会把代码放在哪里?
下面是我用来呈现模式视图控制器的代码
UIStoryboard *storyboard = [UIStoryboard storyboardWithName:@"chat" bundle:nil];
UIViewController *myVC = [storyboard instantiateViewControllerWithIdentifier:@"chatVC"];
[(UINavigationController*)self.window.rootViewController presentViewController:myVC animated:NO completion:nil];
发布于 2018-09-19 08:43:49
看起来你正试图在你的应用程序中完成许多自定义动画过渡,所以我建议你使用你自己的动画制作类,而不是尝试创建自定义segues。类似于我之前发布给你的例子(链接在我上面的评论中),你需要设置某种类型的委托(在上一个例子中是一个UINavigationControllerDelegate)来决定使用哪些自定义动画制作类来呈现/取消(在上一个例子中是为了推送/弹出)某些视图控制器:
下面是我的意思的一个例子:
ViewController.m (将其用作UIViewControllerTransitioningDelegate):
#import "ViewController.h"
#import "SlideDownAnimator.h"
#import "SlideUpAnimator.h"
@interface ViewController () <UIViewControllerTransitioningDelegate>
@end
@implementation ViewController
- (void)viewDidLoad {
[super viewDidLoad];
// Do any additional setup after loading the view, typically from a nib.
}
- (IBAction)_presentCustomDownward:(id)sender {
// setup a fake view controller we're going to present
UIViewController *fakeSecondViewController = [[UIViewController alloc] init];
fakeSecondViewController.view.backgroundColor = [UIColor blueColor];
// make sure to set the desination view controller's transition delegate
// this doesn't have to be set to self here, you can set it anything that will implement: UIViewControllerTransitioningDelegate
fakeSecondViewController.transitioningDelegate = self;
// when we call present on the view controller it asks the transitioningDelegate for an animation coordinator which we're going to provide below
[self.navigationController presentViewController:fakeSecondViewController animated:YES completion:^{
// dismis after a couple seconds to show what the custom dismiss looks like (obviously this is just for the example code, you will handle your own dismissal)
dispatch_after(dispatch_time(DISPATCH_TIME_NOW, (int64_t)(2.0f * NSEC_PER_SEC)), dispatch_get_main_queue(), ^{
[self.navigationController dismissViewControllerAnimated:YES completion:nil];
});
}];
}
// delegate call for presentation
- (id<UIViewControllerAnimatedTransitioning>)animationControllerForPresentedController:(UIViewController *)presented
presentingController:(UIViewController *)presenting
sourceController:(UIViewController *)source {
// return our own custom Animator class (which adheres to UIViewControllerAnimatedTransitioning protocol)
return [[SlideDownAnimator alloc] init];
}
// delegate call for dismissal
- (id<UIViewControllerAnimatedTransitioning>)animationControllerForDismissedController:(UIViewController *)dismissed {
// return our own custom Animator class (which adheres to UIViewControllerAnimatedTransitioning protocol)
return [[SlideUpAnimator alloc] init];
}
SlideDownAnimator.h (自定义向下动画):
#import <Foundation/Foundation.h>
#import <UIKit/UIKit.h>
NS_ASSUME_NONNULL_BEGIN
@interface SlideDownAnimator : NSObject <UIViewControllerAnimatedTransitioning>
@end
NS_ASSUME_NONNULL_END
SlideDownAnimator.m:
#import "SlideDownAnimator.h"
@implementation SlideDownAnimator
- (NSTimeInterval)transitionDuration:(nullable id<UIViewControllerContextTransitioning>)transitionContext {
return 0.4f;
}
- (void)animateTransition:(nonnull id<UIViewControllerContextTransitioning>)transitionContext {
// grab the toViewController (the vc being presented)
UIViewController *toViewController = [transitionContext viewControllerForKey:UITransitionContextToViewControllerKey];
// manually add it to our container view
[[transitionContext containerView] addSubview:toViewController.view];
// get the frame so we can do some of our own animations on it
CGRect toVCFrame = toViewController.view.frame;
CGFloat toVCHeight = toVCFrame.size.height;
// offset the y coordiante by it's height so that it's completely above our current screen
toVCFrame.origin.y = -toVCHeight;
// set the initial frame so it's above our screen
[toViewController.view setFrame:toVCFrame];
[UIView animateWithDuration:[self transitionDuration:transitionContext] animations:^{
// animate the y position to 0 so it slides down
CGRect finalVCFrame = toViewController.view.frame;
finalVCFrame.origin.y = 0;
[toViewController.view setFrame:finalVCFrame];
} completion:^(BOOL finished) {
// make sure to call this so we'll call back to our presentViewdController's completion block
[transitionContext completeTransition:![transitionContext transitionWasCancelled]];
}];
}
@end
我的猜测是,你也会想要一个自定义的上滑动画,所以你需要多一个实现自定义过渡的动画师:
SlideUpAnimator.h:
#import <Foundation/Foundation.h>
#import <UIKit/UIKit.h>
NS_ASSUME_NONNULL_BEGIN
@interface SlideUpAnimator : NSObject <UIViewControllerAnimatedTransitioning>
@end
NS_ASSUME_NONNULL_END
SlideUpAnimator.m:
#import "SlideUpAnimator.h"
@implementation SlideUpAnimator
- (NSTimeInterval)transitionDuration:(nullable id<UIViewControllerContextTransitioning>)transitionContext {
return 0.4f;
}
- (void)animateTransition:(nonnull id<UIViewControllerContextTransitioning>)transitionContext {
// grab our fromViewController (the vc being dismissed)
UIViewController *fromViewController = [transitionContext viewControllerForKey:UITransitionContextFromViewControllerKey];
// and our toViewController (the vc that will be shown after dismissal)
UIViewController *toViewController = [transitionContext viewControllerForKey:UITransitionContextToViewControllerKey];
// add our toViewController as a subview of our container view (make sure to add it beneath the dismissing view controller so we can let it complete it's animation first)
[[transitionContext containerView] insertSubview:toViewController.view belowSubview:fromViewController.view];
[UIView animateWithDuration:[self transitionDuration:transitionContext] animations:^{
// push the view back up above the screen
CGRect fromVCFrame = fromViewController.view.frame;
fromVCFrame.origin.y = -fromVCFrame.size.height;
[fromViewController.view setFrame:fromVCFrame];
} completion:^(BOOL finished) {
// make sure to call this so we'll call back to our presentViewdController's completion block
[transitionContext completeTransition:![transitionContext transitionWasCancelled]];
}];
}
@end
完整的动画最终将如下所示:
Custom_Downward_Animation_Transition
这里有一些对你有帮助的链接:
https://developer.apple.com/documentation/uikit/uiviewcontrollertransitioningdelegate?language=objc
https://developer.apple.com/documentation/uikit/uiviewcontrolleranimatedtransitioning?language=objc
编辑:
至于在自己的代码中放在哪里的其他问题:这高度依赖于您的应用程序结构,所以如果没有看到您试图使用它们的类的更多上下文,很难说最好的方法。
https://stackoverflow.com/questions/52394928
复制相似问题