b6c24d1f9769aea7782bf69450bd684266b53156
[platform/core/api/webapi-plugins.git] / src / sensor / sensor_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 validator_ = xwalk.utils.validator;
18 var converter_ = xwalk.utils.converter;
19 var types_ = validator_.Types;
20 var T_ = xwalk.utils.type;
21 var native_ = new xwalk.utils.NativeManager(extension);
22
23 // Enums
24 var SensorType = {
25     LIGHT : 'LIGHT',
26     MAGNETIC : 'MAGNETIC',
27     PRESSURE : 'PRESSURE',
28     PROXIMITY : 'PROXIMITY',
29     ULTRAVIOLET : 'ULTRAVIOLET',
30     HRM_RAW : 'HRM_RAW',
31 };
32
33 var ProximityState = {
34     FAR : 'FAR',
35     NEAR : 'NEAR'
36 };
37
38 var MagneticSensorAccuracy = {
39     UNDEFINED : 'ACCURACY_UNDEFINED',
40     BAD : 'ACCURACY_BAD',
41     NORMAL : 'ACCURACY_NORMAL',
42     GOOD : 'ACCURACY_GOOD',
43     VERYGOOD : 'ACCURACY_VERYGOOD'
44 };
45
46 // helper class for sensor listeners
47 var SensorListener = function (type, constructor) {
48     this.sensorType = type;
49     this.isStarted = false;
50     this.callback = undefined;
51     this.constructor = constructor;
52 };
53
54 SensorListener.prototype.tryCall = function (object) {
55     if (this.callback) {
56         this.callback(new this.constructor(object));
57     }
58 };
59
60 SensorListener.prototype.start = function (successCallback, errorCallback) {
61     if (!this.isStarted) {
62         // sensor not started
63         var thisObject = this;
64         native_.call('Sensor_start', {'sensorType' : thisObject.sensorType},
65                 function(result) {
66                     if (native_.isFailure(result)) {
67                         if(!T_.isNullOrUndefined(errorCallback)) {
68                             errorCallback(native_.getErrorObject(result));
69                         }
70                     } else {
71                         thisObject.isStarted = true;
72                         successCallback();
73                     }
74                 }
75         );
76     } else {
77         // sensor is already started - just call success callback
78         setTimeout(function(){successCallback()}, 0);
79     }
80 };
81
82 SensorListener.prototype.stop = function () {
83     if (this.isStarted) {
84         var result = native_.callSync('Sensor_stop', {'sensorType' : this.sensorType});
85         if (native_.isFailure(result)) {
86             throw native_.getErrorObject(result);
87         }
88         this.isStarted = false;
89     }
90 };
91
92 SensorListener.prototype.setListener = function (successCallback) {
93     if (!this.callback) {
94         //call platform only if there was no listener registered
95         var result = native_.callSync('Sensor_setChangeListener', {'sensorType' : this.sensorType});
96         if (native_.isFailure(result)) {
97             throw native_.getErrorObject(result);
98         }
99     }
100     this.callback = successCallback;
101 };
102
103 SensorListener.prototype.unsetListener = function () {
104     if (this.callback) {
105         //unregister in platform only if there is callback registered
106         this.callback = undefined;
107         var result = native_.callSync('Sensor_unsetChangeListener', {'sensorType' : this.sensorType});
108         if (native_.isFailure(result)) {
109             throw native_.getErrorObject(result);
110         }
111     }
112 };
113
114 SensorListener.prototype.getData = function (successCallback, errorCallback) {
115     var thisObj = this;
116     if (!thisObj.isStarted) {
117         setTimeout(function() {
118             if (!T_.isNullOrUndefined(errorCallback)) {
119                 errorCallback(new WebAPIException(
120                         WebAPIException.SERVICE_NOT_AVAILABLE_ERR,
121                         'Service is not available.'));
122             }
123         }, 0);
124     } else {
125         native_.call('Sensor_getData', { type : thisObj.sensorType },
126                 function(result) {
127             if (native_.isFailure(result)) {
128                 if(!T_.isNullOrUndefined(errorCallback)) {
129                     errorCallback(native_.getErrorObject(result));
130                 }
131             } else {
132                 successCallback(new thisObj.constructor(result));
133             }
134         });
135     }
136 };
137
138 var _supportedSensors = [];
139 var _isChecked = false;
140 var _sensorListeners = {
141     'LIGHT'       : {},
142     'MAGNETIC'    : {},
143     'PRESSURE'    : {},
144     'PROXIMITY'   : {},
145     'ULTRAVIOLET' : {},
146     'HRM_RAW'     : {},
147 };
148
149 var _listener = function(object) {
150     _sensorListeners[object.sensorType].tryCall(object);
151 };
152
153 var SENSOR_CHANGED_LISTENER = 'SensorChangedListener';
154 native_.addListener(SENSOR_CHANGED_LISTENER, _listener);
155
156 function getAvailableSensors() {
157     var result = native_.callSync('SensorService_getAvailableSensors', {});
158     if (native_.isFailure(result)) {
159         throw native_.getErrorObject(result);
160     }
161     _supportedSensors = native_.getResultObject(result);
162     _isChecked = true;
163 }
164
165 function SensorService() {
166 };
167
168 SensorService.prototype.getDefaultSensor = function() {
169     var args = validator_.validateArgs(arguments, [
170         {
171             name : 'type',
172             type : types_.ENUM,
173             values : T_.getValues(SensorType)
174         }
175     ]);
176
177     if (!_isChecked) {
178         getAvailableSensors();
179     }
180
181     var index = _supportedSensors.indexOf(args.type);
182     if (index === -1) {
183         throw new WebAPIException(WebAPIException.NOT_SUPPORTED_ERR, 'Not supported.');
184     } else if (_supportedSensors[index] === SensorType.LIGHT) {
185         return new LightSensor();
186     } else if (_supportedSensors[index] === SensorType.MAGNETIC) {
187         return new MagneticSensor();
188     } else if (_supportedSensors[index] === SensorType.PRESSURE) {
189         return new PressureSensor();
190     } else if (_supportedSensors[index] === SensorType.PROXIMITY) {
191         return new ProximitySensor();
192     } else if (_supportedSensors[index] === SensorType.ULTRAVIOLET) {
193         return new UltravioletSensor();
194     } else if (_supportedSensors[index] === SensorType.HRM_RAW) {
195         xwalk.utils.checkPrivilegeAccess(xwalk.utils.privilege.HEALTHINFO);
196         return new HRMRawSensor();
197     }
198 };
199
200 SensorService.prototype.getAvailableSensors = function() {
201     if (!_isChecked) {
202         getAvailableSensors();
203     }
204
205     return _supportedSensors.slice();
206 };
207
208 //////////////////////Sensor classes//////////////////////////////////////////////////////////
209 //// Base Sensor class
210 var Sensor = function (type) {
211     Object.defineProperties(this, {
212         sensorType : {value: type, writable: false, enumerable: true}
213     });
214 };
215
216 Sensor.prototype.start = function() {
217     var args = validator_.validateArgs(arguments, [
218        {
219            name : 'successCallback',
220            type : types_.FUNCTION
221        },
222        {
223            name : 'errorCallback',
224            type : types_.FUNCTION,
225            optional : true,
226            nullable : true
227        }
228     ]);
229
230     _sensorListeners[this.sensorType].start(args.successCallback, args.errorCallback);
231 };
232
233 Sensor.prototype.stop = function() {
234     _sensorListeners[this.sensorType].stop();
235 };
236
237 Sensor.prototype.setChangeListener = function() {
238     var args = validator_.validateArgs(arguments, [
239        {
240            name : 'successCallback',
241            type: types_.FUNCTION
242        }
243     ]);
244
245     _sensorListeners[this.sensorType].setListener(args.successCallback);
246 };
247
248 Sensor.prototype.unsetChangeListener = function() {
249     _sensorListeners[this.sensorType].unsetListener();
250 };
251
252 //// LightSensor
253 var LightSensor = function(data) {
254     Sensor.call(this, SensorType.LIGHT);
255 };
256
257 LightSensor.prototype = new Sensor();
258
259 LightSensor.prototype.constructor = Sensor;
260
261 LightSensor.prototype.getLightSensorData = function() {
262     var args = validator_.validateArgs(arguments, [
263        {
264            name : 'successCallback',
265            type : types_.FUNCTION
266        },
267        {
268            name : 'errorCallback',
269            type : types_.FUNCTION,
270            optional : true,
271            nullable : true
272        }
273     ]);
274
275     _sensorListeners[this.sensorType].getData(args.successCallback, args.errorCallback);
276 };
277
278 //// MagneticSensor
279 var MagneticSensor = function(data) {
280     Sensor.call(this, SensorType.MAGNETIC);
281 };
282
283 MagneticSensor.prototype = new Sensor();
284
285 MagneticSensor.prototype.constructor = Sensor;
286
287 MagneticSensor.prototype.getMagneticSensorData = function() {
288     var args = validator_.validateArgs(arguments, [
289        {
290            name : 'successCallback',
291            type : types_.FUNCTION
292        },
293        {
294            name : 'errorCallback',
295            type : types_.FUNCTION,
296            optional : true,
297            nullable : true
298        }
299     ]);
300
301     _sensorListeners[this.sensorType].getData(args.successCallback, args.errorCallback);
302 };
303
304 //// PressureSensor
305 var PressureSensor = function(data) {
306     Sensor.call(this, SensorType.PRESSURE);
307 };
308
309 PressureSensor.prototype = new Sensor();
310
311 PressureSensor.prototype.constructor = Sensor;
312
313 PressureSensor.prototype.getPressureSensorData = function() {
314     var args = validator_.validateArgs(arguments, [
315        {
316            name : 'successCallback',
317            type : types_.FUNCTION
318        },
319        {
320            name : 'errorCallback',
321            type : types_.FUNCTION,
322            optional : true,
323            nullable : true
324        }
325     ]);
326
327     _sensorListeners[this.sensorType].getData(args.successCallback, args.errorCallback);
328 };
329
330 //// ProximitySensor
331 var ProximitySensor = function(data) {
332     Sensor.call(this, SensorType.PROXIMITY);
333 };
334
335 ProximitySensor.prototype = new Sensor();
336
337 ProximitySensor.prototype.constructor = Sensor;
338
339 ProximitySensor.prototype.getProximitySensorData = function() {
340     var args = validator_.validateArgs(arguments, [
341        {
342            name : 'successCallback',
343            type : types_.FUNCTION
344        },
345        {
346            name : 'errorCallback',
347            type : types_.FUNCTION,
348            optional : true,
349            nullable : true
350        }
351     ]);
352
353     _sensorListeners[this.sensorType].getData(args.successCallback, args.errorCallback);
354 };
355
356 //// UltravioletSensor
357 var UltravioletSensor = function(data) {
358     Sensor.call(this, SensorType.ULTRAVIOLET);
359 };
360
361 UltravioletSensor.prototype = new Sensor();
362
363 UltravioletSensor.prototype.constructor = Sensor;
364
365 UltravioletSensor.prototype.getUltravioletSensorData = function() {
366     var args = validator_.validateArgs(arguments, [
367        {
368            name : 'successCallback',
369            type : types_.FUNCTION
370        },
371        {
372            name : 'errorCallback',
373            type : types_.FUNCTION,
374            optional : true,
375            nullable : true
376        }
377     ]);
378
379     _sensorListeners[this.sensorType].getData(args.successCallback, args.errorCallback);
380 };
381
382 ////HRMRawSensor
383 var HRMRawSensor = function(data) {
384     Sensor.call(this, SensorType.HRM_RAW);
385 };
386
387 HRMRawSensor.prototype = new Sensor();
388
389 HRMRawSensor.prototype.constructor = Sensor;
390
391 HRMRawSensor.prototype.getHRMRawSensorData = function() {
392     var args = validator_.validateArgs(arguments, [
393        {
394            name : 'successCallback',
395            type : types_.FUNCTION
396        },
397        {
398            name : 'errorCallback',
399            type : types_.FUNCTION,
400            optional : true,
401            nullable : true
402        }
403     ]);
404
405     xwalk.utils.checkPrivilegeAccess(xwalk.utils.privilege.HEALTHINFO);
406
407     _sensorListeners[this.sensorType].getData(args.successCallback, args.errorCallback);
408 };
409
410 ////////////////////// Sensor Data classes/////////////////////////////////////////////////////
411 ////Base SensorData class
412 var SensorData = function () {
413 };
414
415 //// SensorLightData
416 var SensorLightData = function(data) {
417     SensorData.call(this);
418     Object.defineProperties(this, {
419         lightLevel : {value: data.lightLevel, writable: false, enumerable: true}
420     });
421 };
422
423 SensorLightData.prototype = new SensorData();
424
425 SensorLightData.prototype.constructor = SensorData;
426
427 _sensorListeners[SensorType.LIGHT] = new SensorListener(SensorType.LIGHT,
428         SensorLightData);
429
430 //// SensorMagneticData
431 var SensorMagneticData = function(data) {
432     SensorData.call(this);
433     Object.defineProperties(this, {
434         x : {value: data.x, writable: false, enumerable: true},
435         y : {value: data.y, writable: false, enumerable: true},
436         z : {value: data.z, writable: false, enumerable: true},
437         accuracy : {value: data.accuracy, writable: false, enumerable: true}
438     });
439 };
440
441 SensorMagneticData.prototype = new SensorData();
442
443 SensorMagneticData.prototype.constructor = SensorData;
444
445 _sensorListeners[SensorType.MAGNETIC] = new SensorListener(SensorType.MAGNETIC,
446         SensorMagneticData);
447
448 //// SensorPressureData
449 var SensorPressureData = function(data) {
450     SensorData.call(this);
451     Object.defineProperties(this, {
452         pressure : {value: data.pressure, writable: false, enumerable: true}
453     });
454 };
455
456 SensorPressureData.prototype = new SensorData();
457
458 SensorPressureData.prototype.constructor = SensorData;
459
460 _sensorListeners[SensorType.PRESSURE] = new SensorListener(SensorType.PRESSURE,
461         SensorPressureData);
462
463 //// SensorProximityData
464 var SensorProximityData = function(data) {
465     SensorData.call(this);
466     Object.defineProperties(this, {
467         proximityState : {value: data.proximityState, writable: false, enumerable: true}
468     });
469 };
470
471 SensorProximityData.prototype = new SensorData();
472
473 SensorProximityData.prototype.constructor = SensorData;
474
475 _sensorListeners[SensorType.PROXIMITY] = new SensorListener(SensorType.PROXIMITY,
476         SensorProximityData);
477
478 //// SensorUltravioletData
479 var SensorUltravioletData = function(data) {
480     SensorData.call(this);
481     Object.defineProperties(this, {
482         ultravioletLevel : {value: data.ultravioletLevel, writable: false, enumerable: true}
483     });
484 };
485
486
487 SensorUltravioletData.prototype = new SensorData();
488
489 SensorUltravioletData.prototype.constructor = SensorData;
490
491 _sensorListeners[SensorType.ULTRAVIOLET] = new SensorListener(SensorType.ULTRAVIOLET,
492         SensorUltravioletData);
493
494 ////SensorHRMRawData
495 var SensorHRMRawData = function(data) {
496     SensorData.call(this);
497     Object.defineProperties(this, {
498         lightType : {value: data.lightType, writable: false, enumerable: true},
499         lightIntensity : {value: data.lightIntensity, writable: false, enumerable: true}
500     });
501 };
502
503
504 SensorHRMRawData.prototype = new SensorData();
505
506 SensorHRMRawData.prototype.constructor = SensorData;
507
508 _sensorListeners[SensorType.HRM_RAW] = new SensorListener(SensorType.HRM_RAW,
509         SensorHRMRawData);
510
511 // Exports
512 exports = new SensorService();