3
votes

I am adding an MPMoviePlayerViewController to my app like this:

MPMoviePlayerViewController *vc = [[MPMoviePlayerViewController alloc] initWithContentURL:movieURL];;
[self presentMoviePlayerViewControllerAnimated:vc];

Everything is working but I can't enable landscape mode. I want my whole app except the actual MPMoviePlayerViewController to be portrait. I searched on google but all the solutions require having the rest of the app also in landscape.I need my app to stay in Portrait except in the MPMoviePlayerViewController.

Thanks in advance!

EDIT:

Using @matt answer I added landscape to my Device Orientation:

enter image description here

Next I went to my First View Controller(Not the MPMoviePlayerViewController) and added:

-(NSUInteger)supportedInterfaceOrientations
{
    return UIInterfaceOrientationMaskPortrait;
}

However the app still let's the Main Menu go to Landscape mode.

5
But if the First View Controller is in, say, a navigation controller or a tab bar controller, then it is not the First View Controller but the navigation controller or tab bar controller that you need to worry about.matt

5 Answers

11
votes

Actually there is a way to just make Movie Player landscape without affecting portrait view of rest of screens.

#define degreesToRadian(x) (M_PI * (x) / 180.0)

MPMoviePlayerViewController *moviePlayerVC = [[MPMoviePlayerViewController alloc] initWithContentURL:[NSURL URLWithString:@"http://someurl.com"]];

moviePlayerVC.view.transform = CGAffineTransformIdentity;
moviePlayerVC.view.transform = CGAffineTransformMakeRotation(degreesToRadian(90));

[self presentViewController:moviePlayerVC animated:NO completion:NULL];

Make sure you are using MPMoviePlayerViewController and not MPMoviePlayerController, else it won't work.

2
votes

The problem is that MPMoviePlayerViewController is not your class so you have no control over its response to supportedInterfaceOrientations, which is what you would use to dictate the orientation of the presented view if this were your own view controller class. So you must make it your own view controller class. You will have to create your own MPMoviePlayerViewController subclass so that you can override supportedInterfaceOrientations and express what orientation you want (i.e. landscape). Create and present an instance of that subclass, not the built-in superclass.

0
votes

For Xcode 6.4, Swift 1.2 edited @Chandresh Panchasara answer a bit.

let movieC = MPMoviePlayerViewController()
        movieC.moviePlayer.contentURL = self.movieURL
        movieC.modalPresentationStyle = UIModalPresentationStyle.OverCurrentContext
        movieC.view.transform = CGAffineTransformIdentity;
        movieC.view.transform = CGAffineTransformMakeRotation(CGFloat((M_PI * (90.0) / 180.0)));
        self.view.window?.rootViewController?.addChildViewController(self)
        self.presentMoviePlayerViewControllerAnimated(movieC)
0
votes

Thanks for you answers it helped me.

For those who want it for Swift 4 here the solution:

playerVC.view.transform = CGAffineTransform.identity
playerVC.view.transform = CGAffineTransform.init(rotationAngle: degreesToRadian(90.0))
present(strongPlayerVC, animated: true)

Here the function degreesToRadian:

func degreesToRadian(_ degrees: CGFloat) -> CGFloat {
    return .pi * degrees / 180.0
}

Thanks and good luck!

-2
votes

The best way so far is to implement this AppDelegate function and check if the rootViewController has a child of type AVPlayerViewController then you return [.portrait, .landscapeLeft, .landscapeRight] and else .portrait.

func application(_ application: UIApplication, supportedInterfaceOrientationsFor window: UIWindow?) -> UIInterfaceOrientationMask {
    if let _ = UIApplication.shared.keyWindow?.rootViewController?.childViewControllers.first as? AVPlayerViewController {
        return [.portrait, .landscapeLeft, .landscapeRight]
    }
    return .portrait
}

You should check on the keyWindow of UIApplication because apple presents this viewController in a another UIWindow so if you try to do that check on the window that is declared in the AppDelegate this won't work so be careful.