OSDN Git Service

関数名を変更
[kcd/KCD.git] / KCD / NyukyoDockStatus.swift
1 //
2 //  NyukyoDockStatus.swift
3 //  KCD
4 //
5 //  Created by Hori,Masaki on 2017/01/23.
6 //  Copyright © 2017年 Hori,Masaki. All rights reserved.
7 //
8
9 import Cocoa
10
11 private enum DockState: Int {
12     
13     case empty = 0
14     case hasShip = 1
15 }
16
17 final class NyukyoDockStatus: NSObject {
18     
19     private let number: Int
20     private let controller = NSArrayController()
21     private var didNotify = false
22     private var realTime: TimeInterval = 0.0 {
23         
24         didSet { time = realTime as NSNumber }
25     }
26     
27     @objc dynamic var name: String?
28     @objc dynamic var time: NSNumber?
29     @objc dynamic var state: NSNumber? {
30         
31         didSet { updateState() }
32     }
33     @objc dynamic var shipId: NSNumber? {
34         
35         didSet { updateState() }
36     }
37     @objc dynamic var completeTime: NSNumber?
38     
39     init?(number: Int) {
40         
41         guard case 1...4 = number else { return nil }
42         
43         self.number = number
44         
45         super.init()
46         
47         controller.managedObjectContext = ServerDataStore.default.context
48         controller.entityName = NyukyoDock.entityName
49         controller.fetchPredicate = NSPredicate(#keyPath(NyukyoDock.id), equal: number)
50         controller.automaticallyRearrangesObjects = true
51         controller.fetch(nil)
52         
53         bind(NSBindingName(#keyPath(state)), to: controller, withKeyPath: "selection.state")
54         bind(NSBindingName(#keyPath(shipId)), to: controller, withKeyPath: "selection.ship_id")
55         bind(NSBindingName(#keyPath(completeTime)), to: controller, withKeyPath: "selection.complete_time")
56     }
57     
58     deinit {
59         
60         unbind(NSBindingName(#keyPath(state)))
61         unbind(NSBindingName(#keyPath(shipId)))
62         unbind(NSBindingName(#keyPath(completeTime)))
63     }
64     
65     private func invalidate() {
66         
67         name = nil
68         time = nil
69     }
70     
71     private func updateState() {
72         
73         guard let state = state as? Int,
74             let stat = DockState(rawValue: state) else {
75                 
76                 return Logger.shared.log("unknown State")
77         }
78         
79         if stat == .empty {
80             
81             didNotify = false
82             invalidate()
83             return
84         }
85         
86         guard let shipId = shipId as? Int, shipId != 0 else { return }
87         
88         guard let ship = ServerDataStore.default.ship(by: shipId) else {
89             
90             name = "Unknown"
91             DispatchQueue(label: "NyukyoDockStatus").asyncAfter(deadline: .now() + 0.33) {
92                 
93                 self.updateState()
94             }
95             return
96         }
97         
98         name = ship.name
99     }
100     
101     func update() {
102         
103         guard let name = name else {
104             
105             time = nil
106             return
107         }
108         
109         guard let completeTime = completeTime as? Int else {
110             
111             invalidate()
112             return
113         }
114         
115         let compTime = TimeInterval(Int(completeTime / 1_000))
116         let diff = compTime - Date().timeIntervalSince1970
117         
118         realTime = max(0, diff)
119         
120         if didNotify { return }
121         if diff >= 1 * 60 { return }
122         
123         let notification = NSUserNotification()
124         let format = LocalizedStrings.dockingWillFinish.string
125         notification.title = String(format: format, name)
126         notification.informativeText = notification.title
127         
128         if UserDefaults.standard[.playFinishNyukyoSound] {
129             
130             notification.soundName = NSUserNotificationDefaultSoundName
131         }
132         
133         NSUserNotificationCenter.default.deliver(notification)
134         
135         didNotify = true
136     }
137 }