31_TradfriDevice.pm 10.0 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269
  1. # @author Peter Kappelt
  2. # @author Clemens Bergmann
  3. # @author Sebastian Kessler
  4. # @version 1.18
  5. package main;
  6. use strict;
  7. use warnings;
  8. use Data::Dumper;
  9. use JSON;
  10. use TradfriUtils;
  11. sub TradfriDevice_Initialize($) {
  12. my ($hash) = @_;
  13. $hash->{DefFn} = 'Tradfri_Define';
  14. $hash->{UndefFn} = 'Tradfri_Undef';
  15. $hash->{SetFn} = 'Tradfri_Set';
  16. $hash->{GetFn} = 'Tradfri_Get';
  17. $hash->{AttrFn} = 'Tradfri_Attr';
  18. $hash->{ReadFn} = 'Tradfri_Read';
  19. $hash->{ParseFn} = 'TradfriDevice_Parse';
  20. $hash->{Match} = '^subscribedDeviceUpdate::';
  21. $hash->{AttrList} =
  22. "usePercentDimming:1,0 "
  23. . $readingFnAttributes;
  24. }
  25. #messages look like this: (without newlines)
  26. # subscribedDeviceUpdate::device-id::{
  27. # "lastSeenAt":1501407261,
  28. # "createdAt":1492280964,
  29. # "reachabilityState":1,
  30. # "name":"Fenster Links",
  31. # "dimvalue":200,
  32. # "type":"TRADFRI bulb E27 opal 1000lm",
  33. # "deviceid":65537,
  34. # "version":"1.1.1.0-5.7.2.0",
  35. # "manufacturer":"IKEA of Sweden",
  36. # "onoff":0
  37. # }
  38. sub TradfriDevice_Parse ($$){
  39. my ($io_hash, $message) = @_;
  40. my @parts = split('::', $message);
  41. if(int(@parts) < 3){
  42. #expecting at least three parts
  43. return undef;
  44. }
  45. my $messageID = $parts[1];
  46. #check if device with the id exists
  47. if(my $hash = $modules{'TradfriDevice'}{defptr}{$messageID})
  48. {
  49. # the path returned "Not Found" -> unknown resource, but this message still suits for this device
  50. if($parts[2] eq "Not Found"){
  51. $hash->{STATE} = "NotFound";
  52. return $hash->{NAME};
  53. }
  54. #parse the JSON data
  55. my $jsonData = eval{ JSON->new->utf8->decode($parts[2]) };
  56. if($@){
  57. return undef; #the string was probably not valid JSON
  58. }
  59. my $manufacturer = $jsonData->{'manufacturer'} || '';
  60. my $type = $jsonData->{'type'} || '';
  61. #dimvalue is in range 0 - 254
  62. my $dimvalue = $jsonData->{'dimvalue'} || '0';
  63. #dimpercent is always in range 0 - 100
  64. my $dimpercent = int($dimvalue / 2.54 + 0.5);
  65. $dimpercent = 1 if($dimvalue == 1);
  66. $dimvalue = $dimpercent if (AttrVal($hash->{NAME}, 'usePercentDimming', 0) == 1);
  67. my $state = 'off';
  68. if($jsonData->{'onoff'} eq '0'){
  69. $dimpercent = 0;
  70. }else{
  71. $state = Tradfri_stateString($dimpercent);
  72. }
  73. my $onoff = ($jsonData->{'onoff'} || '0') ? 'on':'off';
  74. my $name = $jsonData->{'name'} || '';
  75. my $createdAt = FmtDateTimeRFC1123($jsonData->{'createdAt'} || '');
  76. my $reachableState = $jsonData->{'reachabilityState'} || '';
  77. my $lastSeen = FmtDateTimeRFC1123($jsonData->{'lastSeenAt'} || '');
  78. my $color = $jsonData->{'color'} || '';
  79. my $version = $jsonData->{'version'} || '';
  80. readingsBeginUpdate($hash);
  81. readingsBulkUpdateIfChanged($hash, 'dimvalue', $dimvalue, 1);
  82. readingsBulkUpdateIfChanged($hash, 'pct', $dimpercent, 1);
  83. readingsBulkUpdateIfChanged($hash, 'state', $state, 1);
  84. readingsBulkUpdateIfChanged($hash, 'name', $name, 1);
  85. readingsBulkUpdateIfChanged($hash, 'createdAt', $createdAt, 1);
  86. readingsBulkUpdateIfChanged($hash, 'softwareVersion', $version, 1);
  87. readingsBulkUpdateIfChanged($hash, 'type', $type, 1);
  88. readingsBulkUpdateIfChanged($hash, 'manufacturer', $manufacturer, 1);
  89. readingsBulkUpdateIfChanged($hash, 'reachableState', $reachableState, 1);
  90. readingsBulkUpdateIfChanged($hash, 'color', $color, 1);
  91. readingsBulkUpdateIfChanged($hash, 'lastSeen', $lastSeen, 1);
  92. readingsBulkUpdateIfChanged($hash, 'onoff', $onoff, 1);
  93. readingsEndUpdate($hash, 1);
  94. #$attr{$hash->{NAME}}{webCmd} = 'pct:toggle:on:off';
  95. #$attr{$hash->{NAME}}{devStateIcon} = '{(Tradfri_devStateIcon($name),"toggle")}' if( !defined( $attr{$hash->{NAME}}{devStateIcon} ) );
  96. #return the appropriate device's name
  97. return $hash->{NAME};
  98. }
  99. return undef;
  100. }
  101. 1;
  102. =pod
  103. =item device
  104. =item summary controls an IKEA Trådfri device (bulb, panel)
  105. =item summary_DE steuert ein IKEA Trådfri Gerät
  106. =begin html
  107. <a name="TradfriDevice"></a>
  108. <h3>TradfriDevice</h3>
  109. <ul>
  110. <i>TradfriDevice</i> is a module for controlling a single IKEA Trådfri device. You currently need a gateway for the connection.
  111. See TradfriGateway.
  112. <br><br>
  113. <a name="TradfriDevicedefine"></a>
  114. <b>Define</b>
  115. <ul>
  116. <code>define &lt;name&gt; TradfriDevice &lt;device-address&gt;</code>
  117. <br><br>
  118. Example: <code>define trDeviceOne TradfriDevice 65538</code>
  119. <br><br>
  120. You can get the ID of the devices by calling "get TradfriGW deviceList" on the gateway device
  121. </ul>
  122. <br>
  123. <a name="TradfriDeviceset"></a>
  124. <b>Set</b><br>
  125. <ul>
  126. <code>set &lt;name&gt; &lt;option&gt; [&lt;value&gt;]</code>
  127. <br><br>
  128. You can set the following options. See <a href="http://fhem.de/commandref.html#set">commandref#set</a>
  129. for more info about the set command.
  130. <br><br>
  131. Options:
  132. <ul>
  133. <li><i>on</i><br>
  134. Turns the device on.<br>The brightness is the one, before the device was turned off</li>
  135. <li><i>off</i><br>
  136. Turn the device off.</li>
  137. <li><i>dimvalue</i><br>
  138. Set the brightness of the device.<br>
  139. You need to specify the brightness value as an integer between 0 and 100/254.<br>
  140. The largest value depends on the attribute "usePercentDimming".<br>
  141. If this attribute is set, the largest value will be 100.<br>
  142. By default, it isn't set, so the largest value is 254.<br>
  143. A brightness value of 0 turns the device off.<br>
  144. If the device is off, and you set a value greater than 0, it will turn on.</li>
  145. <li><i>color</i>
  146. Set the color temperature of a bubl<br>
  147. Of course, that only works with bulbs, that can change their color temperature<br>
  148. You may pass "warm", "cold", "standard" or a RGB code in the format "RRGGBB"<br>
  149. Any RGB code can be set, though the bulb only is able to switch to certain colors.<br>
  150. IKEA uses the following RGB codes for their colors. Bulbs I've tested could only be set to those.<br>
  151. <ul>
  152. <li>F1E0B5 for standard</li>
  153. <li>F5FAF6 for cold</li>
  154. <li>EFD275 for warm</li>
  155. </ul>
  156. Other RGB codes than listed here do not work with the current bulb (they only set their color to those three values).
  157. </li>
  158. </ul>
  159. </ul>
  160. <br>
  161. <a name="TradfriDeviceget"></a>
  162. <b>Get</b><br>
  163. <ul>
  164. <code>get &lt;name&gt; &lt;option&gt;</code>
  165. <br><br>
  166. You can get the following information about the device. See
  167. <a href="http://fhem.de/commandref.html#get">commandref#get</a> for more info about
  168. the get command.
  169. <br><br>
  170. Options:
  171. <ul>
  172. <li><i></i><br>
  173. There are no gets implemented</li>
  174. </ul>
  175. </ul>
  176. <br>
  177. <a name="TradfriDevicereadings"></a>
  178. <b>Readings</b><br>
  179. <ul>
  180. The following readings are displayed for a device. Once there is a change and the connection to the gateway is made, they get updated automatically.
  181. <br><br>
  182. Readings:
  183. <ul>
  184. <li><i>color</i><br>
  185. The color that is set for this bulb. Its value is a hexadecimal code in the format "RRGGBB".<br>
  186. If the device doesn't support the change of colors the reading's value will be "0"</li>
  187. <li><i>createdAt</i><br>
  188. A timestamp string, like "Sat, 15 Apr 2017 18:29:24 GMT", that indicates, when the device was paired with the gateway.</li>
  189. <li><i>dimvalue</i><br>
  190. The brightness that is set for this device. It is a integer in the range of 0 to 100/ 254.<br>
  191. The greatest dimvalue depends on the attribute "usePercentDimming", see below.</li>
  192. <li><i>pct</i><br>
  193. The brightness that is set for this device in percent.</li>
  194. <li><i>lastSeen</i><br>
  195. A timestamp string, like "Wed, 12 Jul 2017 14:32:06 GMT". I haven't understand the mechanism behind it yet.<br>
  196. Communication with the device won't update the lastSeen-timestamp - so I don't get the point of it. This needs some more investigation.</li>
  197. <li><i>manufacturer</i><br>
  198. The device's manufacturer. Since there are only devices from IKEA available yet, it'll surely be "IKEA of Sweden".</li>
  199. <li><i>name</i><br>
  200. The name of the device that you've set in the app.</li>
  201. <li><i>onoff</i><br>
  202. Indicates whether the device is on or off, can be the strings 'on' or 'off'</li>
  203. <li><i>reachableState</i><br>
  204. Indicates whether the gateway is able to connect to the device. This reading's value is either "0" or "1", where "1" indicates reachability.</li>
  205. <li><i>softwareVersion</i><br>
  206. The version of the software that is running on the device.</li>
  207. <li><i>state</i><br>
  208. Indicates, whether the device is on or off. Thus, the reading's value is either "on" or "off", too.</li>
  209. <li><i>type</i><br>
  210. The product type of the device. Is a string like "TRADFRI bulb E27 opal 1000lm"</li>
  211. </ul>
  212. </ul>
  213. <br>
  214. <a name="TradfriDeviceattr"></a>
  215. <b>Attributes</b>
  216. <ul>
  217. <code>attr &lt;name&gt; &lt;attribute&gt; &lt;value&gt;</code>
  218. <br><br>
  219. See <a href="http://fhem.de/commandref.html#attr">commandref#attr</a> for more info about
  220. the attr command.
  221. <br><br>
  222. Attributes:
  223. <ul>
  224. <li><i>usePercentDimming</i> 0/1<br>
  225. If this attribute is one, the largest value for "set dimvalue" will be 100.<br>
  226. Otherwise, the largest value is 254.<br>
  227. This attribute is useful, if you need to control the brightness in percent (0-100%)<br>
  228. For backward compatibility, it is disabled by default, so the largest dimvalue is 254 by default.
  229. </li>
  230. </ul>
  231. </ul>
  232. </ul>
  233. =end html
  234. =cut