【问题标题】:How to create a settings object in Swift如何在 Swift 中创建设置对象
【发布时间】:2016-11-03 15:01:02
【问题描述】:

我正在尝试在 Swift-3 中创建一个对象,该对象将包含各种基本的用户设置,可以在整个应用程序中轻松访问。我目前将此设置作为一个名为PTSettings 的结构。它是这样实现的:

struct PTSettings {
    static var aUserSettings: String()
}

可以像这样在应用程序周围轻松访问:PTSettings.aUserSetting = "Foo"

我在这里苦苦挣扎的是,我希望这个结构能够观察来自NotificationCenter 的 UIScreen 通知。当一个屏幕连接时PTSettings初始化外部屏幕,为其分配一个视图,显示一个横幅让用户知道等等......

我熟悉在 UIViewController 上完成所有这些任务;但是我不擅长使用结构。我的希望是,当应用程序加载时,结构体将被初始化,并且 init 将观察NotificationCenter,同时检查在应用程序加载之前是否连接了屏幕。

以下是我目前拥有的。

/// Struct containing various user-generate data such as color, messages and other settings.
struct PTSettings {


    // External UI
    //
    static var externalScreen: UIScreen!
    //
    static var externalWindow: UIWindow!
    //
    static var extDisplay: PTExternalDisplayVC?


    init () {
        // Receive notifications if a screen is connected or disconnected
        //
        let center = NotificationCenter.default
        center.addObserver(self, selector: #selector(PTSettings.handleScreenDidConnectNotification(notification:)), name: NSNotification.Name.UIScreenDidConnect, object: nil)
        center.addObserver(self, selector: #selector(PTSettings.handleScreenDidDisconnectNotification(notification:)), name: NSNotification.Name.UIScreenDidDisconnect, object: nil)
        center.addObserver(self, selector: #selector(PTSettings.handleScreenModeDidChangeNotification), name: NSNotification.Name.UIScreenModeDidChange, object: nil)
    }




    // MARK: External Displays
    //
    static func initializeExternalScreen(externalScreen:UIScreen) {
        self.externalScreen = externalScreen

        externalScreen.overscanCompensation = UIScreenOverscanCompensation(rawValue: 3)!

        // Create a new window sized to the external screen's bounds
        self.externalWindow = UIWindow(frame: self.externalScreen.bounds)

        // Assign screen object to screen property of the new window
        self.externalWindow.screen = externalScreen

        // Load the clock view
        let viewForExternalScreen = self.storyboard?.instantiateViewController(withIdentifier: "ExternalDisplay") as! PTExternalDisplayVC
        viewForExternalScreen.view.frame = self.externalWindow.frame

        // Add the view to the window
        self.externalWindow.addSubview(viewForExternalScreen.view)

        // Create a reference to the viewForExternalScreen
        self.extDisplay = viewForExternalScreen

        // Make the window visible
        self.externalWindow.makeKeyAndVisible()
    }
    //
    static func handleScreenDidConnectNotification (notification:Notification) {
        if let screen = notification.object as? UIScreen {
            initializeExternalScreen(externalScreen: screen)
        }
    }
    //
    static func handleScreenDidDisconnectNotification (notification:Notification) {
        if externalWindow != nil {
            externalWindow.isHidden = true
            externalWindow = nil
            displayConnectedLabel.text = "No Display"
            displayConnectedLabel.textColor = CustomColors.Red.color
            JSSAlertView().warning(self, title: "External Display Disconnected.")
        }
    }
    //
    static func handleScreenModeDidChangeNotification () {
        let screen = UIScreen.screens[1]
        initializeExternalScreen(externalScreen: screen)
    }

}

编译器会抱怨init() 方法中每次添加的观察者,如下所示:

“#selector”的参数指的是未暴露给 Objective-C 的静态方法“handleScreenDidConnectNotification(notification:)”

但是,当在方法之前添加@objc 时,它会抱怨:

@objc 只能与类的成员、@objc 协议和类的具体扩展一起使用。

我怎样才能达到预期的结果,我是否完全不采用这种方法?

【问题讨论】:

    标签: swift struct notificationcenter


    【解决方案1】:

    我是不是完全不喜欢这种方法

    你确实完全不在了。将 Objective-C(和 Cocoa)与 Swift 区分开来。 Swift 结构是一个纯粹的 Swift 特性。您正在尝试使用 Cocoa 功能,即通过 selector 调用方法,并带有 Swift 功能,即结构。你不能那样做。 Swift 结构缺少允许选择器工作的 Objective-C 内省功能。这就是为什么您只能为 Objective-C 类的方法制作选择器的原因,即 从 NSObject 继承的 class(就像您过去所做的那样)。

    但是,another form 添加了一个通知中心观察者,您可以在其中使用尾随闭包/函数,而不是选择器。你可以试试这个(虽然我不保证什么)。

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2016-12-03
      • 1970-01-01
      • 2012-11-25
      • 1970-01-01
      • 2021-05-11
      • 2021-01-23
      相关资源
      最近更新 更多