# Virtual and real sensors on 1CH-gateway (ESP)?

**URL:** <https://www.thethingsnetwork.org/forum/t/virtual-and-real-sensors-on-1ch-gateway-esp/21008>\
**Category:** \[obsolete\] SCPF\
**Created:** [December 26, 2018, 7:58pm UTC](https://www.thethingsnetwork.org/forum/t/virtual-and-real-sensors-on-1ch-gateway-esp/21008 "2018-12-26T19:58:38Z")\
**Posts on this page:** 1\
**Showing post:** 11

<div class="post-metadata">

**Author:** ![arjanvanb](https://www.thethingsnetwork.org/forum/user_avatar/www.thethingsnetwork.org/arjanvanb/32/46626_2.png) [@arjanvanb](https://www.thethingsnetwork.org/forum/u/arjanvanb)\
**Post date:** [January 4, 2019, 2:01pm UTC](https://www.thethingsnetwork.org/forum/t/virtual-and-real-sensors-on-1ch-gateway-esp/21008/11 "2019-01-04T14:01:08Z")

</div>

> [@Tix](#):
>
> I still want to advance in the understanding of decoding data

Just as an alternative: without any (fake) sensor you can define a payload function in a (dummy) application in TTN Console, and test that using the input field in TTN Console as well:

 ![image](https://www.thethingsnetwork.org/forum/uploads/default/original/3X/2/d/2d7883d663c818cba041ed3e5c9d148c94d2462e.png)

> **Click to see example decoder used above**
>
> This is discussed in [Nemeus NIS-UL – Ultrasonic sensor](https://www.thethingsnetwork.org/forum/t/nemeus-nis-ul-ultrasonic-sensor/14770/) Not the easiest example… See also [Payload Formats [HowTo] - #3 by arjanvanb](https://www.thethingsnetwork.org/forum/t/is-there-any-documentation-on-payload-functions/3441/3)
> 
> ```javascript
> function Decoder(bytes, port) {
>   
> // See http://wiki.nemeus.fr/index.php?title=NIS-UL_UltraSonic_Sensor#Nemeus_uplink_protocol
> // Test with:
> // 8B 02 0097 0098 1f 19: 151, 152cm; 31, 25°C
> // 8B 02 0097 0098 fe 03: 151, 152cm; -2, 3°C
> // AF 03 0097 0098 0090 0fb9 0e91 0fff fe 03 00 0a: 151, 152, 144cm; 4025, 3729, 4095mV, -2, 3, 0°C
> // 82 00a0: 160cm
> // 88 1e: 30°C
> var usonic_dist = [], voltage = [], internal_temp = [];
> var i = 0, m = 0;
> 
> var mask = bytes[i++];
> 
> // If bit 0 set: 1 byte indicating the number of measurements, else 1
> var nb_meas = mask & 1<<0 ? bytes[i++] : 1;
> 
> // If bit 1 set: distances in centimeters, each 2 bytes unsigned MSB, 1 to 300cm
> if (mask & 1<<1) {
> for (m = 0; m < nb_meas; m++) {
> usonic_dist.push(bytes[i++]<<8 | bytes[i++]);
> }
> }
> 
> // If bit 2 set: voltages in millivolts, each 2 bytes unsigned MSB
> if (mask & 1<<2) {
> for (m = 0; m < nb_meas; m++) {
> voltage.push((bytes[i++]<<8 | bytes[i++]) / 1000);
> }
> }
> 
> // If bit 3 set: internal temperatures, each 1 byte signed integer [-128..+127]
> if (mask & 1<<3) {
> for (m = 0; m < nb_meas; m++) {
> // Sign-extend to 32 bits to support negative values, by shifting 24 bits
> // (too far) to the left, followed by a sign-propagating right shift:
> internal_temp.push(bytes[i++]<<24>>24);
> }
> }
> 
> // Bit 4: reserved
> 
> // If bit 5 set: cause for the measurement, else "periodic measurement"
> var cause = mask & 1<<5 ? bytes[i++] : 1;
> 
> // We should have consumed all bytes, if not then just return the payload as hex
> if (i !== bytes.length) {
> return {
> 'error': 'failed to parse payload',
> 'payload': bytes.map(function(b) {
> return ('0' + b.toString(16).toUpperCase()).substr(-2);
> }).join(' ')
> }
> }
> // Format the results
> var result = {};
> // Show all 8 bits, ensuring leading zeroes
> result.mask = '0b' + ('00000000' + mask.toString(2)).substr(-8);
> 
> result.numberOfMeasurements = nb_meas;
> result.distances = usonic_dist;
> result.voltages = voltage;
> result.temperatures = internal_temp;
> 
> // Same data, grouped by measurement
> result.measurements = [];
> for (m = 0; m < nb_meas; m++) {
> result.measurements.push({
> distance: usonic_dist[m],
> voltage: voltage[m],
> temperature: internal_temp[m]
> });
> }
> 
> result.cause = cause;
> result.causeMask = '0b' + ('00000000' + cause.toString(2)).substr(-8);
> result.causes = [];
> if (cause & 1<<0) {
> result.causes.push('periodic');
> }
> if (cause & 1<<1) {
> result.causes.push('usonic_dist > high threshold');
> }
> if (cause & 1<<2) {
> result.causes.push('usonic_dist < high threshold - high hysteresis');
> }
> if (cause & 1<<3) {
> result.causes.push('usonic_dist < low threshold');
> }
> if (cause & 1<<4) {
> result.causes.push('usonic_dist > low threshold + low hysteresis');
> }
> if (cause & 1<<5) {
> result.causes.push('forced manually');
> }
> 
> return result;
> }
> 
> ```

---

_[View the full topic](https://www.thethingsnetwork.org/forum/t/virtual-and-real-sensors-on-1ch-gateway-esp/21008)._
