我使用- (void)animateTransition:(id<UIViewControllerContextTransitioning>)context {
self.ctxContainerView = [context containerView];
UIView *toView = [context viewControllerForKey:UITransitionContextToViewControllerKey].view;
UIView *fromView = [context viewControllerForKey:UITransitionContextFromViewControllerKey].view;
// Create image from view
UIView *viewToImage = (self.isPresenting)? fromView : toView;
UIGraphicsBeginImageContextWithOptions(viewToImage.bounds.size, viewToImage.opaque, 0);
[viewToImage.layer renderInContext:UIGraphicsGetCurrentContext()];
UIImage * img = UIGraphicsGetImageFromCurrentImageContext();
UIGraphicsEndImageContext();
// Create left and right haves of the view image
CGImageRef tmp = CGImageCreateWithImageInRect([img CGImage], CGRectMake(0, 0, img.size.width * img.scale*0.5, img.size.height * img.scale));
UIImage *imgLeft = [UIImage imageWithCGImage:tmp];
CGImageRef tmp2 = CGImageCreateWithImageInRect([img CGImage], CGRectMake(img.size.width * img.scale*0.5, 0, img.size.width * img.scale*0.5, img.size.height * img.scale));
UIImage *imgRight = [UIImage imageWithCGImage:tmp2];
CGImageRelease(tmp);
CGImageRelease(tmp2);
self.snapshotViewLeft = [[UIImageView alloc] initWithImage:imgLeft];
self.snapshotViewRight = [[UIImageView alloc] initWithImage:imgRight];
NSLog(@"Before constraints %@", NSStringFromCGSize(self.snapshotViewLeft.frame.size)); //prints {375, 1334} all the time
if (self.isPresenting) {
[self.ctxContainerView insertSubview:toView belowSubview:fromView];
[self.ctxContainerView addSubview:self.snapshotViewLeft];
[self.ctxContainerView addConstraints: [self setupConstraintsForLeftView:self.snapshotViewLeft]];
[self.ctxContainerView addSubview:self.snapshotViewRight];
[self.ctxContainerView addConstraints: [self setupConstraintsForRightView:self.snapshotViewRight]];
[self.ctxContainerView layoutIfNeeded];
NSLog(@"After constraints %@", NSStringFromCGSize(self.snapshotViewLeft.frame.size)); // prints {187.5, 667} the first time (which is the correct size), but {375, 1334} the second time the controller is presented
// Remove the source view, and animate out the two image views
[fromView removeFromSuperview];
self.leftCon.constant = -self.ctxContainerView.frame.size.width/2;
self.rightCon.constant = self.ctxContainerView.frame.size.width/2;
[UIView animateWithDuration:ANIMATION_TIME animations:^{
[self.ctxContainerView layoutIfNeeded];
} completion:^(BOOL finished) {
[self.snapshotViewRight removeFromSuperview];
[self.snapshotViewLeft removeFromSuperview];
[context completeTransition:YES];
}];
}else{
[self.ctxContainerView addSubview:self.snapshotViewLeft];
[self.ctxContainerView addConstraints: [self setupConstraintsForLeftView:self.snapshotViewLeft]];
self.leftCon.constant = -self.ctxContainerView.frame.size.width/2;
[self.ctxContainerView addSubview:self.snapshotViewRight];
[self.ctxContainerView addConstraints: [self setupConstraintsForRightView:self.snapshotViewRight]];
self.rightCon.constant = self.ctxContainerView.frame.size.width/2;
[self.ctxContainerView layoutIfNeeded];
// Animate in the two image views
self.leftCon.constant = 0;
self.rightCon.constant = 0;
[UIView animateWithDuration:ANIMATION_TIME animations:^{
[self.ctxContainerView layoutIfNeeded];
} completion:^(BOOL finished) {
[self.snapshotViewRight removeFromSuperview];
[self.snapshotViewLeft removeFromSuperview];
[fromView removeFromSuperview];
[context completeTransition:YES];
}];
}
}
-(NSArray *)setupConstraintsForLeftView:(UIView *) inView {
inView.translatesAutoresizingMaskIntoConstraints = NO;
self.leftCon = [NSLayoutConstraint constraintWithItem:inView attribute:NSLayoutAttributeLeft relatedBy:0 toItem:self.ctxContainerView attribute:NSLayoutAttributeLeft multiplier:1 constant:0];
NSLayoutConstraint *con1 = [NSLayoutConstraint constraintWithItem:inView attribute:NSLayoutAttributeBottom relatedBy:0 toItem:self.ctxContainerView attribute:NSLayoutAttributeBottom multiplier:1 constant:0];
NSLayoutConstraint *con2 = [NSLayoutConstraint constraintWithItem:inView attribute:NSLayoutAttributeTop relatedBy:0 toItem:self.ctxContainerView attribute:NSLayoutAttributeTop multiplier:1 constant:0];
NSLayoutConstraint *con3 = [NSLayoutConstraint constraintWithItem:inView attribute:NSLayoutAttributeWidth relatedBy:0 toItem:self.ctxContainerView attribute:NSLayoutAttributeWidth multiplier:0.5 constant:0];
NSArray *arr = @[self.leftCon,con1,con2,con3];
return arr;
}
-(NSArray *)setupConstraintsForRightView:(UIView *) inView {
inView.translatesAutoresizingMaskIntoConstraints = NO;
self.rightCon = [NSLayoutConstraint constraintWithItem:inView attribute:NSLayoutAttributeRight relatedBy:0 toItem:self.ctxContainerView attribute:NSLayoutAttributeRight multiplier:1 constant:0];
NSLayoutConstraint *con1 = [NSLayoutConstraint constraintWithItem:inView attribute:NSLayoutAttributeBottom relatedBy:0 toItem:self.ctxContainerView attribute:NSLayoutAttributeBottom multiplier:1 constant:0];
NSLayoutConstraint *con2 = [NSLayoutConstraint constraintWithItem:inView attribute:NSLayoutAttributeTop relatedBy:0 toItem:self.ctxContainerView attribute:NSLayoutAttributeTop multiplier:1 constant:0];
NSLayoutConstraint *con3 = [NSLayoutConstraint constraintWithItem:inView attribute:NSLayoutAttributeWidth relatedBy:0 toItem:self.ctxContainerView attribute:NSLayoutAttributeWidth multiplier:0.5 constant:0];
NSArray *arr = @[self.rightCon,con1,con2,con3];
return arr;
}
协议进行自定义演示,该协议将初始控制器的视图分成两半(实际上是该视图的图像),并将屏幕上的两个多余部分向左和向右滑动。动画在第一次执行时适用于演示和解雇,但在任何后续演示中都是错误的。
具体来说,保持视图半像的图像视图不会受到给定的约束,因此它们的大小应该是它们的两倍(它们的大小取决于视网膜图像的大小) )。这仅发生在具有视网膜显示器的模拟器上。
动画师对象在每次演示和解雇后都会被解除分配,所以它根本不清楚为什么它在后续运行中应该有不同的行为。
以下是代码,包括在应用约束之前和之后显示其中一个图像视图大小的日志,
$auth = new stdClass();
$auth->loginId = 'test';
$auth->password = '12345';
$client = new SoapClient("example.wsdl", array('trace' => 1));
$header = new SoapHeader('http://example.com','Authentication',$auth,false);
$client->__setSoapHeaders($header);
问题是,为什么第一次运行后的运行行为会有所不同,即使系统应该在第一次展示和解雇后回到相同的启动状态?