分类目录归档:swift

关于swift中的强引用 弱引用 无主引用

好文推荐:
https://numbbbbb.gitbooks.io/-the-swift-programming-language-/content/chapter2/16_Automatic_Reference_Counting.html

精彩语句摘录:

在实例的生命周期中,如果某些时候引用没有值,那么弱引用可以阻止循环强引用。如果引用总是有值,则可以使用无主引用,在无主引用中有描述。在上面Apartment的例子中,一个公寓的生命周期中,有时是没有“居民”的,因此适合使用弱引用来解决循环强引用。

无主引用不会牢牢保持住引用的实例。和弱引用不同的是,无主引用是永远有值的。因此,无主引用总是被定义为非可选类型(non-optional type)。你可以在声明属性或者变量时,在前面加上关键字unowned表示这是一个无主引用。

由于无主引用是非可选类型,你不需要在使用它的时候将它展开。无主引用总是可以被直接访问。不过 ARC 无法在实例被销毁后将无主引用设为nil,因为非可选类型的变量不允许被赋值为nil。

弱引用必须被声明为变量,表明其值能在运行时被修改。弱引用不能被声明为常量。

Person和Apartment的例子展示了两个属性的值都允许为nil,并会潜在的产生循环强引用。这种场景最适合用弱引用来解决。

Customer和CreditCard的例子展示了一个属性的值允许为nil,而另一个属性的值不允许为nil,并会潜在的产生循环强引用。这种场景最适合通过无主引用来解决。

然而,存在着第三种场景,在这种场景中,两个属性都必须有值,并且初始化完成后不能为nil。在这种场景中,需要一个类使用无主属性,而另外一个类使用隐式解析可选属性。

swift osx 使用代码给窗口上增加控件

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
var helloButton : NSButton = NSButton()
override func windowDidLoad() {
       
        super.windowDidLoad()

        // Implement this method to handle any initialization after your window controller's window has been loaded from its nib file.
        let frame = NSRect(x: 10, y: 10, width: 200, height: 100)
        let button = NSButton(frame: frame)
        button.title = "Click me!"
       
        button.translatesAutoresizingMaskIntoConstraints = false
       
        self.window?.contentView?.addSubview(button)
       
        let horizontalConstraints = NSLayoutConstraint.constraintsWithVisualFormat("|-[button]-|", options: .AlignAllBaseline, metrics: nil, views: ["button":button])
        NSLayoutConstraint.activateConstraints(horizontalConstraints)
       
        let verticalConstraints = NSLayoutConstraint.constraintsWithVisualFormat("V:|-[button]-|", options: .AlignAllBaseline, metrics: nil, views: ["button":button])
        NSLayoutConstraint.activateConstraints(verticalConstraints)
       
        self.helloButton = button
       
    }

如果self.window=nil,则需要看下window的Outlets的连接是不是正确。

swift os x 开发 使用代码为NSWindow添加NSViewController

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
import Cocoa

@NSApplicationMain
class AppDelegate: NSObject, NSApplicationDelegate {

    //@IBOutlet weak var window: NSWindow!

    var window: NSWindow?

    func applicationDidFinishLaunching(aNotification: NSNotification) {
       
        let flowViewController = ImageViewController()
        flowViewController.title = "Flow"
        flowViewController.image = NSImage(named: NSImageNameFlowViewTemplate)
       
        let columnViewController = ImageViewController()
        columnViewController.title = "Column"
        columnViewController.image = NSImage(named: NSImageNameColumnViewTemplate)
       
        let tabViewController = NSTabViewController()
        tabViewController.addChildViewController(flowViewController)
        tabViewController.addChildViewController(columnViewController)
       
//        let splitViewController = NSSplitViewController()
//        splitViewController.addChildViewController(flowViewController)
//        splitViewController.addChildViewController(columnViewController)
       
        let window = NSWindow(contentViewController: tabViewController)
        window.makeKeyAndOrderFront(self)
        self.window = window
    }

    func applicationWillTerminate(aNotification: NSNotification) {
        // Insert code here to tear down your application
    }

}

NSUserDefaults的使用

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
import Cocoa

@NSApplicationMain
class AppDelegate: NSObject, NSApplicationDelegate {

    @IBOutlet weak var window: NSWindow!

    @IBOutlet weak var bluetoothSwitch: NSButton!

    func applicationDidFinishLaunching(aNotification: NSNotification) {
        // Insert code here to initialize your application
        let defaults = NSUserDefaults.standardUserDefaults()
       
        if (defaults.objectForKey("SwitchState") != nil) {
            bluetoothSwitch.state = defaults.integerForKey("SwitchState")
        }
    }

    func applicationWillTerminate(aNotification: NSNotification) {
        // Insert code here to tear down your application
    }

    @IBAction func saveSwitchState(sender: NSButton) {
        let defaults = NSUserDefaults.standardUserDefaults()

        defaults.setInteger(bluetoothSwitch.state, forKey: "SwitchState")
    }

swift os x开发之菜单栏程序自定义View

前面的文章 swift os x开发之菜单栏程序 点击菜单图标后弹出的是一个下拉菜单。如果我们想定义自定义的view怎么操作呢?

1、在之前文章的项目中,删掉Menu
2、拖进来一个Popover and View Controller
3、再拖进来一个Custom View
4、将Popover View Controller的view绑定指定给Custom View:
7BED3900 890D 4CE1 996D D3FD7061487B
5、代码:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
import Cocoa

@NSApplicationMain
class AppDelegate: NSObject, NSApplicationDelegate {

    @IBOutlet weak var window: NSWindow!
   
    @IBOutlet weak var popup: NSPopover!
   
    @IBOutlet weak var statusButton: NSButton!
   
    let statusItem = NSStatusBar.systemStatusBar().statusItemWithLength(-1)

    func applicationDidFinishLaunching(aNotification: NSNotification) {
        popup.behavior = NSPopoverBehavior.Transient
       
        let icon = NSImage(named: "statusIcon")
        statusItem.image = icon
        statusItem.target = self
        statusItem.action = Selector("iconClicked")
    }
   
    func iconClicked() {
        popup.showRelativeToRect(self.statusItem.button!.bounds, ofView: self.statusItem.button!, preferredEdge: NSRectEdge.MinY)
    }
}

6、运行效果:
屏幕快照 2015 10 09 上午10 07 44