Add views to "more" tab item - iphone

Is it possible to change appearence of "more" item in TabBarController? For example can I add custom views and change layout of tableView containing "more" controllers list?

Just find it was already discussed in
Customizing the More menu on a Tab bar
https://discussions.apple.com/thread/2399024
So we can get instance of this "More" ViewController using:
UIViewController *moreViewController = tabBarController.moreNavigationController.topViewController;
In fact it is of undocumented class UIMoreListController declared as:
#interface UIMoreListController : UIViewController <UITableViewDelegate, UITableViewDataSource>
moreViewController.view property contain UITableView and we can use it, for example add tableHeaderView:
UITableView *moreTableView = (UITableView*)moreViewController.view;
moreTableView.tableHeaderView = myOwnCustomView;
But I am not sure is this code "applesafe"? Because it use private class although not explicitly.
And what if I want to add a view that shouldn't scroll with table? Any ideas?

yes, this is all possible, if you could give us an example of what you want, maybe with a screenshot or something, then we can help you with some code examples

You can do what you want to do...
by using UITableViewController as a moreview tabbaritem.
and can create a moreview some what similar to the standard moreView controller.

Related

Cannot add Outlet connection from Button to ViewController

I am trying to create an IBOutlet connection/reference from my button to my UIViewController in Xcode, but it is only giving me the "option" to add an Action connection. I am trying to utilize the viewDidLoad and baselineAdjustment to vertically center the buttons label when the text scales to fit the width, but am not having any luck.
Does anyone have a suggestion or know what I'm doing wrong?
EDIT: Adding a few more screenshots for clarity
If I select my main Scene View, the class is of type ViewController. If I select the view that the Button in question is a part of(it is in a ContainerView), it is of class UIViewController and the options do not present a choice of ViewController.
Make sure the right class subclassing the UIViewController, make sure when you are doing it, you choosing the UIViewController and not the View or the safe area.
Let me know if it solved it
I see the you have multiple ViewControllers in storyboard. Ideally, each View controller in the storyboard is supposed to be of only one type of UIViewController implementation and it's also true the other way around. so, If you have say 3 UIViewControllers in Your storyBoard, then you will need to create 3 .swift files which implement UIViewController like so:
abcVC:UIViewController { .....
efgVC:UIViewController { .....
ViewController:UIViewController { ..... //this is the default one you get.
and then set the class of each ViewController in your storyboard to one of each of the above.
if your ViewController which has the button you want to outlet has a class type abcVC, then you can outlet your button only in abcVc's implementation in abcVC.swift.
Hope it makes sense. to see how to set class, refer #Vadim F. 's answer.
and if you happen to upvote this answer, please also consider upvoting #Vadim F. 's answer.
This is how you can crate a new .swift file while subclassing a UIViewController: File -> new -> File -> Cocoa touch class -> #make it subclass of UIViewController and give it a unique name eg: abcVC
Certify that your ViewController in the Storyboard is of the class ViewController (i.e your view controller) and not from UIViewController.

How can I place a UITableView on a UIViewController programmatically so that it doesn't take up the whole view?

I want to have a ViewController that has a table view on the top half of the screen, and a button under it. I'm assuming there's a simple way to do this. Every way I have tried so far ends up in the bottom half of the view being inaccessible.
The trick is that you cannot use a subclass of UITableViewController. You need to enable the datasource and delegate protocols explicitly in a UIViewController.
#interface MyController : UIViewController <UITableViewDatasource, UITableViewDelegate>
// variables and properties
#end
Don't forget to assign self as delegate and datasource of your tableview.
Now you can just put the table view anywhere by giving it an appropriate frame and you can also put a button at the bottom.
Hint: the standard way to "put a button at the bottom" is to use a UIToolBar. With that you could use the normal table view controller without having to worry about the protocols. But your approach is also feasible.
Well, you could have put a sample image to get the clear idea. but AFAI understood, i try to give the answer accordingly :
You can set the frame especially height of TableView just half the size of the height of your UIViewController.
Then rest of the space of UIViewCobtroller you can create another view where you can place your button as you have already done so far.
You can add the button in your UITableView's footer section.

How to get access to UITableViewController properties when subclassing from UIViewController?

I have subclassed UIViewController to provide common functionality for all UIViewControllers (for example I'm overriding viewDidLoad method). My app uses a bunch of view controllers that are arranged inside tab bar controller and in navigation controllers. Everything is OK, except the fact I have one UITableViewController. I would like to subclass not it but my custom MyUIViewController. I'm able to get the table working by implementing data source and delegate protocols:
#interface MaschinenTableViewController : MyUIViewController <UITableViewDataSource, UITableViewDelegate>
However in this case, I do not have an access to UITableViewController properties. For example, I cannot change the behavior of table row selection because self is MyUIViewController not UITableViewController:
self.clearsSelectionOnViewWillAppear = YES;
Are there any workarounds for accessing those properties?
In this case you will need to add a UITableView variable to the header and set it up appropriately in viewDidLoad, and add it to your view. From this point it will work as a UITableViewController will (as essentially that's all it does!)
Take a look at my article here which takes this approach.
You could also subclass UITableViewController as MyUITableViewController, implementing the behavior you want, and then put a MyUITableViewController as variable to your MyUIViewController.
Did the same as Simon Lee mentioned using the delegate.
But without storing the index anywhere, at the end of didSelectRowAtIndexPath method called the deselectRowAtIndexPath. Worked for me no issues so far.

Identify the current Navigation Bar

I'm trying to identify the Navigation Bar in the current view so that I can add a subview to it.
I have seen this code which is able to identify the Navigation Bar that has been dynamically created and tagged:
UINavigationBar *theNavigationBar = (UINavigationBar *)[inParent.view viewWithTag:kNavigationBarTag];
But in my case the Navigation bar is not being created dynamically, so it's not tagged. Is there a way to identify it otherwise?
self.navigationController.navigationBar
Only valid when called from a method in a UIViewController, of course. Otherwise, try to retrieve a reference to the view controller and take it from there.
You set the tag property for UINavigationBar if you create or access it from your UIViewController (self.navigationController.navigationBar )
because tag is the property of UIView which is the super class for UINavigationBar ,
May be you are referring code from the below blog post ...
http://iphonesdevsdk.blogspot.com/

UISearchBar with Controller in a normal UIView?

What I want:
A UIView with a UISearchBar at the top. Starting to edit the searchBar dims the current view and shows search results from another [UITableView]Controller.
What I've tried:
In Interface Builder:
add a "Search Bar and Search Display Controller" to the UIView.
add a placeholder object for my UITableViewController
add a UITableView object and set it as the view for the UITableViewController
set the delegate for the UISearchBar to the UITableViewController
set all the outlets on the UISearchDisplayController to the UITableViewController
In Code:
add the UISearchBarDelegate, UISearchDisplayDelegate protocols to the UITableViewController
What I'm getting:
Tapping to edit the search field crashes the app. No error messages, and only the "viewDidLoad" method in the UITableViewController gets called.
In Conclusion:
How do I go about using an external controller for a UISearchBar that is in a UIView?
Ok, so I've figured it out. I swear this is one of the first things I tried, but obviously I didn't do it correctly.
In my UIViewController (the one that has the UISearchBar in it), I instantiate a UISearchDisplayController:
// sb = IBOutlet UISearchBar
sc = [[SearchController alloc] initWithStyle:UITableViewStylePlain];
sdc = [[UISearchDisplayController alloc] initWithSearchBar:sb contentsController:sc];
sb.delegate = sc;
sdc.delegate = sc;
sdc.searchResultsDelegate = sc;
sdc.searchResultsDataSource:sc = sc; `
Where SearchController is my subclass of UITableViewController and adapts the UISearchBarDelegate and UISearchDisplayDelegate protocols.
Now that I think about it, using one linked from IB would probably work just as well (and in the same way)...
So the above works for me, but now the results tableView doesn't show up unless I manually add it to the main view: [self.view addSubview:sc.tableView]; but that's fodder for another question, I suppose.
There isn't any documentation on the web (as far as my google-fu is concerned) of a non-self-delegated UISearchDisplayController, so hopefully this helps out another Obj-C noob someday.
For one thing, if your Controller class is extending from UITableViewController, you can't have a search bar in it if you're using Interface Builder. Instead, extend from UIViewController and conform to the Table Data Source and Delegate protocols on your own.
But yeah, for that answer to be a good one for you, you're going to have to add some code or something to your question.