John Michael Zorko
John Michael Zorko

Reputation: 329

iOS: How to make one view controller mirror another's actions

I'm trying to "mirror" a view controller:

  1. app instantiates view controller 1 (of class A)
  2. app instantiates view controller 2 (also of class A) on another UIWindow (external display, via Airplay or physical connector)
  3. any touch event that view controller 1 receives should be mimicked on view controller 2

I've got part of this working on things like MkMapViews and simple view controllers by just catching things like region changes or scrolling in vc1 and telling vc2 to set its region or scroll to that position, having UIControl IBActions on vc1 also call the same action in vc2, etc.

This works with simple cases, but the problem comes with complex view controllers that have things like UITableViews with custom UITableViewCells that expand / contract, etc. I find myself having to implement every single possible delegate / action and make a bunch of objects aware of things they shouldn't be aware of, which just seems wrong if I'm going to make this at all reusable.

I've tried walking the subview tree of vc1 and using objc_setAssociatedObject() to associate the UIResponders in the view controller instances with each other, but I still have to catch every delegate / action on vc1 to look up the UIResponder on vc2 to mimic the event. There has to be a simpler way to do this. I tried subclassing UIWindow and overriding sendEvent and sending the event to the external display's UIWindow as well, but each UIEvent seems to have info in it that ties it to the UIWindow it originated in, as the external display UIWindow did nothing with it when I sent it.

How would I do this in a way that would allow me to abstract away the mirroring into a nice subclass or something so I don't have to litter every view controller with special-case code? I've thought about swizzling UIView's touch events, but I'm not even sure if that will help since UITouches and UIEvents are tied to the UIWindow they originated from, and UIEvent doesn't seem to provide a way for me to create my own event.

NOTE: what I'm trying to do is not default Airplay mirroring, as I want the external display experience to take advantage of the full display resolution and dimensions. The idea is to allow an iPhone app to work on the device itself (i.e. taller than it is wide), while also providing an experience on an external display that is geared for that display (wider than it is tall, greater resolution, opportunities to present info in a more readable HDTV-friendly format).

Thoughts?

Upvotes: 5

Views: 424

Answers (0)

Related Questions