I'm developing a game in xcode 5, and after a collision I need to change the view
(it's a new view, not the previous, nor the rootView).
Is it possible to do this without using segues?
Here's a couple ways off the top of my head:
You can use UINavigationController to push another view into the user's view, or you can do a "presentViewController:".
Related
I have a View Controller that is presented when you first open the app, and I have another controller that can be shown on screen if you tap a button at the top of the screen. However, instead of doing it this way I was wondering if I can either drag the view down or tap the button and have an animation take care of that.
I have tried doing this with a PageView Controller, but this doesn't show the effect I wanted as it simply translates over to the next view and doesn't actually keep the initial view fixed in place while the second view slides over it.
Also, instead of a view controller would a view initially placed out of bounds in the main View Controller work? Thanks in advance!
You could use a side menu like MMDrawerController that has 4 type of animations for presenting the viewController.
Or you can create your custom UIView (not viewController) even using Interface Builder and animate that screen yourself. The animation can be started using UIScreenEdgePanGestureRecognizer.
I'm fairly new to Mac development and am slightly confused by the new "storyboard" feature in Xcode 6. What I'm trying to do is segue from one view controller to another in the same window. As of right now, all the different NSViewControllerSegues present the view controller in a new window, be it a modal or just another window. What I'd like to do is just segue within the same window, much in the same way one would on iOS (though an animated transition is not crucial). How would this be achieved?
If you provide a custom segue (subclass of NSStoryboardSegue) you can get the result you are after. There are a few gotchas with this approach though:
the custom segue will use presentViewController:animator so you will need to provide an animator object
because the presented view is not backed by a separate Window object, you may need to provide it with a custom NSView just to catch out mouse events that you don't want to propagate to the underlying NSViewController's view
there's also a Swift-only glitch regarding the custom segue's identifier property you need to watch out for.
As there doesn't seem to be much documentation about this I have made a small demo project with custom segue examples in Swift and Objective-C.
I also have provided some more detail in answer to this question.
(Reviving this as it comes up as first relevant result on Google and I had the same problem but decided against a custom segue)
While custom segues work (at least, the code given in foundry's answer worked under Swift 3; it needs updating for Swift 4), the sheer amount of work involved in writing a custom animator suggests to me that their main use case is custom animations.
The simple solution to changing the content of a window is to create an NSWindowController for your window, and to set its contentViewController to the desired viewController. This is particularly useful if you are following the typical pattern of storyboards and instantiate a new ViewController instance every time you switch.
However.
The NSStoryboard documentation says, quite clearly in macOS, containment (rather than transition) is the more common notion for storyboards which led me to look again at the available tools.
You could use a container view for this task, which adds a NWViewController layer instead of the NSWindowController outlined above. The solution I've gone with is to use an NSTabViewController. In the attributes inspector, set the style to 'unspecified', then select the TabView and set its style to 'tabless'.
To change tabs programatically, you set the selectedTabViewItemIndexof your TabViewController.
This solution reuses the same instance of the ViewControllers for the tab content, so that any data entered in text fields is preserved when the user switches to the other 'tab'.
Simple way with no segues involved to replace the current view controller in the same window:
if let myViewController = self.storyboard?.instantiateController(withIdentifier: "MyViewController") as? MyViewController {
self.view.window?.contentViewController = myViewController
}
I'm building a share extension for my iOS app and I can't use the default SLComposeServiceViewController, so I created (in the storyboard) a basic UIViewController and embedded in a navigation controller. I get to present it, dismiss it etc but it's always full screen. I would like to make it look more like a dialog.
I have tried using self.preferredContentSize on my view controller, tried Use Preferred Explicit Size on the navigation controller in Interface Builder, but it doesn't work.
This can be done easily and directly using the storyboard but is not immediately obvious. There is no need for multiple view controllers.
Create your own view controller class inheriting from UIViewController.
In the MainInterface.storyboard change the class of the view controller to your new class
In the storyboard you can simply draw your UI - but here is the trick. You need to understand that the storyboard view will fill the screen and by default the view has already been created with a clear background. You simply need to create a view inside of the main view. You can set auto layout constraints to size this view and position it (e.g. centered horizontally and vertically). You can also use size classes to cause this inner view to fill the screen on compact layouts. Connect the controls from the inner view to your view controller in the usual way by control-dragging
In you custom view controller you can refer to self.extensionContext to read and complete the share action. Refer to the code in the template ShareViewExtension
Ok I spent a long time trying to figure this out. For whatever reason you can't set the view size like you can with the action extension. It will always go full screen (even on iPad). So a way around this is to make multiple view controllers. Make the first view controller hidden so the user doesn't notice that there is a full screen view controller present (And yes, in a share extension the first hidden view controller actually hides completely so the user doesn't even know it was presented). Then present your actual view controller using the hidden view controller. This way you can present it any way you like and set the size etc.
In my case I actually made my hidden view controller have a UIEffectView so I can have a nice blur animation in the background and then present my actual view controller over it.
Here is a picture:
I have seven views that I need to navigate between from any of the other views. I don't want to keep doing segues from each one as new instances would keep being created...among other issues. What I was originally trying to do was have all the segues start from a home view and then go to the designated target view. When the user left that target view a public variable would be set if they wanted to go to any other view other than the home view. When the home view reappeared, it would check that public variable to see if another jump was needed. In the Home view I put the segue jump check in the -(void)viewDidAppear:(BOOL)animated function. The problem with this being you see the home screen for a second before it goes off to the new target view. The -(void)viewWillAppear:(BOOL)animated does not work for segues. I guess this is because it hasn't fully released the old segue yet?
Is there a better way to handle a freeform many view navigation issue like this? If anyone needs it, I can post some sample code for what I was trying to do. Thanks in advance for any help.
It sounds like you need a UITabBarController.
It allows you to have multiple view controllers, and switch between them by tapping the tab on the bottom of the screen.
It allows you to have only one instance of each controller, so that as you switch between them, data persists and you aren't creating new instances each time.
Here is an example of what one looks like (notice the tabs at the bottom of the screen):
(source: xamarin.com)
I had a question previously that died out and wanted to post a different approach and see if it was possible.
I have a working application that has a UITabBarController that controls 4 distinct UIViewControllers. I am able to navigate fine through these, but a couple of the loaded views need to load others in order to perform actions.
Is it possible to have a button within a UIViewController that will replace the current view with a different one and still maintain the tab bar on the bottom? possible replacing the current view and advising either the new UIViewController or the owner tabBarController that the relationship is still the same?
I can post code and further clarify if you wish. I am VERY new to XCode so i'm not completely familiar with how everything operates as of yet.
thank you in advance,
Silver Tiger
Yes you can add new view to one existed in the tab.
For example, if your view controller in tab is of type navigation based then you can push the other view upon certain event.