OSDN Git Service

10d5847df991e31516c3d0e1fe4c3a842f61562e
[kancollesniffer/KancolleSniffer.git] / KancolleSniffer / Sniffer.cs
1 // Copyright (C) 2013 Kazuhiro Fujieda <fujieda@users.sourceforge.jp>\r
2 // \r
3 // This program is part of KancolleSniffer.\r
4 //\r
5 // KancolleSniffer is free software: you can redistribute it and/or modify\r
6 // it under the terms of the GNU General Public License as published by\r
7 // the Free Software Foundation, either version 3 of the License, or\r
8 // (at your option) any later version.\r
9 //\r
10 // This program is distributed in the hope that it will be useful,\r
11 // but WITHOUT ANY WARRANTY; without even the implied warranty of\r
12 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\r
13 // GNU General Public License for more details.\r
14 //\r
15 // You should have received a copy of the GNU General Public License\r
16 // along with this program; if not, see <http://www.gnu.org/licenses/>.\r
17 \r
18 using System;\r
19 \r
20 namespace KancolleSniffer\r
21 {\r
22     [Flags]\r
23     public enum UpdateInfo\r
24     {\r
25         None = 0,\r
26         Item = 1,\r
27         Ship = 2,\r
28         Timer = 4,\r
29         Quest = 8,\r
30         NDock = 16,\r
31         Mission = 32,\r
32         Charge = 64\r
33     }\r
34 \r
35     public class Sniffer\r
36     {\r
37         private readonly NameAndTimer[] _ndocInfo = new NameAndTimer[4];\r
38         private readonly RingTimer[] _kdocTimers = new RingTimer[4];\r
39         private readonly ShipMaster _shipMaster = new ShipMaster();\r
40         private readonly ItemInfo _itemInfo = new ItemInfo();\r
41         private readonly QuestInfo _questInfo = new QuestInfo();\r
42         private readonly MissionInfo _missionInfo = new MissionInfo();\r
43         private readonly ShipInfo _shipInfo;\r
44 \r
45         public Sniffer()\r
46         {\r
47             _shipInfo = new ShipInfo(_shipMaster);\r
48             for (var i = 0; i < _ndocInfo.Length; i++)\r
49                 _ndocInfo[i] = new NameAndTimer();\r
50             for (var i = 0; i < _kdocTimers.Length; i++)\r
51                 _kdocTimers[i] = new RingTimer(0);\r
52         }\r
53 \r
54         public UpdateInfo Sniff(string uri, dynamic json)\r
55         {\r
56             if (uri.EndsWith("api_get_master/ship"))\r
57             {\r
58                 _shipMaster.InspectShip(json);\r
59                 return UpdateInfo.None;\r
60             }\r
61             if (uri.EndsWith("api_get_member/basic"))\r
62             {\r
63                 _itemInfo.InspectBasic(json);\r
64                 return UpdateInfo.Item;\r
65             }\r
66             if (uri.EndsWith("api_get_member/record"))\r
67             {\r
68                 _itemInfo.InspectRecord(json);\r
69                 return UpdateInfo.Item;\r
70             }\r
71             if (uri.EndsWith("api_get_member/material"))\r
72             {\r
73                 _itemInfo.InspectMaterial(json);\r
74                 return UpdateInfo.Item;\r
75             }\r
76             if (uri.EndsWith("api_get_member/slotitem"))\r
77             {\r
78                 _itemInfo.InspectSlotItem(json);\r
79                 return UpdateInfo.Item;\r
80             }\r
81             if (uri.EndsWith("api_get_member/questlist"))\r
82             {\r
83                 _questInfo.Inspect(json);\r
84                 return UpdateInfo.Quest;\r
85             }\r
86             if (uri.EndsWith("api_get_member/ndock"))\r
87             {\r
88                 InspectNDock(json);\r
89                 return UpdateInfo.NDock | UpdateInfo.Timer;\r
90             }\r
91             if (uri.EndsWith("api_get_member/kdock"))\r
92             {\r
93                 InspectKDock(json);\r
94                 return UpdateInfo.Timer;\r
95             }\r
96             if (uri.EndsWith("api_get_master/mission"))\r
97             {\r
98                 _missionInfo.InspectMission(json);\r
99                 return UpdateInfo.Mission;\r
100             }\r
101             if (uri.Contains("api_get_member/deck"))\r
102             {\r
103                 _missionInfo.InspectDeck(json);\r
104                 _shipInfo.InspectDeck(json);\r
105                 return UpdateInfo.Mission | UpdateInfo.Ship | UpdateInfo.Charge;\r
106             }\r
107             if (uri.EndsWith("api_get_member/ship2") || uri.EndsWith("api_get_member/ship3"))\r
108             {\r
109                 _shipInfo.InspectShipInfo(uri.EndsWith("ship3") ? json.api_ship_data : json);\r
110                 _itemInfo.NowShips = _shipInfo.NumShips;\r
111                 return UpdateInfo.Ship | UpdateInfo.Item | UpdateInfo.Timer | UpdateInfo.Charge;\r
112             }\r
113             return UpdateInfo.None;\r
114         }\r
115 \r
116         public void SaveMaster()\r
117         {\r
118             _missionInfo.SaveNames();\r
119             _shipMaster.Save();\r
120         }\r
121 \r
122         public void LoadMaster()\r
123         {\r
124             _missionInfo.LoadNames();\r
125             _shipMaster.Load();\r
126         }\r
127 \r
128         private void InspectNDock(dynamic json)\r
129         {\r
130             foreach (var entry in json)\r
131             {\r
132                 var id = (int)entry.api_id;\r
133                 _ndocInfo[id - 1].Timer.EndTime = (double)entry.api_complete_time;\r
134                 var ship = (int)entry.api_ship_id;\r
135                 _ndocInfo[id - 1].Name = ship == 0 ? "" : _shipInfo.GetNameById(ship);\r
136             }\r
137         }\r
138 \r
139         public NameAndTimer[] NDock\r
140         {\r
141             get { return _ndocInfo; }\r
142         }\r
143 \r
144         private void InspectKDock(dynamic json)\r
145         {\r
146             foreach (var entry in json)\r
147                 _kdocTimers[(int)entry.api_id - 1].EndTime = (double)entry.api_complete_time;\r
148         }\r
149 \r
150         public RingTimer[] KDock\r
151         {\r
152             get { return _kdocTimers; }\r
153         }\r
154 \r
155         public ItemInfo Item\r
156         {\r
157             get { return _itemInfo; }\r
158         }\r
159 \r
160         public QuestInfo.NameAndProgress[] Quests\r
161         {\r
162             get { return _questInfo.Quests; }\r
163         }\r
164 \r
165         public NameAndTimer[] Missions\r
166         {\r
167             get { return _missionInfo.Missions; }\r
168         }\r
169 \r
170         public string FleetName\r
171         {\r
172             get { return _shipInfo.FleetName; }\r
173         }\r
174 \r
175         public DateTime[] RecoveryTimes\r
176         {\r
177             get { return _shipInfo.RecoveryTimes; }\r
178         }\r
179 \r
180         public ShipStatus[] ShipStatuses\r
181         {\r
182             get { return _shipInfo.ShipStatuses; }\r
183         }\r
184 \r
185         public ChargeStatus[] ChargeStatuses\r
186         {\r
187             get { return _shipInfo.ChargeStatuses; }\r
188         }\r
189     }\r
190 \r
191     public class NameAndTimer\r
192     {\r
193         public string Name { get; set; }\r
194 \r
195         public RingTimer Timer { get; set; }\r
196 \r
197         public NameAndTimer()\r
198         {\r
199             Timer = new RingTimer();\r
200         }\r
201     }\r
202 \r
203     public class RingTimer\r
204     {\r
205         private bool _ringed;\r
206         private DateTime _endTime;\r
207         private TimeSpan _rest;\r
208         private readonly TimeSpan _spare;\r
209 \r
210         public RingTimer(int spare = 60)\r
211         {\r
212             _spare = TimeSpan.FromSeconds(spare);\r
213         }\r
214 \r
215         public double EndTime\r
216         {\r
217             set\r
218             {\r
219 // ReSharper disable once CompareOfFloatsByEqualityOperator\r
220                 if (value != 0)\r
221                     _endTime = new DateTime(1970, 1, 1).ToLocalTime().AddSeconds(value / 1000);\r
222                 else\r
223                 {\r
224                     _endTime = DateTime.MinValue;\r
225                     _ringed = false;\r
226                 }\r
227             }\r
228         }\r
229 \r
230         public void Update()\r
231         {\r
232             if (_endTime == DateTime.MinValue)\r
233             {\r
234                 _rest = TimeSpan.Zero;\r
235                 return;\r
236             }\r
237             _rest = _endTime - DateTime.Now;\r
238             if (_rest < TimeSpan.Zero)\r
239                 _rest = TimeSpan.Zero;\r
240             if (_rest > _spare || _ringed)\r
241                 return;\r
242             _ringed = true;\r
243             NeedRing = true;\r
244         }\r
245 \r
246         public bool NeedRing { get; set; }\r
247 \r
248         public bool IsSet\r
249         {\r
250             get { return _endTime != DateTime.MinValue; }\r
251         }\r
252 \r
253         public override string ToString()\r
254         {\r
255             return _rest.Days == 0 ? _rest.ToString(@"hh\:mm\:ss") : _rest.ToString(@"d\.hh\:mm");\r
256         }\r
257     }\r
258 }