代码之家  ›  专栏  ›  技术社区  ›  user1107173

Swift:无法在协议扩展中使用可变方法

  •  0
  • user1107173  · 技术社区  · 8 年前

    我有4个视图控制器,需要根据用户屏幕宽度使用不同的图像。我试图保持代码干燥并使用协议扩展。

    以下是我的方案:

    import UIKit
    
    enum ScreenWidths: CGFloat {
            case iPhone455s = 320.0
            case iPhone6 = 375.0
            case iPhone6Plus = 414.0
    }
    
    protocol ScreenSizeProtocolExt {
        mutating func setupBG() -> String    
    }
    
    
    extension ScreenSizeProtocolExt {
        mutating func setupBG() -> String {
            let imageName: String
            let userScreenWidth = UIScreen.mainScreen().bounds.width
    
            switch userScreenWidth {
            case ScreenSizeWidth.iPhone455s.rawValue:
                imageName = "imageA"
            case ScreenSizeWidth.iPhone6.rawValue:
                imageName = "imageB"
            case ScreenSizeWidth.iPhone6Plus.rawValue:
                imageName = "imageC"
            default:
                imageName = "imageAll"
            }
    
            return imageName
        }
    }
    

    现在我正在尝试使用它:

    extension myViewController: ScreenSizeProtocolExt {
    
    let imageToUse = setupBG()
    // Here is get an error: 'Use of instance member 'setupBG' on type 'inout Self'; did you mean to use a value of type 'inout self' instead?
    let image = UIImage(named: imageToUse)
    imageView.image = image
    
    }
    

    如何使用协议扩展检测屏幕宽度并为我提供正确的 imageName 使用。

    1 回复  |  直到 8 年前
        1
  •  0
  •   Lou Franco    8 年前

    此代码:

    extension myViewController: ScreenSizeProtocolExt {    
    let imageToUse = setupBG()
    // Here is get an error: 'Use of instance member 'setupBG' on type 'inout Self'; did you mean to use a value of type 'inout self' instead?
    let image = UIImage(named: imageToUse)
    imageView.image = image    
    }
    

    不合法。主要的是,扩展无法添加新的存储属性,因此您无法执行以下操作:

    let imageToUse = setupBG()
    

    在分机中。

    此外,这一行:

    imageView.image = image 
    

    是非法的 func .

    至于你在这里需要什么,这一切似乎都太过分了。为什么要将其扩展到具有协议的viewControllers?您有一个返回imageName的函数,它可以在任何地方(只是一个自由函数,不在类中)。

    然后,在viewControllers中,只需将图像视图的图像设置为该函数返回的名称。

    扩展是为类提供更多接口的一种方式——不能让类仅通过扩展自动调用方法。