Merge "[Application] Fixed path of getAppSharedURI" into tizen_5.0
[platform/core/api/webapi-plugins.git] / src / alarm / alarm_api.js
1 /*
2  * Copyright (c) 2015 Samsung Electronics Co., Ltd All Rights Reserved
3  *
4  *    Licensed under the Apache License, Version 2.0 (the "License");
5  *    you may not use this file except in compliance with the License.
6  *    You may obtain a copy of the License at
7  *
8  *        http://www.apache.org/licenses/LICENSE-2.0
9  *
10  *    Unless required by applicable law or agreed to in writing, software
11  *    distributed under the License is distributed on an "AS IS" BASIS,
12  *    WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13  *    See the License for the specific language governing permissions and
14  *    limitations under the License.
15  */
16
17 var T = xwalk.utils.type;
18 var Converter = xwalk.utils.converter;
19 var AV = xwalk.utils.validator;
20 var privUtils_ = xwalk.utils;
21
22 var native = new xwalk.utils.NativeManager(extension);
23
24 var isAlarmAbsolutePeriodDeprecated = true;
25
26 var AlarmManager = function () {
27     Object.defineProperties(this, {
28         PERIOD_MINUTE:  { value: 60, writable: false, enumerable: true},
29         PERIOD_HOUR:    { value: 3600, writable: false, enumerable: true},
30         PERIOD_DAY:     { value: 86400, writable: false, enumerable: true},
31         PERIOD_WEEK:    { value: 604800, writable: false, enumerable: true},
32     });
33 };
34
35 var EditManager = function() {
36     this.canEdit = false;
37 };
38
39 EditManager.prototype.allow = function() {
40     this.canEdit = true;
41 };
42
43 EditManager.prototype.disallow = function() {
44     this.canEdit = false;
45 };
46
47 var _edit = new EditManager();
48
49 function InternalData_(data) {
50     if (!(this instanceof InternalData_)) {
51         return new InternalData_(data);
52     }
53
54     for(var key in data) {
55         if (data.hasOwnProperty(key)) {
56             this[key] = data[key];
57         }
58     }
59 }
60
61 function UpdateInternalData_(internal, data) {
62     var values = InternalData_(data);
63
64     for(var key in data) {
65         if (values.hasOwnProperty(key) && internal.hasOwnProperty(key)) {
66             internal[key] = values;
67         }
68     }
69 }
70
71 var LogManager = function() {
72     this.enableLog = true;
73 };
74
75 LogManager.prototype.allow = function() {
76     this.enableLog = true;
77 };
78
79 LogManager.prototype.disallow = function() {
80     this.enableLog = false;
81 };
82
83 var _warningLogs = new LogManager();
84
85 //class AlarmManager ////////////////////////////////////////////////////
86 AlarmManager.prototype.add = function () {
87     var args = AV.validateMethod(arguments, [
88         {
89             name : 'alarm',
90             type : AV.Types.PLATFORM_OBJECT,
91             values : [tizen.AlarmRelative, tizen.AlarmAbsolute]
92         },
93         {
94             name : 'applicationId',
95             type : AV.Types.STRING,
96         },
97         {
98             name : 'appControl',
99             type : AV.Types.PLATFORM_OBJECT,
100             values : tizen.ApplicationControl,
101             optional : true,
102             nullable : true
103         },
104     ]);
105
106     var type = null, seconds = 0;
107     if (args.alarm instanceof tizen.AlarmRelative) {
108         type = 'AlarmRelative';
109     } else if (args.alarm instanceof tizen.AlarmAbsolute) {
110         type = 'AlarmAbsolute';
111         seconds = args.alarm.date.getTime();
112     }
113
114     var callArgs = {};
115     callArgs.alarm = args.alarm;
116     callArgs.applicationId = args.applicationId;
117     if (args.has.appControl) {
118         callArgs.appControl = args.appControl;
119     }
120
121     callArgs.type = type;
122     callArgs.seconds = Converter.toString(seconds);
123     callArgs.isPeriodSet = !T.isNullOrUndefined(args.alarm.period);
124
125     var result = native.callSync('AlarmManager_add', callArgs);
126     if (native.isFailure(result)) {
127         throw native.getErrorObject(result);
128     } else {
129         _edit.allow();
130         UpdateInternalData_(args.alarm, native.getResultObject(result));
131         _edit.disallow();
132     }
133 };
134
135 AlarmManager.prototype.addAlarmNotification = function() {
136     var args = AV.validateMethod(arguments, [
137     {
138         name: 'alarm',
139         type: AV.Types.PLATFORM_OBJECT,
140         values: [tizen.AlarmRelative, tizen.AlarmAbsolute]
141     }, {
142         name: 'notification',
143         type: AV.Types.PLATFORM_OBJECT,
144         values: [tizen.StatusNotification, tizen.UserNotification]
145     }]);
146
147     var type = null, milliseconds = 0;
148     if (args.alarm instanceof tizen.AlarmRelative) {
149         type = 'AlarmRelative';
150     } else if (args.alarm instanceof tizen.AlarmAbsolute) {
151         type = 'AlarmAbsolute';
152         milliseconds = args.alarm.date.getTime();
153     }
154
155     var callArgs = {};
156     callArgs.alarm = args.alarm;
157     callArgs.type = type;
158     callArgs.notification = args.notification;
159     callArgs.milliseconds = Converter.toString(milliseconds);
160     callArgs.isPeriodSet = !T.isNullOrUndefined(args.alarm.period);
161
162     //add marker for UserNotification implementation
163     callArgs.newImpl = (callArgs.notification instanceof tizen.UserNotification);
164
165     var result = native.callSync('AlarmManager_addAlarmNotification', callArgs);
166     if (native.isFailure(result)) {
167         throw native.getErrorObject(result);
168     }
169     else {
170         _edit.allow();
171         UpdateInternalData_(args.alarm, native.getResultObject(result));
172         _edit.disallow();
173     }
174 };
175
176 AlarmManager.prototype.remove = function () {
177     var args = AV.validateMethod(arguments, [
178         {
179             name : 'id',
180             type : AV.Types.STRING,
181         }
182     ]);
183
184     var result = native.callSync('AlarmManager_remove', {id: Number(args.id)});
185
186     if (native.isFailure(result)) {
187         throw native.getErrorObject(result);
188     }
189 };
190
191 AlarmManager.prototype.removeAll = function () {
192     var result = native.callSync('AlarmManager_removeAll', {});
193
194     if (native.isFailure(result)) {
195         throw native.getErrorObject(result);
196     }
197 };
198
199 AlarmManager.prototype.get = function () {
200     var args = AV.validateMethod(arguments, [
201         {
202             name : 'id',
203             type : AV.Types.STRING,
204         }
205     ]);
206
207     var result = native.callSync('AlarmManager_get', {id: Number(args.id)});
208
209     if (native.isFailure(result)) {
210         throw native.getErrorObject(result);
211     } else {
212         result = native.getResultObject(result);
213
214         var alarm;
215         _warningLogs.disallow();
216         if ('AlarmRelative' === result.type) {
217             alarm = new tizen.AlarmRelative(result.delay, result.period, InternalData_(result));
218         } else {
219             var date = new Date(result.year, result.month, result.day,
220                     result.hour, result.min, result.sec);
221
222             alarm = new tizen.AlarmAbsolute(date, result.second, InternalData_(result));
223         }
224         _warningLogs.allow();
225         return alarm;
226     }
227 };
228
229 function _prepareAppControl(noti) {
230   if (!noti || !noti.actions || !noti.actions.appControl) {
231     privUtils_.log("Do nothing - appControl is NOT present");
232     return;
233   }
234   if (!T.isNullOrUndefined(noti.actions.appControl.operation)) {
235     noti.actions.appControl = new tizen.ApplicationControl(
236         noti.actions.appControl.operation,
237         noti.actions.appControl.uri,
238         noti.actions.appControl.mime,
239         noti.actions.appControl.category,
240         noti.actions.appControl.data,
241         noti.actions.appControl.launchMode);
242   }
243 }
244
245 function _prepareDetailInfo(noti) {
246   if (!noti || !noti.textContents || !noti.textContents.detailInfo) {
247     console.log("Do nothing - detailInfo is NOT present");
248     return;
249   }
250   var detailInfo = noti.textContents.detailInfo;
251   if (T.isArray(detailInfo)) {
252     var _d = [];
253     for (var i = 0; i < detailInfo.length; ++i) {
254       _d.push(new tizen.NotificationDetailInfo(detailInfo[i].mainText,
255           detailInfo[i].subText || null));
256     }
257     noti.textContents.detailInfo = _d;
258   }
259 }
260
261 AlarmManager.prototype.getAlarmNotification = function () {
262     var args = AV.validateMethod(arguments, [
263         {
264             name : 'id',
265             type : AV.Types.STRING,
266         }
267     ]);
268
269     var result = native.callSync('AlarmManager_getAlarmNotification', {id: Number(args.id)});
270
271     if (native.isFailure(result)) {
272         throw native.getErrorObject(result);
273     } else {
274         var noti = native.getResultObject(result);
275         _prepareAppControl(noti);
276         _prepareDetailInfo(noti);
277         return new tizen.UserNotification(noti.userType, noti.title, noti);
278     }
279 };
280
281 AlarmManager.prototype.getAll = function () {
282     var result = native.callSync('AlarmManager_getAll', {});
283
284     if (native.isFailure(result)) {
285         throw native.getErrorObject(result);
286     } else {
287         var data = native.getResultObject(result);
288         var md = [];
289         _warningLogs.disallow();
290         data.forEach(function (i) {
291             if ('AlarmRelative'=== i.type) {
292                 md.push(new tizen.AlarmRelative(i.delay, i.period, InternalData_(i)));
293             } else {
294                 var date = new Date(i.year, i.month, i.day,
295                         i.hour, i.min, i.sec);
296                 md.push(new tizen.AlarmAbsolute(date, i.second, InternalData_(i)));
297             }
298         });
299         _warningLogs.allow();
300         return md;
301     }
302 };
303
304 //class Alarm //////////////////////////////////////////////////////////
305 function Alarm(id) {
306     var m_id = null;
307
308     if (!T.isNullOrUndefined(id) && id instanceof InternalData_) {
309         m_id = id.id;
310     }
311
312     var _internal = {
313         'id' : m_id
314     };
315
316     Object.defineProperties(this, {
317         id: {
318             get: function () {return _internal.id;},
319             set: function (value) {
320                 if (value instanceof InternalData_) {
321                     _internal.id = value.id;
322                 }
323             },
324             enumerable: true
325         }
326     });
327 }
328 //class AlarmRelative //////////////////////////////////////////////////
329
330 tizen.AlarmRelative = function(delay, period, internal) {
331     AV.validateConstructorCall(this, tizen.AlarmRelative);
332
333     var m_period = null;
334
335     var m_delay = Converter.toLong(delay);
336
337     if (arguments.length >= 2) {
338         if(!T.isNullOrUndefined(period)){
339             m_period = Converter.toLong(period, true);
340         }
341     }
342
343     Alarm.call(this, internal);
344
345     Object.defineProperties(this, {
346         delay: {
347             get: function() {
348                 return m_delay;
349             },
350             set: function(v) {
351                 if (_edit.canEdit && v) {
352                     m_delay = Converter.toLong(v.delay);
353                 }
354             },
355             enumerable: true
356         },
357         period: {
358             get: function() {
359                 return m_period;
360             },
361             set: function(v) {
362                 if (_edit.canEdit && v) {
363                     m_period = Converter.toLong(v.period);
364                 }
365             },
366             enumerable: true
367         }
368     });
369 };
370
371 tizen.AlarmRelative.prototype = new Alarm();
372
373 tizen.AlarmRelative.prototype.constructor = tizen.AlarmRelative;
374
375 tizen.AlarmRelative.prototype.getRemainingSeconds = function () {
376     var result = native.callSync('AlarmRelative_getRemainingSeconds', {id: Number(this.id)});
377
378     if (native.isFailure(result)) {
379         throw native.getErrorObject(result);
380     } else {
381         return Converter.toLong(native.getResultObject(result).seconds, true);
382     }
383 };
384
385 function makeDateConst(obj) {
386     privUtils_.log('Enter MakeConst');
387     obj.setDate = function() {};
388     obj.setFullYear = function() {};
389     obj.setHours = function() {};
390     obj.setMilliseconds = function() {};
391     obj.setMinutes = function() {};
392     obj.setMonth = function() {};
393     obj.setSeconds = function() {};
394     obj.setTime = function() {};
395     obj.setUTCDate = function() {};
396     obj.setUTCFullYear = function() {};
397     obj.setUTCHours = function() {};
398     obj.setUTCMilliseconds = function() {};
399     obj.setUTCMinutes = function() {};
400     obj.setUTCMonth = function() {};
401     obj.setUTCSeconds = function() {};
402     obj.setYear = function() {};
403     privUtils_.log('Leave MakeConst');
404 }
405
406 //class AlarmAbsolute //////////////////////////////////////////////////
407
408 tizen.AlarmAbsolute = function(date, second, internal) {
409     AV.validateConstructorCall(this, tizen.AlarmAbsolute);
410
411     var m_period = null, m_daysOfWeek = [], m_date;
412
413     if (T.isDate(date)) {
414         m_date = date;
415         if (arguments.length >= 2) {
416             if(T.isArray(second)){
417                 m_daysOfWeek = second;
418             } else {
419                 if(!T.isNullOrUndefined(second)){
420                     m_period = Converter.toLong(second);
421                     if(_warningLogs.enableLog && isAlarmAbsolutePeriodDeprecated){
422                         privUtils_.warn("This Constructor is deprecated since Tizen 4.0." +
423                         " Please consider using other constructors or other type of an alarm.");
424                     }
425                 }
426             }
427         }
428
429         Alarm.call(this, internal);
430     } else {
431         m_period = undefined;
432     }
433     makeDateConst(m_date);
434     Object.defineProperties(this, {
435         date: {
436             get: function() {
437                 return m_date;
438             },
439             set: function(v) {
440                 if (_edit.canEdit && T.isDate(v.date)) {
441                     m_date = v.date;
442                 }
443             },
444             enumerable: true
445         },
446         period: {
447             get: function() {
448                 if(_warningLogs.enableLog && isAlarmAbsolutePeriodDeprecated){
449                     privUtils_.warn('Since Tizen 4.0 constructor AlarmAbsolute(Date date, long period) ' +
450                     'is deprecated, thus period attribute should not be used.');
451                 }
452                 return m_period;
453             },
454             set: function(v) {
455                 if(_warningLogs.enableLog && isAlarmAbsolutePeriodDeprecated){
456                     privUtils_.warn('Since Tizen 4.0 constructor AlarmAbsolute(Date date, long period) ' +
457                     'is deprecated, thus period attribute should not be used.');
458                 }
459
460                 if (_edit.canEdit && v) {
461                     m_period = Converter.toLong(v.period);
462                 }
463             },
464             enumerable: true
465         },
466         daysOfTheWeek: {
467             get: function() {
468                 return m_daysOfWeek;
469             },
470             set: function(v) {
471                 if (_edit.canEdit && T.isArray(v.second)) {
472                     m_daysOfWeek = v.second;
473                 }
474             },
475             enumerable: true
476         }
477     });
478 };
479
480 tizen.AlarmAbsolute.prototype = new Alarm();
481
482 tizen.AlarmAbsolute.prototype.constructor = tizen.AlarmAbsolute;
483
484 tizen.AlarmAbsolute.prototype.getNextScheduledDate = function () {
485     var result = native.callSync('AlarmAbsolute_getNextScheduledDate', {id: Number(this.id)});
486
487     if (native.isFailure(result)) {
488         throw native.getErrorObject(result);
489     } else {
490         var d = native.getResultObject(result);
491         if (T.isNull(d.year)) {
492             return null;
493         } else {
494             var date = new Date(d.year, d.month, d.day, d.hour, d.min, d.sec);
495             return date;
496         }
497     }
498 };
499
500 // Singleton to check on which profile plugins are executed
501 var ProfileAlarm = (function() {
502     var m_profile = null;
503     function ProfileAlarm() {
504        if (m_profile == null) {
505            m_profile = privUtils_.checkProfile();
506        }
507        Object.defineProperties(this, {
508            profile: {
509                get: function() {
510                    return m_profile;
511                },
512                set: function() {},
513                enumerable: true
514            }
515        })
516     };
517
518     var instance;
519     return {
520         getInstance: function() {
521             if (instance == null) {
522                 instance = new ProfileAlarm();
523                 // Hide the constructor so the returned objected can't be new'd...
524                 instance.constructor = null;
525             }
526             return instance;
527         }
528    };
529 })();
530
531 var _profile = ProfileAlarm.getInstance().profile;
532
533 // Notifications feature are available on mobile and wearable profile
534 if (_profile != 'mobile' && _profile != 'wearable') {
535     delete AlarmManager.prototype.addAlarmNotification;
536     delete AlarmManager.prototype.getAlarmNotification;
537     isAlarmAbsolutePeriodDeprecated = false;
538 }
539
540 //exports //////////////////////////////////////////////////////////////
541 exports = new AlarmManager();