Present a UIViewController with active background - ios

There is a view controller (B), which presents as a half-screen modal with a custom presentation style and animation. I present this on a button tap on the main view controller (A), and dismiss with a close button on modal. When this modal is presented I want to access background view (A) buttons too. But when I inspect there is a TransitionView between the modal (B) and the background view (A).
Is there anyway to achieve this by presenting B as a modal on top of A? Or is there any other approach to show both A and B together & keep both active?

Yes it's possible, for modal presentation you have to use UIPresentationController and set shouldRemovePresentersView = false and implement UIViewControllerAnimatedTransitioning to perform the actual animation.
Alternatively you can use UISplitViewController with overlay presentation style, which then will take care of animations and layout for you.

Related

Transition between different presentation styles for a UIViewController using swift

I'm trying to create an affect where I present a UIViewController as a popover and then animate that view controller into a few different modal presentation styles.
I have successfully presented the view as a popover, and then after dismissing the view re presented it as a full screen overlay but I'm having trouble finding a workflow that allows me to transition without first dismissing the view controller.
I've included an illustration below showing the kind of effect I'd like to achieve where a single view controller transitions between 3 presentation styles, A, B, & C without being dismissed.
In the illustration A represents a popover modal presentation style, B custom, and C fullScreen
It's worth noting that these particular modal presentation styles are not important, rather that I would like to be able to transition between many kind of modal presentation style for a single view controller without first dismissing it.
What would be the best way to approach this kind of transition?

Dismiss all modals in iOS with Swift 4

I am trying to achieve a navigation similar to the Netflix app for iOS. When you click on a movie, a modal window pops up with a close button. If within this movie I choose to see another movie then the second modal pops up and in addition to the close button, a back button appears. I can use the back button to dismiss one by one and the close button to return to the base screen.
I am able to dismiss a single view using
dismiss(animated: true, completion: nil)
but how can I return to the base screen closing all modals at once? Also, is modals the way to go? I chose this because I didn't want the navigation bar on top.
I'm working with Swift 4.2 in Xcode 10.
The way you are dismissing a ViewController is not the correct way. The presenting view controller is responsible for dismissing the view controller. Ideally you have to implement a protocol in your presenting ViewController and , dismiss your modal from your 'presenting' ViewController not 'presented' ViewController.
The reason why your way still works is, when a ViewController calls self.dimiss if there's nothing to dismiss UIKit will delegate it back to its parent. If you implement this correct way, once you dismiss , your presenting viewcontroller will dismiss , hence all the presented viewcontrollers will be dismissed instead of the last one.
From Apple Docs:
The presenting view controller is responsible for dismissing the view controller it presented. If you call this method on the presented view controller itself, UIKit asks the presenting view controller to handle the dismissal.
If you present several view controllers in succession, thus building a stack of presented view controllers, calling this method on a view controller lower in the stack dismisses its immediate child view controller and all view controllers above that child on the stack. When this happens, only the top-most view is dismissed in an animated fashion; any intermediate view controllers are simply removed from the stack. The top-most view is dismissed using its modal transition style, which may differ from the styles used by other view controllers lower in the stack.
If you want to retain a reference to the view controller's presented view controller, get the value in the presentedViewController property before calling this method.
The completion handler is called after the viewDidDisappear(_:) method is called on the presented view controller.
try this
self.navigationController?.viewControllers.removeAll(where: {$0.isModalInPopover})

With a custom navigation controller push transition, how do I have the previous view controller behind like modal presentations?

When performing a custom modal view controller transition, the view controller you're coming from sits behind the new one nicely (think of Apple's "form sheet" style presentation on an iPad for instance), and when you rotate the device the previous view controller visible in the back rotates as well.
I'm unsure how to get this functionality with a UINavigationController custom push animation. It seems it isn't expected for the previous view controller to be visible from behind and it isn't.
I could take a screenshot, but it won't update on landscape rotation.
How is it done so easily with a modal transition and how do I replicate that for navigation controller custom transitions?
As far as I understand the UINavigationController class such functionality cannot be achieved through it.
UINavigationController is a container controller, which can show only one VC within it at a time. It keeps all the VCs in the stack, but not their views (views are kept by VCs themselves).
Unlike it, the modal presentation is a special type of VC-presentation, and it's not limited by the container-functionality.

Unable to set a dim background to a modal view

I'm developing an app targeting iOS 7 and above. I'd like to present modally a view with a dim background that partially shows the previous view below. I've read several posts dealing with this scenario, and I did:
Created a view controller scene in storyboard and set a modal segue to navigate to it.
Set the Presentation value of that modal segue to Current Context.
Set the view controller's view background color to clear color.
Added a full-screen view above the parent view, with black color background and 50% opacity.
Transition to the modal view is default and animated. While the animation, I see the view being presented as semi-transparent, but once the transition animation ends and view finally occupies the full screen, the view becomes opaque black.
What I'm doing wrong? How could I solve this?
As #luk2302 said, when you present a view controller modally, iOS removes the view controllers underneath it from the view hierarchy so is nothing underneath it except the app window, which is black. Anyway, iOS 7 has a new modal presentation style, UIModalPresentationCustom, that forces iOS not to remove the views underneath the presented view controller. But you must provide your own transition delegate to handle the presentation and dismiss animations
Check this link how to implement custom transition delegate.

Show UITabBar while presenting a modal view

When a user taps on a UITabBar item, I would like to present a view controller modally, but I would also like the UITabBar to remain visible. When the user is finished with the modal view controller I want to dismiss it modally. Basically, I want to show one view controller on top of another and dismiss the top view controller with a modal animation, while keeping the UITabBar visible. I am thinking I have to do some sort of custom animation, but I cannot figure out how to make that work.
Anyone know how to do this for iOS 6 and iOS 7?
Modal segues coverup the previous navigation controller stack, so any existing tab, navigation, and tool bar controllers will no longer accessible. You'll either need to use a push segue to retain the existing tab bar, or add a new tab bar controller to the modal view.

Resources