johnno1962 / injectionforxcode

Runtime Code Injection for Objective-C & Swift
MIT License
6.55k stars 565 forks source link

Injection does not work with Generic Classes #244

Open mkkroliks opened 6 years ago

mkkroliks commented 6 years ago

Hey I just realized that injection doesn't work when I subclass view controller from generic view controller. I have a file like this.

import UIKit

class GenericController<A>: BaseViewController {

}

class NonGenericController: BaseViewController {

}

class LoginViewController: GenericController<UIView> {

    override func viewDidLoad() {
        super.viewDidLoad()
        view.backgroundColor = .white
    }

    #if DEBUG
    @objc func injected() {
        for subview in self.view.subviews {
            subview.removeFromSuperview()
        }
        viewDidLoad()
    }
    #endif
}

When I subclass like this it's doesn't reload and I'm getting following output:

`Compiling /Users/mk/proexe/dogWalkTrophy-ios/DogWalkTrophy/DogWalkTrophy/Screens/Login/LoginViewController.swift

Injection: Loading /Users/mk/Library/Developer/Xcode/DerivedData/DogWalkTrophy-ckqnnpzyqukneiczeuwblphvsqyg/Logs/iOSInjectionProject/build/Debug-iphonesimulator/InjectionBundle100.bundle objc[35393]: Class _TtC13DogWalkTrophy20NonGenericController is implemented in both /Users/mk/Library/Developer/CoreSimulator/Devices/78BAC6B7-531C-4136-9581-65147C03C856/data/Containers/Bundle/Application/FE4C6AD6-4AF6-4270-88F7-08D182370AE7/DogWalkTrophy.app/DogWalkTrophy (0x10f994810) and /Users/mk/Library/Developer/Xcode/DerivedData/DogWalkTrophy-ckqnnpzyqukneiczeuwblphvsqyg/Logs/iOSInjectionProject/build/Debug-iphonesimulator/InjectionBundle100.bundle/InjectionBundle (0x13269e7a0). One of the two will be used. Which one is undefined. 80 injections performed so far. Injection: Ignore any warning, Swizzled DogWalkTrophy.NonGenericController 0x13269e7a0 -> 0x10f994810`

but when subclass from non generic code everything works fine:

class LoginViewController: NonGenericController {

Why is that? Anyone has some idea? Thanks!

johnno1962 commented 6 years ago

Generic classes are not visible to the Objective-C runtime which injection uses so this is not possible. You could argue a concrete non-generic subclass should be represented somehow but that’s more of a Swift bug.

mkkroliks commented 6 years ago

@johnno1962 thanks for answer, that makes sense!