Is it possible to reuse a viewcontroller in another part of a viewcontroller?

1.5k Views Asked by At

I'd like to be able to use the same layout and viewcontroller but use different data set in different parts of the app. Is this possible without having to create another separate viewcontroller?

Because in my viewDid load I'm already calling upon an API request for that specific viewcontroller... Would there be a way to distinctly set a switch case on which viewcontroller it is supposed to be on?

I'm using storyboard and the stack hierarchy in navigation controller and looks similar to this:

V1 --> V2 --> V3 --> V4

So the idea is... same layout with different data. V1 and V4 should have the same exact layout. But the data set would be just a bit different. V1 is set up correctly and working fine already.

Is this a segue issue? Or something else? Thanks !! Much appreicated!!

1

There are 1 best solutions below

3
On BEST ANSWER

Please don't create 2 UIViewControllers that are almost exactly the same.

There are several ways to solve your problem. But since you're using Storyboards and segues, we'll do it that way.

In your V1 controller create a method to pass in the type of data that should be loaded. Something like this:

Objective-C

// In .h file
typedef enum : NSUInteger {
    DataTypeOne,
    DataTypeTwo
} DataType;


- (void)setupForDataType:(DataType) type;

In your V1 you'll have to move the logic that makes the API call from viewDidLoad into that new method. Something like:

// In .m file

@property(nonatomic, assign) BOOL didFetchData;

  - (void)setupForDataType:(DataType) type {
    self.didFetchData = YES;

    switch (type) {
        case DataTypeOne:
            // some API call
            break;
        case DataTypeTwo:
            // another API call
        default:
            break;
    }
}

- (void)viewDidLoad {
  [super viewDidLoad];

  if (self.didFetchData) { return; }
  // make default API call
}

Now in V3 in prepareForSegue method do this:

- (void)prepareForSegue:(UIStoryboardSegue *)segue sender:(id)sender {
    if ([segue.destinationViewController isKindOfClass:[V1 class]]) {
        V1 *vc1 = (V1 *)segue.destinationViewController;
        [vc1 setupForDataType:DataTypeTwo];
    }
}

Swift 3

 // In V1
enum DataType {
    case one
    case two
}

fileprivate var didFetchData = false

func setup(for dataType: DataType) {
    didFetchData = true
    switch dataType {
    case .one:
        // some API call
    case .two:
        // another API call
    }
}

func viewDidLoad() {
   super.viewDidLoad()
   if didFetchData { return }
   // make default API call
}

In V3 prepareForSegue

override func prepare(for segue: UIStoryboardSegue, sender: Any?) {
        guard let v1 = segue.destination as? V1 else { return }
        v1.setup(for: .two)
}