In IOS programming, is a "View Controller" actually a controller? - ios

The name "View Controller" in iOS programming is a bit confusing as it includes both words "View" and "Controller" in the MVC model. Is "View Controller" actually just another name for Controller (as the view is actually mostly done by the Interface Builder). Why is it called a "View Controller"? Is it because this controller does all the view properties updating and event handling as well?

Yes, a UIViewController lives inside the "Controller" layer of MVC. But it is a special controller that controls and updates a view. View controllers can also handle events because they derive from UIResponder.
You can also create general controllers by subclassing NSObject. For example an accounts controller that manages accounts etc. You actually find other controller classes in the iOS SDK, e.g. UIDocumentInteractionController.
From the iOS View Controller Programming Guide:
For iOS applications, view controllers provide a vital link between an
application’s data and its visual appearance. Understanding when and
how to use view controllers is crucial to the design of iOS
applications. View controllers are traditional controller objects in
the Model-View-Controller design paradigm but they also do much more.
In iOS applications, view controllers provide much of the logic needed
to manage basic application behaviors. For example, view controllers
manage the presentation and removal of content from the screen and
they manage the reorientation of views in response to device
orientation changes.

"Controller" follows the thing being controller. If I were writing a controller for a chair I would call it a ChairController. Since a UIView is being controlled, it makes sense to call it a UIViewController right? The view itself is only responsible for display, but the logic of what to display is up to its controller.

From Apple docs - http://developer.apple.com/library/ios/#documentation/UIKit/Reference/UIViewController_Class/Reference/Reference.html
The UIViewController class provides the fundamental view-management model for all iOS apps.
Basically it is the container for your views and handles more logic than just the visual display that your view does.
Where necessary, a view controller:
resizes and lays out its views
adjusts the contents of the views
acts on behalf of the views when the user interacts with them

You should see a "View Controller" as a "Class that controles the view".
This is a classic Model View Controller pattern (MVC).
A UIViewController has a view of type UIView and you update this UIView depending on your business objects (Model) for each particular controller.
Also, events that occur on your UIView, are sent back to your UIViewController for handling them properly.

Related

MVC: Is a custom UITableViewCell a view or controller or both?

I used to consider a CustomUITableViewCell.xib as the view and the corresponding CustomUITableViewCell.swift class as the controller of a table view cell.
Is this correct? A youtube video I stumbled upon considers the class as the view: https://youtu.be/n06RE9A_8Ks?t=177
Edit:
To clarify the question: Which one of the following is the view and controller? Are both considered the view?
CustomUITableViewCell.xib
CustomUITableViewCell.swift
I'd absolutely consider it a "view" (in terms of MVC). It's of the group of logic that (along with the .xib) handles 1 particular view of information, rather than orchestrating some aspect of the general logic of the app.
I also consider a UIViewController as belonging to the "view" part of MVC for the same reason. Of course, if you put far more business logic into your view controllers than that which is necessary to support the single view, then your view controller is some mix of MVC. For example, if your view controller chooses what scene of the app comes next, your view controller then participates in controller logic and it's not really following MVC. Your view controller is forced to do a lot of single view-related work, though, because there's a single view it's responsible for and that the view-work is more practically done in the UIViewController rather than the UIView.
So when you ask about a cell view class's stance in MVC, if it's doing single view work, then it's a "View". If you mix in controller work or model work, then you've muddied up the separation of responsibilities that MVC espouses.
In my personal opinion it is a view. It should be handling only UI components in the class. Think of both files as a complete view. One cannot be without the other. Thus I consider them one.

A debatable delegate-like event notification pattern

I was left with continuing the code of a senior developer, where I came across a coding pattern that was not only bizarre, but got me curious about a lot of things. The pattern, however, that I spoke about had something like this:
There is a UIViewController the view of which has an instance of extended UIView attached to it as a subview.
This custom UIView class has a reference of the above-stated UIViewController.
There are a series of methods defined within the UIViewController that are responsible for handling events at the UIView.
Since this UIViewController exists as a reference, our custom view calls those event-handling methods through this reference!
In such a system of code, what are the memory implications? How is this any different from the delegate pattern? Under what circumstances using this sort of coding okay?
While this pattern is a little curious, I would hesitate to condemn this without more information about what this child view is doing and what it needs to inform the view controller about. There is, admittedly, a faint code smell here, and if I were to hazard a guess, I'd bet that this view is likely doing stuff that one would now generally put in a view controller.
Often, when adding a subview that has any significant complexity (or is likely to be reused in different views), one would consider an iOS 5 feature, "view controller containment" (see the Creating Custom Container View Controllers section of the View Controller Programming Guide or WWDC 2011 video Implementing UIViewController Containment).
If using storyboards, you can achieve much of this using the special "Container View" control introduced with iOS 6, found in Interface Builder's "Object Library" (in the bottom of the right panel in the standard Xcode layout). If doing this programmatically, just make sure to call the appropriate methods listed in the "Managing Child View Controllers in a Custom Container" section of the UIViewController Class Reference.
When using view controller containment, you have a parent view controller (the main view controller) and the child view controller (the view controller that is managing the subview). And in this scenario, it's very common to design a custom protocol by which a child view controller notifies its parent view controller of particular events. But rather than adding your own custom delegate property, you can use the built-in parentViewController property which is automatically populated when you adopt the above "view controller containment" pattern.
Having said all of this, I might let practical concerns drive whether the existing code base needs to be refactored or not. Perhaps the code predates iOS 5, but is a solid implementation of what we might have done back in the day. Bottom line, if it works, is otherwise well written, and has the delineation of responsibilities clearly defined, you might decide to just leave well enough alone. And if it's a little ambiguous (as the absence of a discussion of a protocol might suggest), perhaps just start by introducing a formal protocol between the child view and the view controller to make the interface explicit. Whether a more radical refactoring of the code (to use something like view controller containment) is called for is hard for us to advise on the basis of the limited information provided thus far.

What should be in View Controllers and what should be in Views?

I am at the beginning of developing an iOS app I am having trouble understanding the MVC (Model-View-Controller) design pattern. I thought I had it down but the more I read the more confused I get. I don't know if this should be an iOS specific question or if the same goes for every use of MVC. I am not using storyboards btw, I want to do it all programmatically.
I believe I understand the basic relationship between Controllers and Models, it's the separation of Views and Controllers that I don't get. Let's say I want to create a UIButton and display it on the screen. Should I initiate the button in the Controller or the View? The controller is responsible for what should be displayed, correct? Wouldn't you just call on a View to display that and not worry about creating the button in the Controller? From what I understand, View Controllers are just Controllers and should therefore control the View, not be the View. It seems like most people do just about everything in the View Controllers. I guess my question boils down to what code goes where?
UIViewController is controller part in the MVC pattern of code.
M(Model)
C(ontroller)
V(View)
Controllers handle navigation between different views , etc.
From here you can get more idea : view and viewcontroller
A view is an object that is drawn to the screen. It may also contain other views (subviews) that are inside it and move with it. Views can get touch events and change their visual state in response. Views are dumb, and do not know about the structure of your application, and are simply told to display themselves in some state.
A view controller is not drawable to the screen directly, it manages a group of view objects. View controllers usually have a single view with many subviews. The view controller manages the state of these views. A view controller is smart, and has knowledge of your application's inner workings. It tells the dumb view objects what to do and how to show themselves.
A view controller is the glue between you overall application and the screen. It controls the views that it owns according to the logic of your application
About View Controllers
View controllers are a vital link between an app’s data and its visual appearance. Whenever an iOS app displays a user interface, the displayed content is managed by a view controller or a group of view controllers coordinating with each other. Therefore, view controllers provide the skeletal framework on which you build your apps.
iOS provides many built-in view controller classes to support standard user interface pieces, such as navigation and tab bars. As part of developing an app, you also implement one or more custom controllers to display the content specific to your app.
Not sure about any iOS specifics but from a PHP standpoint controllers are there to get any data that is needed for the view (via models) and then pass that data to the view.
The view is there to render things to the screen only and should have no logic in it.
So from a website point of view if you wanted to display a users name on the screen:
The controller would request the username from the model
The model would get the username and return it to the controller
The controller would then pass the username to the view
And the view would then render the username.
Hope that helps.
To be not specific, but on a upper layer, you can say as following :
You can put controller code in class extending UIViewControllers
You can put view code in class extending UIView
You can put model code in class extending NSObject

iOS - UIViewControllers sharing a screen

I'm writing an app that has two sections like this:
The idea is that on the top half I'm creating a request, and on the bottom I'm displaying the results. As my UIViewController subclass grows and grows I thought it might be a good idea to split that into two UIViewControllers. (So what I'm trying to do is something like a UISplitViewController).
Although I know it's possible programmatically I'd like to put both UIViewControllers in the screen from the Interface Builder so I can manage autolayouts and design there. Dragging and dropping doesn't work there.
Is that possible? And more important - is that a good design or should I stick to the rule "One view controller for one screen"?
You can use a custom container view controller to achieve what you want. See:
WWDC 2011 #102 on UIViewController Containment (Apple developer ID required)
the containment section of the View Controller Programming Guide
the containment section of the UIViewController Reference document
In short, since iOS 5, you no longer have to have a single view controller. Just make sure you call the necessary containment related calls. And iOS 6 makes it easier to design the storyboards for custom containers with the "container view" object.
Apple have stated (WWDC 2012, Evolution of View Controllers, I think) that the "screenful" is no longer appropriate. A view controller should manage a self-contained chunk of functionality.
As of iOS5 you can compose an interface of multiple view controllers using view controller containment (addChildViewController: and so forth). As of iOS6 you can do this in interface builder using containers and containment segues.
You will of course need a view controller to hold your two child view controllers - this will hold a screenful of content, and will usually perform any coordination between the two children.

What's the best controller to use for interactive books?

I'm creating an interactive touch book in iOS. I'd like to know what the best controller is to use for books. (e.g. UIViewController, NavigationController, etc.). I'd prefer to stay with storyboard options.
And secondly what is the best way to handle pages? A separate ViewController for each page? a separate view for each page?
UIPageViewController
From the docs:
Page view controllers allow users to navigate between view controllers
using the specified transition. Navigation can be controlled by the
user using gestures as well as programatically.
View controllers are either provided one at a time (or two at a time,
depending upon the spine position and double-sided state) via the
setViewControllers:direction:animated:completion: method, or provided
as-needed by the data source. Gesture-based navigation is enabled only
when a data source is provided.
To alter the behavior of this class, you should provide a data source
and delegate. This class is not intended to be subclassed.
As for your second question, yes it is easiest to manage each page as a view controller since UIPageViewController is a container view controller and it holds an array of view controllers.

Resources