transitionWithView和animateWithDuration的问题

时间:2012-12-14 20:13:26

标签: iphone ios xcode ipad uianimation

我遇到transitionWithViewanimateWithDuration的问题。我的一个animateWithDuration块没有转换,它是一个突然改变,而transitionWithView不会暂时禁用用户交互。我检查了文档,并相信我正在做的一切正确,但显然有些不对劲。以下是两段代码:

这是在我的主视图控制器ViewController中,它有三个容器视图/子视图控制器。此块移动其中一个容器视图,但在转换发生时不会阻止用户进入ViewController中的其他交互。

[UIView transitionWithView:self.view duration:0.5 options:UIViewAnimationOptionCurveEaseOut animations:^ {
        CGRect frame = _containerView.frame;
        frame.origin.y = self.view.frame.size.height - _containerView.frame.size.height;
        _containerView.frame = frame;
}completion:^(BOOL finished) {
     // do something   
}];

这是我的一个容器视图控制器。动画似乎无效,因为productTitleLabelproductDescriptionTextView的文本突然发生变化,就好像动画块不存在一样。

- (void)tableView:(UITableView *)tableView didSelectRowAtIndexPath:(NSIndexPath *)indexPath
{    
    [self.viewController toggleFlavoredOliveOilsTableView];

    if (indexPath.row > 0) {
        NSDictionary *selectedCellDict = [[_flavoredOliveOilsDict objectForKey:@"Unflavored Olive Oils"] objectAtIndex:indexPath.row - 1];

        [UIView animateWithDuration:0.5 delay:0 options:UIViewAnimationOptionTransitionCrossDissolve animations:^ {
            self.viewController.productTitleLabel.text = [_flavoredOliveOilsTableView cellForRowAtIndexPath:indexPath].textLabel.text;
            self.viewController.productDescriptionTextView.text = [selectedCellDict objectForKey:@"Description"];
        }completion:nil];

        if (indexPath.row == 1) {
            [self.viewController setProductDescriptionTextViewFrameForInformationTab];
        }
        else {
            [self.viewController setProductDescriptionTextViewFrameForNonInformationTab];

            //self.viewController.productImageView.image = [UIImage imageNamed:[selectedCellDict objectForKey:@"Image"]];
        }
    }
}

我认为问题有些相关,因为我的大多数动画和转换块都没有按预期完全运行。谢谢你的帮助。

修改

我想要完成的是在ViewController中移动容器视图并设置标签,文本视图和图像视图的文本和图像属性;所有这些都在主视图中。这些属性的详细信息通过子视图控制器发送。 transitionWithView位于名为toggleFlavoredOiveOilsTableView的方法中,在didSelectRowAtIndexPath中调用。我认为问题在于我试图同时调用两个不同的动画/转换块。

1 个答案:

答案 0 :(得分:13)

如果在另一个正在进行动画的视图的子视图上完成一个动画,则可以体验这两种动画相互干扰的行为。因此,如果您执行transitionWithView:self.view(即在主视图上),就像您的代码段所示,您可能会遇到问题。如果您在不同的子视图上执行两个动画,问题可能会消失。在我下面的原始答案中,我:

  • 在包含两个transitionWithView控件的子视图上执行UILabel;

  • 将我的视图控制器包含子视图放在主视图的子视图中,然后transitionFromViewController被约束到该子视图。

当我将两个动画部分放在不同的子视图上时,动画可以同时发生而不会发生意外。


如果要为两个文本标签的内容更改设置动画,您可以:

[UIView transitionWithView:self.viewController.textLabelsContainerView
                  duration:0.5
                   options:UIViewAnimationOptionTransitionCrossDissolve
                animations:^{
                    self.viewController.productTitleLabel.text = [_flavoredOliveOilsTableView cellForRowAtIndexPath:indexPath].textLabel.text;
                    self.viewController.productDescriptionTextView.text = [selectedCellDict objectForKey:@"Description"];
                }
                completion:nil];

通常我会使用animateWithDuration,但text属性不是可动画的属性,因此我使用transitionWithView的原因,确保我有一个容器用于这些文本字段。但我尝试使用animateWithDuration动画其他控件,同时动画更改子控件,它工作正常。

为了转换子视图控制器,我使用transitionFromViewController设置容器子控制器视图的交换动画(它是Managing Child View Controllers in a Custom Container方法系列的一部分)。为了便于该过程,我在主视图控制器的视图中放置了一个容器视图,并将子控制器的视图添加为该容器的子视图。这样,当我为子项的转换设置动画时,动画很好地约束到容器视图。

因此,这里有一些示例代码将视图控制器添加到我的容器视图中,然后使用分段按钮在两个子视图控制器之间转换的代码:

- (void)addFirstChild
{
    UIViewController *child = [self.storyboard instantiateViewControllerWithIdentifier:@"Stooge"];
    [self addChildViewController:child];

    child.view.frame = self.bottomContainerView.bounds;
    [self.bottomContainerView addSubview:child.view];

    [child didMoveToParentViewController:self];
}

- (void)changedChild
{
    UIViewController *oldController = [self.childViewControllers lastObject];
    UIViewController *newController;

    if (self.segmentedControl.selectedSegmentIndex == 0)
        newController = [self.storyboard instantiateViewControllerWithIdentifier:@"Stooge"];
    else
        newController = [self.storyboard instantiateViewControllerWithIdentifier:@"Marx"];

    [oldController willMoveToParentViewController:nil];
    [self addChildViewController:newController];

    // start off screen below

    CGRect startFrame = self.bottomContainerView.bounds;
    startFrame.origin.y += startFrame.size.height;

    // end up where it's supposed to be, right in the container

    newController.view.frame = startFrame;

    [self transitionFromViewController:oldController
                      toViewController:newController
                              duration:0.5
                               options:0
                            animations:^{
                                newController.view.frame = self.bottomContainerView.bounds;
                            }
                            completion:^(BOOL finished) {
                                [oldController removeFromParentViewController];
                                [newController didMoveToParentViewController:self];
                            }];

}

最重要的是,我没有问题动画容器子控制器和父控制器中的字段。也许我不理解你所描述的问题。或者也许我们的动画效果有些微妙之处。如果你愿意的话,如果你想看一下,我就把this above code放在github上。