Switch the sub viewController use segmented control
Follow below steps.
Add VC1 & VC2 as a childVC of mainVC.
On segment 1 selection
VC1.view.hidden = false
&vc2.view.hidden = true
On segment 2 selection
VC2.view.hidden = false
&vc1.view.hidden = true
take reference
How-to-add-childVC
How-tobind-segment-control-action
Code work
@IBAction func indexChanged(_ sender: AnyObject) {
switch segmentedControl.selectedSegmentIndex
{
case 0:
vc1.view.hidden = false
vc2.view.hidden = true
case 1:
vc2.view.hidden = false
vc1.view.hidden = true
default:
break
}
}
Change views using Segmented Control
Here i have created a complete solution as per your requirement.
Swift 4
//
// SegementedVC.swift
//
// Created by Test User on 01/02/18.
// Copyright © 2018 Test User. All rights reserved.
//
import UIKit
class SegementedVC: UIViewController {
//----------------------------------------------------------------
// MARK:-
// MARK:- Outlets
//----------------------------------------------------------------
@IBOutlet weak var segmentControl : UISegmentedControl!
@IBOutlet weak var containerView : UIView!
//----------------------------------------------------------------
// MARK:-
// MARK:- Variables
//----------------------------------------------------------------
private lazy var firstViewController: FirstViewController = {
// Load Storyboard
let storyboard = UIStoryboard(name: "Main", bundle: Bundle.main)
// Instantiate View Controller
var viewController = storyboard.instantiateViewController(withIdentifier: "FirstViewController") as! FirstViewController
// Add View Controller as Child View Controller
self.add(asChildViewController: viewController)
return viewController
}()
private lazy var secondViewController: SecondViewController = {
// Load Storyboard
let storyboard = UIStoryboard(name: "Main", bundle: Bundle.main)
// Instantiate View Controller
var viewController = storyboard.instantiateViewController(withIdentifier: "SecondViewController") as! SecondViewController
// Add View Controller as Child View Controller
self.add(asChildViewController: viewController)
return viewController
}()
//----------------------------------------------------------------
// MARK:-
// MARK:- Abstract Method
//----------------------------------------------------------------
static func viewController() -> SegementedVC {
return UIStoryboard.init(name: "Main", bundle: nil).instantiateViewController(withIdentifier: "SegementedView") as! SegementedVC
}
//----------------------------------------------------------------
// MARK:-
// MARK:- Memory Management Methods
//----------------------------------------------------------------
override func didReceiveMemoryWarning() {
super.didReceiveMemoryWarning()
}
//----------------------------------------------------------------
// MARK:-
// MARK:- Action Methods
//----------------------------------------------------------------
@IBAction func segmentValueChanged(_ sender: UISegmentedControl) {
updateView()
}
//----------------------------------------------------------------
// MARK:-
// MARK:- Custom Methods
//----------------------------------------------------------------
private func add(asChildViewController viewController: UIViewController) {
// Add Child View Controller
addChildViewController(viewController)
// Add Child View as Subview
containerView.addSubview(viewController.view)
// Configure Child View
viewController.view.frame = containerView.bounds
viewController.view.autoresizingMask = [.flexibleWidth, .flexibleHeight]
// Notify Child View Controller
viewController.didMove(toParentViewController: self)
}
//----------------------------------------------------------------
private func remove(asChildViewController viewController: UIViewController) {
// Notify Child View Controller
viewController.willMove(toParentViewController: nil)
// Remove Child View From Superview
viewController.view.removeFromSuperview()
// Notify Child View Controller
viewController.removeFromParentViewController()
}
//----------------------------------------------------------------
private func updateView() {
if segmentControl.selectedSegmentIndex == 0 {
remove(asChildViewController: secondViewController)
add(asChildViewController: firstViewController)
} else {
remove(asChildViewController: firstViewController)
add(asChildViewController: secondViewController)
}
}
//----------------------------------------------------------------
func setupView() {
updateView()
}
//----------------------------------------------------------------
// MARK:-
// MARK:- View Life Cycle Methods
//----------------------------------------------------------------
override func viewDidLoad() {
super.viewDidLoad()
self.setupView()
}
//----------------------------------------------------------------
override func viewWillAppear(_ animated: Bool) {
super.viewWillAppear(animated)
}
//----------------------------------------------------------------
override func viewDidAppear(_ animated: Bool) {
super.viewDidAppear(animated)
}
}
Storyboard Screenshots
Swift - Segmented control - Switch multiple views
You can use the isHidden
property of the UIView
to show/hide your required views.
First you have to link both views to IBOutlets
through the Interface builder
@IBOutlet weak var historyView: UIView!
@IBOutlet weak var popularView: UIView!
@IBAction func indexChanged(_ sender: UISegmentedControl) {
switch segmentedControl.selectedSegmentIndex {
case 0:
historyView.isHidden = true
popularView.isHidden = false
case 1:
historyView.isHidden = false
popularView.isHidden = true
default:
break;
}
}
Note: it was named hidden
in Swift 1 and 2.
Swift how to use container view and segmented control
You got very common mistake and error. But don't worry.
Check your full error message. There must be a clue what variable you are trying to access and getting nil (it might be resultLabel
).
Then make sure the connection between storyboard and view controller for this variable is correct. You can try to remove and create it again if you don't get what is wrong.
If you need more help, please show us full error message.
How can I use segmented control from container view to control my main view
I've found solution for this.
class FirstTestTableViewController: UITableViewController, ScrollSegmentDelegate {
func segmentIsChosen(segment: Int) {
print(segment)
questionNumber = segment + 1
}
var questionNumber = 0
func updateQuestionNumber() {
questionNumber + 1
scrollSegmentVC?.questionNumberToReceive = questionNumber
}
var scrollSegmentVC: ScrollSegmentVC?
override func prepare(for segue: UIStoryboardSegue, sender: Any?) {
if segue.identifier == "segment" {
scrollSegmentVC = segue.destination as? ScrollSegmentVC
scrollSegmentVC?.delegate = self
}
}
iOS Swift Segmented control with container view for switching - views are not loading first time
You can try added this code after method viewDidLoad, for show animation after app loaded.
override func viewDidAppear(_ animated: Bool) {
super.viewDidAppear(animated)
UIView.animateWithDuration(0.5, animations: {
self.containerViewA.alpha = 1
self.containerViewB.alpha = 0
}
}
Switching ViewControllers with UISegmentedControl in iOS5
This code works pretty well for your purpose, I use it for one of my new apps.
It uses the new UIViewController containment APIs that allow UIViewControllers inside your own UIViewControllers without the hassles of manually forwarding stuff like viewDidAppear:
- (void)viewDidLoad {
[super viewDidLoad];
// add viewController so you can switch them later.
UIViewController *vc = [self viewControllerForSegmentIndex:self.typeSegmentedControl.selectedSegmentIndex];
[self addChildViewController:vc];
vc.view.frame = self.contentView.bounds;
[self.contentView addSubview:vc.view];
self.currentViewController = vc;
}
- (IBAction)segmentChanged:(UISegmentedControl *)sender {
UIViewController *vc = [self viewControllerForSegmentIndex:sender.selectedSegmentIndex];
[self addChildViewController:vc];
[self transitionFromViewController:self.currentViewController toViewController:vc duration:0.5 options:UIViewAnimationOptionTransitionFlipFromBottom animations:^{
[self.currentViewController.view removeFromSuperview];
vc.view.frame = self.contentView.bounds;
[self.contentView addSubview:vc.view];
} completion:^(BOOL finished) {
[vc didMoveToParentViewController:self];
[self.currentViewController removeFromParentViewController];
self.currentViewController = vc;
}];
self.navigationItem.title = vc.title;
}
- (UIViewController *)viewControllerForSegmentIndex:(NSInteger)index {
UIViewController *vc;
switch (index) {
case 0:
vc = [self.storyboard instantiateViewControllerWithIdentifier:@"FooViewController"];
break;
case 1:
vc = [self.storyboard instantiateViewControllerWithIdentifier:@"BarViewController"];
break;
}
return vc;
}
I got this stuff from chapter 22 of Ray Wenderlichs book iOS5 by tutorial.
Unfortunately I don't have a public link to a tutorial. But there is a WWDC 2011 video titled "Implementing UIViewController Containment"
EDIT
self.typeSegmentedControl
is outlet for your UISegmentedControl
self.contentView
is outlet for your container view
self.currentViewController
is just a property that we're using to store our currently used UIViewController
Related Topics
When Do I Need to Call Setneedsdisplay in iOS
Uibutton Touch Is Delayed When in Uiscrollview
How to Write an Objective-C Completion Block
Ios11 Photo Library Access Is Possible Even If Settings Are Set to "Never"
Xcode 6 with Swift Super Slow Typing and Autocompletion
Uiscrollview with Centered Uiimageview, Like Photos App
Add Shadow on Uiview Using Swift 3
Build Not Visible in Itunes Connect
Convert Uiimage to Nsdata and Convert Back to Uiimage in Swift
How to Change the Color of the Text in a Uipickerview Under iOS 7
When Should Translatesautoresizingmaskintoconstraints Be Set to True
How to Combine Two Dictionary Instances in Swift
How to Make a Function Execute Every Second in Swift
Font Sizes in Uiwebview Does Not Match iOS Font Size
Debug on Real Apple Watch: Application Verification Failed