Transition behavior using transitionFromView and transitionWithView

I am attempting to create a transition between two subviews (view1 and view2). When a button is pressed I want view1 (front) to flip and show view2 (back). I have tried both transitionFromView and transitionWithView. Each works – but each has a problem.

transitionFromView – flips the superview (the whole window view flips, not the subviews). When this flip happens – one subview is on the front of the superview before the flip, and the other subview is on the back of the flip – as it should be. But I don’t want the superview to flip, just the subviews.

  • iOS Objective C - UIWebView AutoFill and Execute
  • Amazon S3 POST upload in iOS
  • to Parse JSON to NSArray in Swift
  • get pfx file included in a mobilecertificate in iOS
  • Protocol Delegate Method is not called in Swift
  • AFNetworking 2.0 - “unacceptable content-type: text/plain”
  • transitionWithView – flips only the subviews – but the ‘to’ view gets displayed before the transition happens.

    Anyone have a suggestion?

    -(IBAction) button1action:(id) sender {  
    
     if ([sender tag] == 0) {  
    
      [UIView transitionFromView:view2 toView:view1 duration:2.0   
      options:UIViewAnimationOptionTransitionFlipFromLeft   
      completion:nil];   
    }  
    
     else {  
      [view1 removeFromSuperview];    
      [self.view addSubview:view2];  
      [UIView transitionWithView:view2   
        duration:2.0  
        options:UIViewAnimationOptionTransitionFlipFromRight +  
        UIViewAnimationOptionShowHideTransitionViews  
          animations:^{}   
         completion:nil];  
     }
    }
    

    7 Solutions Collect From Internet About “Transition behavior using transitionFromView and transitionWithView”

    You need to remove and add the subviews in the animation block. Also, I think that transitionWithView is supposed to take the super view as argument. I think what you need to do to get this right is to use a container view that is the same size as the views you want to flip.

    This is copied from the documentation:

    [UIView transitionWithView:containerView
           duration:0.2
           options:UIViewAnimationOptionTransitionFlipFromLeft
           animations:^{ [fromView removeFromSuperview]; [containerView addSubview:toView]; }
           completion:NULL];
    

    I have run into this exact same problem, and I agree with the earlier answer. It seems you must have a container view for animating a transition from one subview to another subview.

    I’m using the transitionFromView approach. To have a background behind the animation, you will also need a superview with the background for the container view.

    My code looks like:

        [UIView transitionFromView:view1
                            toView:view2
                          duration:0.5
                           options:UIViewAnimationOptionTransitionFlipFromRight |
                                   UIViewAnimationOptionAllowUserInteraction    |
                                   UIViewAnimationOptionBeginFromCurrentState
                        completion:nil];
    

    Here’s my working solution stub, a simple thing that took 2 hours, damn:
    we got 1 button to flip things, a UIView called panel that holds the 2 views I want to swap with a flip animation.

    -(void)viewDidLoad{
        [super viewDidLoad];
        UIButton *btnFlip = [UIButton buttonWithType:UIButtonTypeRoundedRect];
        btnFlip.frame = CGRectMake(10, 10, 50, 30);
        [btnFlip setTitle:@"flip" forState:UIControlStateNormal];
        [btnFlip addTarget:self action:@selector(flip) forControlEvents:UIControlEventTouchUpInside];
        [self.view addSubview:btnFlip];
    
        panel = [[UIView alloc] initWithFrame:CGRectMake(10, 40, 300,300)];
        panel.backgroundColor = [UIColor darkGrayColor];
        [self.view addSubview:panel];
    
        panelBack = [[UIView alloc] initWithFrame:CGRectMake(10, 40, 280, 200)];
        panelBack.tag = 1;
        panelBack.backgroundColor = [UIColor brownColor];
        [panel addSubview:panelBack];
    
        panelFront = [[UIView alloc] initWithFrame:CGRectMake(10, 40, 280, 200)];
        panelFront.tag = 2;
        panelFront.backgroundColor = [UIColor whiteColor];
        [panel addSubview:panelFront];
    
        displayingFront = TRUE;
    }
    
    -(void)flip{
    
        [UIView transitionWithView:panel 
        duration:0.5
        options:(displayingFront ? UIViewAnimationOptionTransitionFlipFromRight : UIViewAnimationOptionTransitionFlipFromLeft)
        animations:^{ 
            if (displayingFront) {
                //panelFront.hidden=TRUE;
                //panelBack.hidden = FALSE;
                [panelFront removeFromSuperview];
                [panel addSubview:panelBack];
            }else{
                //panelFront.hidden=FALSE;
                //panelBack.hidden = TRUE;
                [panelBack removeFromSuperview];
                [panel addSubview:panelFront];
            }
         }
         completion:^(BOOL finished){
             displayingFront = !displayingFront;
         }];
    }
    

    Having run into the same problem I agree with Eric and Sam:
    either transitionWithView or transitionFromView will both do what you want as given above as long as you create a container view of the appropriate size that you wish to flip. Otherwise the whole window view will flip.

    So if view1 is the subview you begin with and you want to flip to view2 then add

    UIView *containerView = [[UIView alloc] initWithFrame:appropriateSize];
    [containerView addSubview:view1];
    

    And then the simplest way to animate is probably:

    [UIView transitionFromView:view1 
                        toView:view2 
                      duration:2.0   
                       options:UIViewAnimationOptionTransitionFlipFromLeft   
                    completion:nil];   
    

    I had the same requirement, and saw many approaches — from using layers (which ends up very complicated if you just want to deal with a UIView) to suggestions that i needed a “container” to then transition between to sub-views. But if you just want to swithc something front to back, like flipping over a playing card or a game tile, i made a one line change:

    (note: i have an array of UIViews (tiles[x][y]) in a grid (for a game). i have all my imagefilenames in database tables / arrays, which dynamically are loaded into the UIImages of the UIImageViews. The image for the “back” of a card or tile in a UIImage named “tileBackPicImageNM”.

    so my code that simply swapped the front image out for an image of the back was:

    [tiles[indexX][indexY] setImage:[UIImage imageNamed:tileBackPicImageNM]];
    

    which works fine.

    but and now, to show a flipping action, it is:

    [UIView transitionWithView:tiles[indexX][indexY] duration:0.3 options:UIViewAnimationOptionTransitionFlipFromLeft 
                        animations:^{  
                            [[indexX][indexY] setImage:[UIImage imageNamed:tileBackPicImageNM]];
                        }
                        completion:NULL];    
    

    I experimented with different “duration” parameters — subsequently made it a float that I set in the viewDidLoad routine. Faster than 0.3 is almost not visible, and a value of 1 or 2 is very slow…

    This does not involve two sub-views, which is my case is a lot more useful since i didn’t want to have an array of containers containing a hierarchy of views, etc… and on new levels etc i always reload the arrays anyway…

    Keep in mind that the container view requires a solid background color.It means anything else than clear color.This was my mistake and spent quite long time to figure it out.

    using transitionFromView, both front and back view should be inside another view(not the super view). this way it will not flip the whole screen.

    > superview
    >     another view
    >        backview
    >        frontview
    

    UIView.transitionFromView(frontView, toView: backView, duration: 0.5, options: .TransitionFlipFromLeft | .ShowHideTransitionViews) { finished in

    }

    You might want to make the (another view) equal to the size of the frontView