﻿<?xml version="1.0" encoding="UTF-8"?><rss version="2.0"
	xmlns:content="http://purl.org/rss/1.0/modules/content/"
	xmlns:wfw="http://wellformedweb.org/CommentAPI/"
	xmlns:dc="http://purl.org/dc/elements/1.1/"
	xmlns:atom="http://www.w3.org/2005/Atom"
	xmlns:sy="http://purl.org/rss/1.0/modules/syndication/"
	xmlns:slash="http://purl.org/rss/1.0/modules/slash/"
	>

<channel>
	<title>Tag C# - Constellation</title>
	<atom:link href="https://developer.myconstellation.io/tag/c/feed/" rel="self" type="application/rss+xml" />
	<link>https://developer.myconstellation.io/tag/c/</link>
	<description>Votre plateforme d&#039;interconnexion</description>
	<lastBuildDate>Thu, 19 Apr 2018 05:06:39 +0000</lastBuildDate>
	<language>fr-FR</language>
	<sy:updatePeriod>
	hourly	</sy:updatePeriod>
	<sy:updateFrequency>
	1	</sy:updateFrequency>
	<generator>https://wordpress.org/?v=6.0.11</generator>

<image>
	<url>https://developer.myconstellation.io/wp-content/uploads/2016/02/256x256-e1457476015859.png</url>
	<title>Tag C# - Constellation</title>
	<link>https://developer.myconstellation.io/tag/c/</link>
	<width>32</width>
	<height>32</height>
</image> 
	<item>
		<title>Créer une prise connectée avec un ESP8266</title>
		<link>https://developer.myconstellation.io/tutorials/creer-une-prise-connectee-avec-un-esp8266/</link>
					<comments>https://developer.myconstellation.io/tutorials/creer-une-prise-connectee-avec-un-esp8266/#respond</comments>
		
		<dc:creator><![CDATA[Lucas]]></dc:creator>
		<pubDate>Tue, 31 Oct 2017 11:29:46 +0000</pubDate>
				<category><![CDATA[Tutoriels]]></category>
		<category><![CDATA[Relais]]></category>
		<category><![CDATA[XBMC]]></category>
		<category><![CDATA[Kodi]]></category>
		<category><![CDATA[C#]]></category>
		<category><![CDATA[MessageCallback]]></category>
		<category><![CDATA[Switch]]></category>
		<category><![CDATA[StateObjectLink]]></category>
		<category><![CDATA[Arduino]]></category>
		<category><![CDATA[ESP8266]]></category>
		<category><![CDATA[ESP]]></category>
		<category><![CDATA[Domotique]]></category>
		<guid isPermaLink="false">https://developer.myconstellation.io/?p=5668</guid>

					<description><![CDATA[<p>Par Lucas Dupuis La prise connectée est un élément phare de la domotique de la maison. Il permet d&#8217;allumer ou d&#8217;éteindre un équipement branché dessus ou encore de connaitre sa consommation en énergie. Dans mon cas, j&#8217;avais besoin d&#8217;allumer ou</p>
<p>The post <a rel="nofollow" href="https://developer.myconstellation.io/tutorials/creer-une-prise-connectee-avec-un-esp8266/">Créer une prise connectée avec un ESP8266</a> appeared first on <a rel="nofollow" href="https://developer.myconstellation.io">Constellation</a>.</p>
]]></description>
										<content:encoded><![CDATA[<p><em>Par Lucas Dupuis</em></p>
<p>La prise connectée est un élément phare de la domotique de la maison. Il permet d&rsquo;allumer ou d&rsquo;éteindre un équipement branché dessus ou encore de connaitre sa consommation en énergie. Dans mon cas, j&rsquo;avais besoin d&rsquo;allumer ou d&rsquo;éteindre les enceintes de mon média center automatiquement lorsque ce dernier était démarré.</p>
<p align="center"><a href="https://developer.myconstellation.io/wp-content/uploads/2017/10/2016-08-08-16.32.30.jpg"><img class="colorbox-5668"  loading="lazy" style="background-image: none; padding-top: 0px; padding-left: 0px; display: inline; padding-right: 0px; border-width: 0px;" title="Prise connectée" src="https://developer.myconstellation.io/wp-content/uploads/2017/10/2016-08-08-16.32.30_thumb.jpg" alt="Prise connectée" width="404" height="304" border="0" /></a></p>
<p align="left">Découvrons ensemble comment créer sa prise connectée avec un ESP8266.</p>
<p><span id="more-5668"></span></p>
<h2>Prérequis</h2>
<p>Pour ce tutoriel, il vous faut :</p>
<ul>
<li>Un bloc prise avec un interrupteur</li>
<li>Un transformateur AC/DC 5v</li>
<li>Un ESP-01 (ESP8266)</li>
<li>Un régulateur de tension 3.3v</li>
<li>Un relais 220V pilotable en 5v</li>
<li>Un transistor, des résistances, des leds, une diode, des condensateurs</li>
<li>Du fil électrique</li>
<li>Un pistolet à colle et une drémel</li>
<li>Un serveur Constellation</li>
</ul>
<h2>Etape 1 : Construire la prise</h2>
<p>Dans un premier temps, il nous faut un boitier abordable que nous pourrons ouvrir pour insérer notre ESP à l&rsquo;intérieur. Après quelques recherches, j&rsquo;ai opté pour le <a href="http://www.conrad.fr/ce/fr/product/778994/Prise-intermdiaire-commutable-Renkforce-778994-1-ple-argent">boitier Renkforce disponible chez Conrad</a> pour 3€ environ.</p>
<p>On commence donc par l’ouvrir pour la vider littéralement :</p>
<p align="center"><a href="https://developer.myconstellation.io/wp-content/uploads/2017/10/2016-11-10-22.38.32.jpg"><img class="colorbox-5668"  loading="lazy" style="background-image: none; padding-top: 0px; padding-left: 0px; display: inline; padding-right: 0px; border-width: 0px;" title="Prise Renkforce" src="https://developer.myconstellation.io/wp-content/uploads/2017/10/2016-11-10-22.38.20_thumb.jpg" alt="Prise Renkforce" width="204" height="271" border="0" /><img class="colorbox-5668"  loading="lazy" style="background-image: none; padding-top: 0px; padding-left: 0px; display: inline; padding-right: 0px; border-width: 0px;" title="Prise Renkforce" src="https://developer.myconstellation.io/wp-content/uploads/2017/10/2016-11-10-22.38.32_thumb.jpg" alt="Prise Renkforce" width="204" height="271" border="0" /></a></p>
<p align="center"><img class="colorbox-5668"  loading="lazy" style="background-image: none; padding-top: 0px; padding-left: 0px; display: inline; padding-right: 0px; border-width: 0px;" title="Démontage" src="https://developer.myconstellation.io/wp-content/uploads/2017/10/2016-11-10-22.41.28_thumb.jpg" alt="Démontage" width="244" height="184" border="0" /><a href="https://developer.myconstellation.io/wp-content/uploads/2017/10/2016-11-10-22.41.28.jpg"><img class="colorbox-5668"  loading="lazy" style="background-image: none; padding-top: 0px; padding-left: 0px; display: inline; padding-right: 0px; border-width: 0px;" title="Prise démontée" src="https://developer.myconstellation.io/wp-content/uploads/2017/10/2016-11-10-22.44.15_thumb.jpg" alt="Prise démontée" width="244" height="184" border="0" /></a></p>
<p>Puis tous les supports plastique à l&rsquo;intérieur doivent être cassés pour libérer un maximum de place. Je les ai cassés avec une pince coupante et j&rsquo;ai fini de retirer le maximum de plastique avec un dremel. Sur cette photo j&rsquo;avais retiré une partie du fond de la prise pour un autre projet.</p>
<p align="center"><a href="https://developer.myconstellation.io/wp-content/uploads/2017/10/2016-12-18-11.25.15.jpg"><img class="colorbox-5668"  loading="lazy" style="background-image: none; padding-top: 0px; padding-left: 0px; display: inline; padding-right: 0px; border-width: 0px;" title="Usinage" src="https://developer.myconstellation.io/wp-content/uploads/2017/10/2016-12-18-11.25.15_thumb.jpg" alt="Usinage" width="354" height="266" border="0" /></a></p>
<p>Il faut ensuite préparer un câblage avec le relais pour qu&rsquo;il s&rsquo;intercale entre l&rsquo;arrivée de la phase (mur) et la phase distribuée à l&rsquo;élément branché sur la prise. Mais il faut également garder en tête que l&rsquo;alimentation de l&rsquo;ESP doit être permanente :</p>
<p align="center"><a href="https://developer.myconstellation.io/wp-content/uploads/2017/10/2016-08-10-22.52.19.jpg"><img class="colorbox-5668"  loading="lazy" style="background-image: none; padding-top: 0px; padding-left: 0px; display: inline; padding-right: 0px; border-width: 0px;" title="Schéma" src="https://developer.myconstellation.io/wp-content/uploads/2017/10/2016-08-10-22.52.19_thumb.jpg" alt="Schéma" width="354" height="266" border="0" /></a></p>
<p align="center"><a href="https://developer.myconstellation.io/wp-content/uploads/2017/10/Schma-relais.png"><img class="colorbox-5668"  loading="lazy" style="background-image: none; padding-top: 0px; padding-left: 0px; display: inline; padding-right: 0px; border-width: 0px;" title="Schéma" src="https://developer.myconstellation.io/wp-content/uploads/2017/10/Schma-relais_thumb.png" alt="Schéma" width="350" height="321" border="0" /></a></p>
<p>Mon principal problème dans ce tutoriel a été de tout faire rentrer dans la prise. En effet, l&rsquo;alimentation + le relais prennent beaucoup de place et tout est rentré au chausse-pied, avec le câblage noyé dans la colle chaude afin d&rsquo;assurer l&rsquo;isolation.</p>
<p>Le transformateur alimente donc en 5v un régulateur de tension LM1117 3.3V avec deux condensateurs pour lisser du 3.3v pour l&rsquo;ESP01.</p>
<p>Il alimente également directement la bobine du relais dont le circuit est interrompu par un transistor NPN BC547 dont la base sera pilotée en saturation par un GPIO de l&rsquo;ESP.</p>
<p>L&rsquo;ESP pilote deux leds de statut : une rouge et une verte et possède également son dernier GPIO en input pour un bouton physique placé sur le dessus du boitier. Si vous avez suivi jusque-là et que vous connaissez l&rsquo;ESP01, vous aurez compris qu&rsquo;il est impossible de le programmer directement dans la prise, deux des 4 GPIO devant normalement être utilisés pour la communication série.</p>
<p align="center"><a href="https://developer.myconstellation.io/wp-content/uploads/2017/10/2016-08-07-16.00.46.jpg"><img class="colorbox-5668"  loading="lazy" style="background-image: none; padding-top: 0px; padding-left: 0px; display: inline; padding-right: 0px; border-width: 0px;" title="2016-08-07 16.00.46" src="https://developer.myconstellation.io/wp-content/uploads/2017/10/2016-08-07-16.00.46_thumb.jpg" alt="2016-08-07 16.00.46" width="454" height="342" border="0" /></a></p>
<p>Pour combler le « trou » du bouton physique original, j&rsquo;ai choisi de coller par l&rsquo;intérieur du boitier un petit bout de plexiglas translucide. Je l&rsquo;ai ensuite percé pour faire passer les deux leds rouge et verte.</p>
<p align="center"><a href="https://developer.myconstellation.io/wp-content/uploads/2017/10/2016-12-18-18.27.32.jpg"><img class="colorbox-5668"  loading="lazy" style="background-image: none; padding-top: 0px; padding-left: 0px; display: inline; padding-right: 0px; border-width: 0px;" title="2016-12-18 18.27.32" src="https://developer.myconstellation.io/wp-content/uploads/2017/10/2016-12-18-18.27.32_thumb.jpg" alt="2016-12-18 18.27.32" width="244" height="184" border="0" /></a><a href="https://developer.myconstellation.io/wp-content/uploads/2017/10/2016-08-22-23.08.43.jpg"><img class="colorbox-5668"  loading="lazy" style="background-image: none; padding-top: 0px; padding-left: 0px; display: inline; padding-right: 0px; border-width: 0px;" title="2016-08-22 23.08.43" src="https://developer.myconstellation.io/wp-content/uploads/2017/10/2016-08-22-23.08.43_thumb.jpg" alt="2016-08-22 23.08.43" width="244" height="184" border="0" /></a></p>
<p align="left">Et voilà, on obtient une prise connectée par Wifi avec un ESP8266 avec un bouton poussoir et deux LEDs, reste plus qu’à le programmer !</p>
<h2>Etape 2 : la programmation</h2>
<p>La fonction de base de la prise est assez simple : couper le courant ou le laisser passer. Dans un premier temps, j&rsquo;ai uploadé un sketch de base Constellation avec Arduino sur l&rsquo;ESP01 à l&rsquo;extérieur de la prise. Je l&rsquo;ai ensuite branché dans la prise que j&rsquo;ai enfiché dans le mur. Bazinga, le régulateur 3.3v fait son job, l&rsquo;ESP boote, se connecte à mon réseau wifi et envoie un « hello world » dans la console Constellation. Pour découvrir comment connecter un ESP8266 à Constellation, <a href="https://developer.myconstellation.io/getting-started/connecter-un-arduino-ou-un-esp8266-constellation/">suivez ce guide</a>.</p>
<p>Ensuite, j&rsquo;ai utilisé la librairie Constellation <a href="https://developer.myconstellation.io/client-api/arduino-esp-api/recevoir-des-messages-et-exposer-des-methodes-messagecallback-sur-arduino-esp/">pour ajouter un MessageCallback</a> pour activer ou désactiver le GPIO de la prise, <a href="https://developer.myconstellation.io/client-api/arduino-esp-api/produire-des-stateobjects-depuis-arduino-esp/">couplé à un StateObject</a> pour maintenir l’état de la prise dans Constellation :</p>
<p></p><pre class="crayon-plain-tag">constellation.registerMessageCallback("Switch", MessageCallbackDescriptor().setDescription("Switch le statut du relais."),
  [](JsonObject &amp; json) {
    statutRelais = !statutRelais;
    digitalWrite(gpioRelais, statutRelais);
    constellation.pushStateObject("Status", stringFormat("{ 'IsActivated':%s }", statutRelais ? "true" : "false" ));
  });</pre><p></p>
<p align="left">Ainsi Constellation a toujours connaissance de l’état de la prise via le StateObject nommé “Status” :</p>
<p align="center"><a href="https://developer.myconstellation.io/wp-content/uploads/2017/10/StateObject.png"><img class="colorbox-5668"  loading="lazy" style="background-image: none; padding-top: 0px; padding-left: 0px; display: inline; padding-right: 0px; border-width: 0px;" title="StateObject de l'état de la prise" src="https://developer.myconstellation.io/wp-content/uploads/2017/10/StateObject_thumb.png" alt="StateObject de l'état de la prise" width="354" height="259" border="0" /></a></p>
<p align="left">Et tout le monde peut maintenant découvrir et utiliser le MessageCallback “Switch” exposé par notre ESP pour permuter l’état de notre prise :</p>
<p align="center"><a href="https://developer.myconstellation.io/wp-content/uploads/2017/10/MessageCallback2-002.png"><img class="colorbox-5668"  loading="lazy" style="background-image: none; padding-top: 0px; padding-left: 0px; display: inline; padding-right: 0px; border: 0px;" title="MessageCallback" src="https://developer.myconstellation.io/wp-content/uploads/2017/10/MessageCallback2-002_thumb.png" alt="MessageCallback" width="354" height="115" border="0" /></a></p>
<p align="left">Bingo, on a donc une prise 220V connectée à Constellation qu’on pourra piloter depuis une page Web, un programme Python ou autre.</p>
<p align="left">Pour vous donnez quelques idées, n’hésitez pas à relire ce tutoriel : <a href="https://developer.myconstellation.io/tutorials/creer-un-relais-connecte/">Créer un relais connecté</a>.</p>
<h2 align="left">Etape 3 : Lier sa prise connectée à l’état de son média-center</h2>
<p align="left">Dans ma Constellation, je dispose d&rsquo;un package « brain » développé en C# avec Visual Studio qui contient l’ensemble des règles de la maison (gestion du chauffages, lumières, volets, etc..).</p>
<p align="left">Je l’ai enrichi pour faire en sorte que si Kodi est en train de lire un média (audio ou vidéo) et que la prise n’est pas allumée, alors il invoque le MessageCallback pour allumer la prise. Et inversement pour l&rsquo;éteindre !</p>
<p align="left">J’ai donc dans une classe C#, ajouté <a href="https://developer.myconstellation.io/client-api/net-package-api/consommer-des-stateobjects/#Les_StateObjectLink">deux StateObjectLinks</a>, c’est à dire que j’ai deux propriétés de mon code C# qui sont liées à mes StateObjets représentant l’état de mon media-center de l’état de ma prise !</p>
<p align="left">Il me reste plus qu’à ajouter un handler sur le changement d’état du State Object de Kodi, afin d’ajouter deux conditions “if” :</p>
<ul>
<li>
<div align="left">Si la prise est éteinte alors que Kodi joue quelque chose (PlayerState différent de null) alors on allume la prise</div>
</li>
<li>
<div align="left">Si la prise est allumée alors que Kodi joue rien (PlayerState null) alors on éteint la prise</div>
</li>
</ul>
<p align="left">Pour allumer ou éteindre la prise, il suffit d’invoquer le MessageCallback “Switch” exposé par notre code Arduino <a href="https://developer.myconstellation.io/client-api/net-package-api/envoyer-des-messages-invoquer-des-messagecallbacks/">en créant un proxy vers notre package.</a></p>
<p></p><pre class="crayon-plain-tag">public class KodiDemo
{
    /// &lt;summary&gt;
    /// StateObject XBMC. Permet de connaitre les infos de lecture.
    /// &lt;/summary&gt;
    [StateObjectLink(Package = "Xbmc", Name = "Kodi Salon NUC")]
    public StateObjectNotifier KodiNotifier { get; set; }

    /// &lt;summary&gt;
    /// StateObject de l'ESP controlant le relais d'activation. Permet de synchroniser les infos de lecture avec la valeur du relais.
    /// &lt;/summary&gt;
    [StateObjectLink(Sentinel = "ESP8266-01-001", Package = "ESP_Relay_Button", Name = "Status")]
    public StateObjectNotifier PriseKodi { get; set; }

    public void Start()
    {
        this.KodiNotifier.ValueChanged += (s, e) =&gt;
        {
            if (this.PriseKodi.DynamicValue.Status == false
                &amp;&amp; e.IsNew == false
                &amp;&amp; e.OldState.DynamicValue.PlayerState == null
                &amp;&amp; e.NewState.DynamicValue.PlayerState != null)
            {
                // démarrage.
                PackageHost.WriteInfo("Activation de la prise.");
                PackageHost.CreateMessageProxy("ESP8266_01_002/ESP_Relay_Button").Switch();
            }

            if (this.PriseKodi.DynamicValue.Status == true
                &amp;&amp; e.IsNew == false
                &amp;&amp; e.OldState.DynamicValue.PlayerState != null
                &amp;&amp; e.NewState.DynamicValue.PlayerState == null)
            {
                PackageHost.WriteInfo($"Arret de la prise.");
                PackageHost.CreateMessageProxy("ESP8266_01_002/ESP_Relay_Button").Switch();
            }
        };
    }
}</pre><p></p>
<p>Et voilà comment en quelques lignes de C# et grâce à Constellation, mes enceintes seront automatiquement allumées ou éteintes selon que mon media-center diffuse ou non un média vidéo ou audio !</p>
<h2>Pour aller plus loin</h2>
<p>Pour aller plus loin, j&rsquo;ai ajouté quelques fonctionnalités intéressantes :</p>
<ul>
<li>J&rsquo;ai pluggé le bouton poussoir ajouté sur le dessus de la prise pour qu&rsquo;il change l&rsquo;état du relais et mette à jour le state objet en conséquence.</li>
<li>J&rsquo;ai ajouté la possibilité d&rsquo;associer les leds de façade au fonctionnement de la prise en m&rsquo;inspirant de ce qui existe sur les prises connectées du marché. La led rouge indique le statut de fonctionnement (power on / connexion au wifi en clignotant), la led verte indique l&rsquo;état du relais.</li>
<li>J&rsquo;ai ajouté également un mode « blind », je trouve que c&rsquo;est une fonctionnalité intéressante mais qui est absente des prises sur le marché : Quand il fait noir dans une pièce et que la prise se reconnecte au wifi, cela peut être gênant de la voir clignoter. Un package de « brain » peut alors gérer les leds directement en <a href="https://developer.myconstellation.io/showcases/connecter-volets-constellation-arduino-raspberry/">fonction de mes volets</a> <img src="https://s.w.org/images/core/emoji/14.0.0/72x72/1f642.png" alt="🙂" class="wp-smiley" style="height: 1em; max-height: 1em;" /></li>
<li>Ensuite, en cas de déconnection du wifi ou de coupure de courant, j&rsquo;ai prévu un bout de code permettant, au démarrage de l&rsquo;ESP, de requêter son propre StateObject. Cela permet à la prise de revenir à l&rsquo;état dans lequel elle était avant la coupure.</li>
<li>J&rsquo;ai également fait intervenir <a href="https://developer.myconstellation.io/tutorials/connecter-un-video-projecteur-dans-constellation/">l&rsquo;activation de mon projecteur</a>. Ce dernier push un StateObject. Si le média center est éteint, il envoie un paquet WOL via <a href="https://developer.myconstellation.io/package-library/networktools/">le package networktools</a> pour l&rsquo;allumer et envoie une notification de fermeture des volets du salon. Le démarrage de la lecture du média sur kodi pilote la prise d&rsquo;allumage des enceintes sans action manuelle. Ainsi, le démarrage du projecteur et la lecture sur kodi lancent l&rsquo;ambiance parfaite pour profiter de mes séries en un seul geste.</li>
</ul>
<p>The post <a rel="nofollow" href="https://developer.myconstellation.io/tutorials/creer-une-prise-connectee-avec-un-esp8266/">Créer une prise connectée avec un ESP8266</a> appeared first on <a rel="nofollow" href="https://developer.myconstellation.io">Constellation</a>.</p>
]]></content:encoded>
					
					<wfw:commentRss>https://developer.myconstellation.io/tutorials/creer-une-prise-connectee-avec-un-esp8266/feed/</wfw:commentRss>
			<slash:comments>0</slash:comments>
		
		
			</item>
		<item>
		<title>Constellation à la DevCon #4 le 26 octobre à l&#8217;école 42</title>
		<link>https://developer.myconstellation.io/blog/devcon-4-le-26-octobre-lecole-42/</link>
					<comments>https://developer.myconstellation.io/blog/devcon-4-le-26-octobre-lecole-42/#comments</comments>
		
		<dc:creator><![CDATA[Sebastien Warin]]></dc:creator>
		<pubDate>Fri, 20 Oct 2017 09:02:14 +0000</pubDate>
				<category><![CDATA[Blog]]></category>
		<category><![CDATA[Web Platform Installer]]></category>
		<category><![CDATA[Raspberry]]></category>
		<category><![CDATA[C#]]></category>
		<category><![CDATA[Supervision]]></category>
		<category><![CDATA[Package]]></category>
		<category><![CDATA[conférence]]></category>
		<category><![CDATA[Python]]></category>
		<category><![CDATA[Sentinel]]></category>
		<category><![CDATA[Raspberry Pi]]></category>
		<category><![CDATA[Constellation]]></category>
		<category><![CDATA[IoT]]></category>
		<guid isPermaLink="false">https://developer.myconstellation.io/?p=5604</guid>

					<description><![CDATA[<p>Jeudi 26 octobre 2017 se tiendra la 4ème édition de la DevCon, la conférence technique du magazine Programmez! Le thème de cet après-midi sera 100 % Raspberry Pi &#38; Co en production : serveur, IoT, développement, Docker. Et à cette</p>
<p>The post <a rel="nofollow" href="https://developer.myconstellation.io/blog/devcon-4-le-26-octobre-lecole-42/">Constellation à la DevCon #4 le 26 octobre à l&rsquo;école 42</a> appeared first on <a rel="nofollow" href="https://developer.myconstellation.io">Constellation</a>.</p>
]]></description>
										<content:encoded><![CDATA[<p>Jeudi 26 octobre 2017 se tiendra la 4ème édition de la <strong>DevCon</strong>, la conférence technique du magazine <a href="https://www.programmez.com/">Programmez!</a></p>
<p align="center"><a href="https://www.programmez.com/content/devcon-4-100-raspberry-pi-co"><img class="colorbox-5604"  loading="lazy" style="background-image: none; padding-top: 0px; padding-left: 0px; display: inline; padding-right: 0px; border: 0px;" title="devcon-4" src="https://developer.myconstellation.io/wp-content/uploads/2017/10/devcon-4.jpg" alt="devcon-4" width="400" height="317" border="0" /></a></p>
<p>Le thème de cet après-midi sera <strong>100 % Raspberry Pi &amp; Co en production</strong> : serveur, IoT, développement, Docker.</p>
<p>Et à cette occasion, vous retrouverez une nouvelle fois une session dédiée à <a href="http://www.myconstellation.io/">Constellation</a> spécial Raspberry.</p>
<p>Au menu de cette session :</p>
<ul>
<li>Comment <a href="https://developer.myconstellation.io/constellation-platform/constellation-server/installer-constellation-sur-linux/">déployer une Constellation sur Raspbian</a> en une seule ligne de commande grâce au Web Platform Installer</li>
<li>Comment <a href="https://developer.myconstellation.io/getting-started/ajouter-des-sentinelles/#Installation_dune_sentinelle_sur_un_systeme_Linux">joindre des RPi v1, v2, v3 </a>dans Constellation pour y <a href="https://developer.myconstellation.io/plateforme/fonctionnalites/deploiement-administration/">déployer et superviser des packages</a> (programmes) depuis une interface Web centrale</li>
<li>Comment développer des packages avec <a href="https://developer.myconstellation.io/getting-started/creez-votre-premier-package-constellation-en-csharp/">Visual Studio</a> ou en ligne de commande avec le « <a href="https://developer.myconstellation.io/blog/developpez-vos-packages-python-ligne-de-commande/">Constellation Package Tools CLI</a> » et les déployer automatiquement sur vos RPi</li>
<li>Comment <a href="https://developer.myconstellation.io/client-api/python-api/">vos packages Python</a> sur RPi peuvent interagir avec vos autres systèmes et autres packages Python, C#, objets Arduino ou des ESP8266, des pages Javascript, ou autre</li>
<li>Comment contrôler un RPi depuis une pages Web ou une application mobile multi-plateforme avec quelques lignes !</li>
</ul>
<p>Nous verrons également plusieurs applications concrètes déployées pour ma « smarthome » comme : <a href="http://sebastien.warin.fr/2015/03/24/2478-senergy-la-solution-de-monitoring-des-ressources-energetiques-de-la-maison-geek-is-in-da-house-2015/">S-Energy</a>, ma solution de supervision des ressources énergique basée sur un Raspberry, <a href="http://sebastien.warin.fr/2015/08/20/2833-s-opener-connectez-et-scurisez-votre-porte-de-garage-avec-constellation-et-un-raspberry-pi-la-porte-de-garage-intelligente/">S-Opener</a> pour piloter la porte de garage depuis un Raspberry, <a href="https://developer.myconstellation.io/tutorials/un-capteur-de-luminosite-exterieur-pilote-par-raspberry/">capteurs luminosité</a>, gestion des volets, etc&#8230;</p>
<p><b>Quand ? </b>26 octobre à partir de 13h30</p>
<p><b>Où :</b> à l’école 42 (Paris)</p>
<p><b>Informations &amp; inscriptions :</b> <a href="https://www.programmez.com/content/devcon-4-100-raspberry-pi-co">https://www.programmez.com/content/devcon-4-100-raspberry-pi-co</a></p>
<p>The post <a rel="nofollow" href="https://developer.myconstellation.io/blog/devcon-4-le-26-octobre-lecole-42/">Constellation à la DevCon #4 le 26 octobre à l&rsquo;école 42</a> appeared first on <a rel="nofollow" href="https://developer.myconstellation.io">Constellation</a>.</p>
]]></content:encoded>
					
					<wfw:commentRss>https://developer.myconstellation.io/blog/devcon-4-le-26-octobre-lecole-42/feed/</wfw:commentRss>
			<slash:comments>1</slash:comments>
		
		
			</item>
		<item>
		<title>S-Fit : Concevez un miroir connecté orienté fitness</title>
		<link>https://developer.myconstellation.io/showcases/s-fit-concevez-un-miroir-connecte-oriente-fitness/</link>
					<comments>https://developer.myconstellation.io/showcases/s-fit-concevez-un-miroir-connecte-oriente-fitness/#comments</comments>
		
		<dc:creator><![CDATA[Sebastien Warin]]></dc:creator>
		<pubDate>Wed, 27 Sep 2017 10:05:42 +0000</pubDate>
				<category><![CDATA[Showcases]]></category>
		<category><![CDATA[Web]]></category>
		<category><![CDATA[StateObject]]></category>
		<category><![CDATA[C#]]></category>
		<category><![CDATA[Javascript]]></category>
		<category><![CDATA[Miroir]]></category>
		<category><![CDATA[Constellation]]></category>
		<category><![CDATA[AngularJS]]></category>
		<category><![CDATA[UI]]></category>
		<category><![CDATA[Consumer]]></category>
		<category><![CDATA[IoT]]></category>
		<category><![CDATA[ForecastIO]]></category>
		<category><![CDATA[Domotique]]></category>
		<guid isPermaLink="false">https://developer.myconstellation.io/?p=5474</guid>

					<description><![CDATA[<p>C’est l’été, la saison des maillots de bains, il est grand temps de se prendre en main et de se sculpter un corps de rêve. Pourquoi ne pas utiliser une des nombreuses solutions de tracker d’activités présentes sur le marché</p>
<p>The post <a rel="nofollow" href="https://developer.myconstellation.io/showcases/s-fit-concevez-un-miroir-connecte-oriente-fitness/">S-Fit : Concevez un miroir connecté orienté fitness</a> appeared first on <a rel="nofollow" href="https://developer.myconstellation.io">Constellation</a>.</p>
]]></description>
										<content:encoded><![CDATA[<p><i>C’est l’été, la saison des maillots de bains, il est grand temps de se prendre en main et de se sculpter un corps de rêve. Pourquoi ne pas utiliser une des nombreuses solutions de tracker d’activités présentes sur le marché ? Ce n’est pas assez drôle pour des makers, nous avons donc décidé de créer notre propre solution fitness axée autour d’un miroir connecté !</i></p>
<p style="text-align: center;"><a href="https://developer.myconstellation.io/wp-content/uploads/2017/09/fig1.png"><img class="colorbox-5474"  loading="lazy" title="Résultat final du miroir connecté à Constellation" src="https://developer.myconstellation.io/wp-content/uploads/2017/09/fig1_thumb.png" alt="Résultat final du miroir connecté à Constellation" width="300" height="381" border="0" /></a></p>
<h2>Introduction</h2>
<p>Nous sommes 5 étudiants en troisième année de Cycle Informatique et Réseaux à l’ISEN et nous avons conçu un nouveau concept de solution fitness basée sur un miroir. Pour réaliser notre projet, nous avions un budget de 0€ mais nous avions surtout une grande motivation pour créer un produit innovant et agréable à utiliser.</p>
<p>C’est pour cela que nous avons utilisé des produits de récupérations. En effet, nous avons tous dans notre garage un ordinateur portable que nous n’utilisons plus, une ancienne webcam, et quelques planches de contreplaqué. Concernant l’aspect miroir, nous avons utilisé du film sans tain car nous en avions déjà, cependant, pour une dizaine d’euros de plus, vous pourrez utiliser une vitre sans tain. Cette dernière donnera un rendu bien meilleur à votre miroir. Voilà qui devrait suffire pour la partie matérielle de notre projet.</p>
<p>Pour la partie logicielle, nous avons utilisé la plateforme Constellation. Les lecteurs réguliers de ce magazine la connaissent déjà, pour les autres, il s’agit d’une plateforme technique d’orchestration et d’interconnexion des objets, des services et des applications. Elle s’appuie sur des paquets qui peuvent publier et consommer des messages ainsi que sur des fonctions partagées. Concrètement, avec Constellation, en quelques lignes, il devient très simple de connecter des objets (ou applications) entre eux. Ces derniers vont donc dialoguer via Constellation comme le feraient des micro-services. L’avantage d’utiliser cette plateforme pour un tel projet c’est la facilité avec laquelle nous avons pu connecter et déployer les différentes briques de notre miroir. Pour en savoir plus sur cette technologie, vous pouvez vous rendre sur <a href="http://www.myconstellation.io/">http://www.myconstellation.io/</a></p>
<p>Pour résumer, en raison d’un coût très faible et d’un développement simplifié, S-Fit est le projet parfait pour vous occuper cet été.</p>
<h2>Fonctionnement général</h2>
<p>Nous avons tout d’abord pensé S-Fit comme une application dotée d’un podomètre. Cette dernière synchronise les différents profils des membres de la famille en temps réel grâce à Constellation. Vous pouvez ainsi y gérer vos propres objectifs et surveiller votre progression. Vous ne perdrez pas votre motivation grâce à notre système de trophées qui vous donnera envie de repousser vos limites chaque jour. Comme il n’existe pas de meilleure motivation que la compétition, vous pourrez vous comparer à vos proches grâces à des outils d’analyse s’appuyant sur une série de graphiques.</p>
<p align="center"><a href="https://developer.myconstellation.io/wp-content/uploads/2017/09/fig7.png"><img class="colorbox-5474"  loading="lazy" style="background-image: none; padding-top: 0px; padding-left: 0px; display: inline; padding-right: 0px; border-width: 0px;" title="Les sources d’informations du miroir" src="https://developer.myconstellation.io/wp-content/uploads/2017/09/fig7_thumb.png" alt="Les sources d’informations du miroir" width="240" height="240" border="0" /></a></p>
<p>Pour vous rappeler vos objectifs chaque matin, nous avons ajouté à S-Fit un miroir compagnon. Ce dernier a demandé beaucoup de réflexion car il s’agit d’un nouvel objet avec lequel il faut interagir de manière naturelle. De plus, il fallait faire de ce dernier un bel objet que l’on puisse retrouver chez soi. Nous avons donc fait le choix d’une interface minimaliste qui affiche seulement les informations pertinentes : la météo, les évènements à venir et votre progression. De ce fait, pas besoin de toucher le miroir et d’y laisser des traces de doigts.</p>
<p>Pour gérer les multiples profils, nous avons également intégré un module de reconnaissance faciale qui permettra au miroir d’afficher des informations personnalisées en fonction de son utilisateur.</p>
<p>Comme vous vous en doutez surement, le lien entre l’application et le miroir se fait par l&rsquo;intermédiaire de la plateforme Constellation. Tout est synchronisé en temps réel et cela fonctionne comme par magie.</p>
<h3>Etape 1 : Conception du boîtier</h3>
<p>Pour commencer, il faut démonter votre vieil ordinateur, afin d’en récupérer la dalle LCD. On utilise ensuite la référence de cette dernière pour pouvoir se procurer le contrôleur adapté.</p>
<p align="center"><a href="https://developer.myconstellation.io/wp-content/uploads/2017/09/fig2.jpg"><img class="colorbox-5474"  loading="lazy" style="background-image: none; padding-top: 0px; padding-left: 0px; display: inline; padding-right: 0px; border-width: 0px;" title="La dalle récupérée et son contrôleur" src="https://developer.myconstellation.io/wp-content/uploads/2017/09/fig2_thumb.jpg" alt="La dalle récupérée et son contrôleur" width="236" height="244" border="0" /></a></p>
<p>Ensuite, il faut concevoir un boîtier capable d’accueillir l’ensemble de votre appareil. Son épaisseur et ses dimensions dépendent donc de votre miroir. Nous ne fournirons donc pas de plans pour rendre votre création unique.</p>
<p>Attention toutefois à prévoir des espaces pour l’aération, l’alimentation et les contrôles de la dalle.</p>
<p>C’est la partie la plus personnelle du projet, c’est le moment de libérer votre créativité pour mettre en place votre vision de S-Fit.</p>
<p align="center"><a href="https://developer.myconstellation.io/wp-content/uploads/2017/09/fig3.jpg"><img class="colorbox-5474"  loading="lazy" style="background-image: none; padding-top: 0px; padding-left: 0px; display: inline; padding-right: 0px; border-width: 0px;" title="Assemblage du boîtier et vernissage" src="https://developer.myconstellation.io/wp-content/uploads/2017/09/fig3_thumb.jpg" alt="Assemblage du boîtier et vernissage" width="244" height="125" border="0" /></a><a href="https://developer.myconstellation.io/wp-content/uploads/2017/09/fig4.jpg"><img class="colorbox-5474"  loading="lazy" style="background-image: none; padding-top: 0px; padding-left: 0px; display: inline; padding-right: 0px; border-width: 0px;" title="Assemblage du boîtier et vernissage" src="https://developer.myconstellation.io/wp-content/uploads/2017/09/fig4_thumb.jpg" alt="Assemblage du boîtier et vernissage" width="244" height="127" border="0" /></a></p>
<p>Nous avons également prévu une trappe d’accès à l’arrière pour pouvoir modifier notre miroir plus tard.</p>
<p>Si vous avez fait le choix du film sans tain, il va falloir le poser. Pour cela, voici les quelques étapes à suivre :</p>
<ul>
<li>Nettoyer votre dalle à l’aide d’un chiffon doux</li>
<li>Appliquer un peu d’eau savonneuse sur celle-ci</li>
<li>Poser le film sans tain petit à petit en vous aidant d’un grattoir. Attention à ne pas rayer le film avec, c’est très fragile !</li>
<li>Chassez, toujours avec ce grattoir, les dernières bulles d’air</li>
</ul>
<p>Prenez bien votre temps lors de la pose, c’est une partie très délicate et elle affectera directement l’esthétique de votre miroir.</p>
<p>Vous avez maintenant l’ensemble des pièces qui vont constituer votre miroir. Pour terminer, il ne vous reste plus qu’à tout assembler en faisant attention à bien aligner la dalle et le boîtier.</p>
<p align="center"><a href="https://developer.myconstellation.io/wp-content/uploads/2017/09/fig5.jpg"><img class="colorbox-5474"  loading="lazy" style="background-image: none; padding-top: 0px; padding-left: 0px; display: inline; padding-right: 0px; border-width: 0px;" title="Le miroir assemblé, prêt à être refermé" src="https://developer.myconstellation.io/wp-content/uploads/2017/09/fig5_thumb.jpg" alt="Le miroir assemblé, prêt à être refermé" width="354" height="266" border="0" /></a></p>
<p>Si vous souhaitez intégrer un module de reconnaissance faciale, il va falloir ajouter une webcam (USB).</p>
<p>Pour cela, il faut la démonter, récupérer le circuit et le fixer dans le boîtier.</p>
<p align="center"><a href="https://developer.myconstellation.io/wp-content/uploads/2017/09/fig07.jpg"><img class="colorbox-5474"  loading="lazy" style="background-image: none; padding-top: 0px; padding-left: 0px; display: inline; padding-right: 0px; border: 0px;" title="Miroir assemblé sans la webcam" src="https://developer.myconstellation.io/wp-content/uploads/2017/09/fig07_thumb.jpg" alt="Miroir assemblé sans la webcam" width="304" height="404" border="0" /></a></p>
<h3>Etape 2 : Le développement logiciel</h3>
<h4>Etape 2.1 : L’interface du miroir</h4>
<p>Pour réaliser le miroir, nous avons choisi de concevoir une application web avec AngularJS. En effet, comme le dit le créateur de Constellation, Sébastien Warin, on peut connecter n’importe quoi avec quelques lignes de code qui vont bien.</p>
<p>Tout d’abord, il est important de rappeler que pour continuer ce tutoriel, il est nécessaire d’avoir une Constellation déployée chez soi. Vous trouverez la plateforme ainsi que les tutoriels de prise en main sur le portail <a href="https://developer.myconstellation.io/">https://developer.myconstellation.io/</a></p>
<p align="center"><a href="https://developer.myconstellation.io/wp-content/uploads/2017/09/fig8.png"><img class="colorbox-5474"  loading="lazy" style="background-image: none; padding-top: 0px; padding-left: 0px; display: inline; padding-right: 0px; border-width: 0px;" title="Le rôle de Constellation dans la plateforme S-Fit" src="https://developer.myconstellation.io/wp-content/uploads/2017/09/fig8_thumb.png" alt="Le rôle de Constellation dans la plateforme S-Fit" width="300" height="300" border="0" /></a></p>
<p>Nous allons donc pouvoir connecter notre application Angular à Constellation :</p>
<p></p><pre class="crayon-plain-tag">var app = angular.module('Mirror', ['ngConstellation']);

app.controller('MyController', ['$scope', 'constellationConsumer', ($scope, constellation) =&gt; {

    constellation.initializeClient("maconstellation.local", "masupercle123", "MyMirror");

    constellation.connect();

}]);</pre><p></p>
<p>Il ne reste plus qu’à s’abonner aux StateObjects de Constellation que l’on veut voir sur le miroir. Par exemple, ici, nous allons récupérer la météo dans la ville de Lille :</p>
<p></p><pre class="crayon-plain-tag">constellation.registerStateObjectLink("*", "ForecastIO", "Lille", "*", (so) =&gt; {
    $scope.$apply(() =&gt; {
        $scope.temperature = so.Value.currently.temperature;
    });
});</pre><p></p>
<p>Pour en savoir plus, vous pouvez vous rendre sur le portail dont le lien se trouve plus haut pour y trouver la documentation complète. Vous trouverez d’ailleurs un tutoriel détaillé sur l’utilisation de Constellation en JavaScript. Mais rassurez vous, ce n’est pas plus compliqué que cela. Il ne manque que quelques lignes d’HTML et de CSS pour donner vie à votre miroir.</p>
<p>Si on continue l’exemple de la météo, le code HTML associé pourrait-être le suivant :</p>
<p></p><pre class="crayon-plain-tag">&lt;p&gt;{{temperature}}&lt;/p&gt;</pre><p></p>
<p>On obtiendrait alors une page sur laquelle la température va s’afficher dynamiquement.</p>
<p align="center"><a href="https://developer.myconstellation.io/wp-content/uploads/2017/09/fig6.png"><img class="colorbox-5474"  loading="lazy" style="background-image: none; padding-top: 0px; padding-left: 0px; display: inline; padding-right: 0px; border-width: 0px;" title="L’interface finale du miroir: le choix du noir et blanc permet un meilleur rendu sur le miroir" src="https://developer.myconstellation.io/wp-content/uploads/2017/09/fig6_thumb.png" alt="L’interface finale du miroir: le choix du noir et blanc permet un meilleur rendu sur le miroir" width="450" height="336" border="0" /></a></p>
<h4>Etape 2.2 : La reconnaissance faciale</h4>
<p>Comme nous l’expliquions plus haut, nous avons ajouté un module de reconnaissance faciale pour gérer plusieurs profils. Il s’agit d’une partie facultative et plutôt complexe.</p>
<p>Pour cela, nous avons utilisé une <a href="https://www.codeproject.com/Articles/261550/EMGU-Multiple-Face-Recognition-using-PCA-and-Paral">application open source existante</a> qui s’appuie sur EMGU.CV. C’est un portage en C# d’OpenCV. Malheureusement, cette application était trop ancienne et nous n’avons pas réussi à la connecter directement à Constellation. Pour résoudre ce problème, nous avons conçu un paquet Constellation qui permet de publier et de s’abonner aux StateObjects par l’intermédiaire de sockets TCP.</p>
<p>Lors de l’ajout d’un nouvel utilisateur S-Fit, le paquet lance la séquence d’enregistrement d’un visage automatiquement.</p>
<p>Nous avons effectué plusieurs essais sur la quantité d’images à enregistrer, afin d’obtenir l’équilibre idéal entre une reconnaissance optimale et un minimum d’espace utilisé. Pour vous reconnaître, l’algorithme s’appuie sur plusieurs caractéristiques faciales, comme la forme du nez, de la bouche, des yeux, de vos sourcils…</p>
<p>De par le peu d’espace pris par la reconnaissance, vous pouvez aisément enregistrer toute votre famille, afin que le miroir devienne un élément à part entière de votre lieu de vie, et que tout le monde participe à la compétition !</p>
<p>La reconnaissance faciale se déroule en deux étapes. La première consiste à détecter un visage. Pour cela nous avons utilisé le classificateur Haar car il nous fallait une reconnaissance faciale en temps réel. Le classificateur Haar est, en fait, un fichier xml contenant une quantité énorme de photos dites négatives et positives. Les photos positives contiennent un visage, tandis que les photos négatives n’en contiennent pas. Cela permet donc de savoir si un visage est présent sur une photo ne faisant pas partie du classificateur. À noter qu’il est possible de créer soi-même son propre classificateur ou même d’en améliorer un.</p>
<p>Ici, nous nous servons donc de ce dernier afin de vérifier si, sur la frame actuelle, un visage est présent ou non de la sorte :</p>
<p></p><pre class="crayon-plain-tag">gray_frame = currentFrame.Convert&lt;Gray, Byte&gt;();

MCvAvgComp[][] facesDetected = gray_frame.DetectHaarCascade(Face, 1.2, 10, Emgu.CV.CvEnum.HAAR_DETECTION_TYPE.DO_CANNY_PRUNING, new Size(50, 50));</pre><p></p>
<p>Ceci va donc insérer dans le tableau facesDetected[0] tous les visages ayant eu un résultat positif après comparaison avec le classificateur Haar.</p>
<p>Dans un second temps, on cherche à reconnaître une personne à l’aide de son visage, l’application dispose donc d’une architecture très simple divisée en trois classes C#. La classe principale va capturer le flux vidéo de la webcam puis par la suite analyser chaque image via la classe de reconnaissance de personne qui, elle, aura au préalable chargé les données des personnes déjà enregistrées. La dernière classe sert, quant à elle, à enregistrer une personne en prenant une centaine de photos du visage de celle-ci.</p>
<p>Pour communiquer avec notre package, nous avons également ajouté une classe TCPClient.cs qui se connecte et échange les StateObjects via le réseau.</p>
<p>C’est d’ailleurs les paquets reçus qui vont démarrer les fonctions d’ajout d’utilisateur.</p>
<p>Pour rendre la gestion des utilisateurs agréable, nous avons intégré cette reconnaissance faciale de manière totalement transparente. Lorsqu’un utilisateur s’enregistre dans l’application il doit être face au miroir. Pour vérifier cela, l’utilisateur sera invité à saisir un code à six chiffres qui s’affichera quelques secondes sur le miroir. Une fois l’ensemble des informations saisies dans l’application, le miroir va automatiquement lancer une séquence de capture de 100 clichés du nouvel utilisateur.</p>
<p>Pour la reconnaissance des utilisateurs enregistrés, le paquet de reconnaissance faciale va capturer une image chaque seconde pour vérifier la présence ou non d’un individu connu.</p>
<p>Lorsque deux utilisateurs enregistrés sont face au miroir, ce dernier va se concentrer sur celui qu’il identifie le mieux.</p>
<h4>Etape 2.3 : L’application mobile</h4>
<p>L’application S-Fit a été conçue avec les frameworks Ionic 3 et Apache Cordova. Ces frameworks permettent d’obtenir une application Web à l&rsquo;intérieur d’une application native Android ou iOS qui embarque un serveur NodeJS sur le mobile. Comme nous l’avons vu plus haut, l’application qu’affiche le miroir est une page web, l’application mobile utilise donc les mêmes technologies.</p>
<p>Ainsi, la connexion s’effectuera tout aussi simplement :</p>
<p></p><pre class="crayon-plain-tag">var constellation = $.signalR.createConstellationConsumer("maconstellation.local", "masupercle123", "MonApp");

constellation.connection.start();</pre><p></p>
<p>Une application comme la nôtre peut alors consommer des StateObjects mais également envoyer des MessageCallbacks. C’est à dire exécuter des fonctions directement sur la Constellation. C’est particulièrement utile pour incrémenter le compteur de pas.</p>
<p>Nous avons découpé notre application en trois grandes parties : la gestion des profils, les activités et les trophées.</p>
<h5>Gestion des profils</h5>
<p>Comme S-Fit est pensé pour plusieurs utilisateurs, nous avons géré les profils dans notre application.</p>
<p align="center"><a href="https://developer.myconstellation.io/wp-content/uploads/2017/09/fig10-1.png"><img class="colorbox-5474"  loading="lazy" style="background-image: none; padding-top: 0px; padding-left: 0px; display: inline; padding-right: 0px; border: 0px;" title="Choix d’utilisateur, nouvel utilisateur et informations" src="https://developer.myconstellation.io/wp-content/uploads/2017/09/fig10_thumb-1.png" alt="Choix d’utilisateur, nouvel utilisateur et informations" width="354" height="202" border="0" /></a></p>
<p>Lorsqu’un utilisateur lance l’application, il peut choisir son profil. Cette action va établir la connexion avec la Constellation pour récupérer les informations personnelles et l’historique d’activités. Toutefois, s’il n’a pas de profil, il peut en ajouter un s’il est en face du miroir, qui lui affichera alors un code de vérification. Lors du lancement de l’application, cette dernière synchronise instantanément les nouvelles données d’activités avec le serveur Constellation.</p>
<p>L’utilisation d’S-Fit est totalement transparente et ne demande pas de manipulation particulière de l’utilisateur. En effet, nous avons cherché à fournir un produit simple, accessible et entièrement automatisé. Cette synchronisation est permise par Constellation.</p>
<h5>Les activités</h5>
<p>Cette partie se compose d’un podomètre, d’un récapitulatif de la journée en cours et d’un historique sous forme de graphiques.</p>
<p align="center"><a href="https://developer.myconstellation.io/wp-content/uploads/2017/09/fig11-1.png"><img class="colorbox-5474"  loading="lazy" style="background-image: none; padding-top: 0px; padding-left: 0px; display: inline; padding-right: 0px; border: 0px;" title="Récapitulatif de la journée en temps réel et statistiques" src="https://developer.myconstellation.io/wp-content/uploads/2017/09/fig11_thumb-1.png" alt="Récapitulatif de la journée en temps réel et statistiques" width="304" height="262" border="0" /></a></p>
<p>Pour le podomètre, nous nous sommes appuyés sur un plugin de Cordova permettant d’accéder aux données de l&rsquo;accéléromètre du mobile. A l’aide des données fournies par ce plugin, nous avons pu étudier les variations sur les axes x, y et z, dans l’optique de compter les pas.</p>
<p>L’application récupère donc les données accélérométriques de votre mobile toutes les 0.120 secondes. C’est une valeur que nous avons retenue après plusieurs jours de tests pour affiner la précision du compteur de pas, puis, en s’appuyant sur les précédentes valeurs, on va déterminer si le mouvement effectué est un pas ou non, et donc informer Constellation si elle doit incrémenter le nombre de pas de l’utilisateur.</p>
<p>Le développement de cette application ne se résume pas qu’à de la programmation informatique. Nous avons également réalisé des mesures sur plusieurs dizaines de personnes afin d’obtenir un lien entre la morphologie et la longueur des pas</p>
<p></p><pre class="crayon-plain-tag">var slope = 0.64878048 ;
var origin = 44.6744 ;

function getDistance(size, stepCounter) {
    return (size * slope - origin) * stepCounter;
}</pre><p></p>
<p>Avec les informations physiologiques et l’activité de l’utilisateur, on peut donc créer un ensemble de fonctions qui permettent d’étudier son état de santé, en calculant par exemple les calories dépensées chaque jour. C’est grâce à ces données qu’il est possible de créer une application fitness entièrement maîtrisée. On est alors libre d’appliquer les algorithmes souhaités sur les données récupérées.</p>
<p>Pour la page des graphiques sur l’application mobile, nous avons utilisé la bibliothèque Chart.js qui permet de tracer des graphiques dynamiques avec un rendu épuré. Son principal avantage est la prise en main rapide de la bibliothèque ainsi que toutes ses options.</p>
<p>Voici un exemple pour tracer un graphique linéaire</p>
<p></p><pre class="crayon-plain-tag">var myLineChart = new Chart(ctx, {
    type: 'line',
    data: data,
    options: options
});</pre><p></p>
<p>Cependant, il faut tout d’abord récupérer les informations présentes dans les StateObjects pour les afficher dans les graphiques. Cela nous permet de faire des graphes qui se mettent à jour en temps réel.</p>
<h5>Les trophées</h5>
<p align="center"><a href="https://developer.myconstellation.io/wp-content/uploads/2017/09/fig12.png"><img class="colorbox-5474"  loading="lazy" style="background-image: none; padding-top: 0px; padding-left: 0px; display: inline; padding-right: 0px; border: 0px;" title="La liste des trophées et détails d’un trophée" src="https://developer.myconstellation.io/wp-content/uploads/2017/09/fig12_thumb.png" alt="La liste des trophées et détails d’un trophée" width="354" height="303" border="0" /></a></p>
<p>Comme nous l’expliquions plus haut, nous avons intégré un système de trophées et de récompense. Il se présente tout d’abord comme une liste de trophées que l’on débloque en réalisant des succès particuliers (pas, distance).</p>
<p>Les trophées montrent votre expérience sur S-Fit, et représentent donc la récompense pour vos efforts. Lorsque l’on clique sur un trophée débloqué, on affiche son détail et le nombre de points qu’il a rapporté.</p>
<p align="center"><a href="https://developer.myconstellation.io/wp-content/uploads/2017/09/fig11.png"><img class="colorbox-5474"  loading="lazy" style="background-image: none; padding-top: 0px; padding-left: 0px; display: inline; padding-right: 0px; border-width: 0px;" title="Schéma récapitulatif de la synchronisation" src="https://developer.myconstellation.io/wp-content/uploads/2017/09/fig11_thumb.png" alt="Schéma récapitulatif de la synchronisation" width="240" height="240" border="0" /></a></p>
<h2>Conclusion</h2>
<p>Voilà qui conclue les grandes étapes de la réalisation de S-Fit. Comme vous avez pu le voir les possibilités de personnalisation sont très nombreuses. C’est un projet ludique et facile à réaliser. C’est également un bon point de départ pour prendre en main la plateforme Constellation. Nous espérons vraiment qu’il vous a plu et que vous allez réaliser votre propre version.</p>
<p>Nous tenons également à remercier Julie, Adrien et tous ceux qui se sont impliqués de près ou de loin dans la réalisation de ce projet.</p>
<p align="center"><a href="https://developer.myconstellation.io/wp-content/uploads/2017/09/fig9.jpg"><img class="colorbox-5474"  loading="lazy" style="background-image: none; padding-top: 0px; padding-left: 0px; display: inline; padding-right: 0px; border-width: 0px;" title="L’équipe au complet" src="https://developer.myconstellation.io/wp-content/uploads/2017/09/fig9_thumb.jpg" alt="L’équipe au complet" width="404" height="256" border="0" /></a></p>
<p>Auteurs : Valentin BEQUART, David BRICENO-AGUILERA, Pierre-Alexandre CHOAIN, Milan FERTIN et Hugo MROCZKOWSKI.</p>
<p>The post <a rel="nofollow" href="https://developer.myconstellation.io/showcases/s-fit-concevez-un-miroir-connecte-oriente-fitness/">S-Fit : Concevez un miroir connecté orienté fitness</a> appeared first on <a rel="nofollow" href="https://developer.myconstellation.io">Constellation</a>.</p>
]]></content:encoded>
					
					<wfw:commentRss>https://developer.myconstellation.io/showcases/s-fit-concevez-un-miroir-connecte-oriente-fitness/feed/</wfw:commentRss>
			<slash:comments>2</slash:comments>
		
		
			</item>
		<item>
		<title>Synchroniser un interrupteur mural avec des ampoules connectées et contrôler l&#8217;ambiance lumineuse de votre pièce</title>
		<link>https://developer.myconstellation.io/tutorials/synchroniser-interrupteur-mural-ampoules-connectee/</link>
					<comments>https://developer.myconstellation.io/tutorials/synchroniser-interrupteur-mural-ampoules-connectee/#comments</comments>
		
		<dc:creator><![CDATA[Sebastien Warin]]></dc:creator>
		<pubDate>Mon, 15 May 2017 23:12:13 +0000</pubDate>
				<category><![CDATA[Tutoriels]]></category>
		<category><![CDATA[C#]]></category>
		<category><![CDATA[Package]]></category>
		<category><![CDATA[Vera]]></category>
		<category><![CDATA[Z-Wave]]></category>
		<category><![CDATA[Hue]]></category>
		<category><![CDATA[Lampe]]></category>
		<category><![CDATA[Fibaro]]></category>
		<category><![CDATA[Ampoules]]></category>
		<guid isPermaLink="false">https://developer.myconstellation.io/?p=4853</guid>

					<description><![CDATA[<p>Dans cet article nous allons découvrir comment contrôler l&#8217;ambiance lumineuse d&#8217;une pièce équipée d&#8217;ampoules connectées avec un simple interrupteur mural. L&#8217;idée est à la fois de pouvoir allumer ou éteindre toutes les ampoules de la pièce à partir de l’interrupteur</p>
<p>The post <a rel="nofollow" href="https://developer.myconstellation.io/tutorials/synchroniser-interrupteur-mural-ampoules-connectee/">Synchroniser un interrupteur mural avec des ampoules connectées et contrôler l&rsquo;ambiance lumineuse de votre pièce</a> appeared first on <a rel="nofollow" href="https://developer.myconstellation.io">Constellation</a>.</p>
]]></description>
										<content:encoded><![CDATA[<p>Dans cet article nous allons découvrir comment contrôler l&rsquo;ambiance lumineuse d&rsquo;une pièce équipée d&rsquo;ampoules connectées avec un simple interrupteur mural.</p>
<p>L&rsquo;idée est à la fois de pouvoir allumer ou éteindre toutes les ampoules de la pièce à partir de l’interrupteur mais également de pouvoir sélectionner une ambiance lumineuse en fonction des circonstances, par exemple pour un salon : ambiance « réception », ambiance « soirée », ambiance « Ciné », ambiance « Feu de cheminée », etc&#8230;</p>
<p align="center"><a href="https://developer.myconstellation.io/wp-content/uploads/2017/05/Hue1.gif"><img class="colorbox-4853"  loading="lazy" style="background-image: none; padding-top: 0px; padding-left: 0px; display: inline; padding-right: 0px; border-width: 0px;" title="Hue1" src="https://developer.myconstellation.io/wp-content/uploads/2017/05/Hue1_thumb-gap.jpg" data-gif="https://developer.myconstellation.io/wp-content/uploads/2017/05/Hue1_thumb.gif" alt="Hue1" width="150" height="266" border="0" /></a></p>
<h3>Prérequis</h3>
<ul>
<li>Un serveur Constellation</li>
<li>Des lampes ou ampoules connectées, ici des Philips Hue</li>
<li>Un interrupteur mural connecté, ici un interrupteur Legrand relié à un module Z-Wave Fibaro FGS-211</li>
<li>Le SDK Constellation pour Visual Studio</li>
</ul>
<h3>Etape 1 : connecter un interrupteur mural</h3>
<p>La première étape consiste donc à intégrer un interrupteur dans Constellation. Avec la polyvalence de la plateforme Constellation, il y a mille et une manière d&rsquo;y parvenir.</p>
<p>Pour ma part, j&rsquo;ai conservé les interrupteurs existants de la gamme Mosaic Legrand. Il s&rsquo;agit pour être exacte d&rsquo;un double bouton poussoir.</p>
<p>Pour le rendre connecté, j&rsquo;ai ajouté un micro-module de la marque Fibaro spécialement conçu pour être intégré dans la boite d&rsquo;encastrement juste derrière l’interrupteur.</p>
<p>Ce module Fibaro est un FGS-211 connecté en Z-Wave et disposant de deux relais en sortie pilotant des charges jusqu&rsquo;à 1500W et de deux entrées. Dans mon cas, il n&rsquo;y a aucune charge connectée sur ce module, il me sert juste de »capteur ».</p>
<p>Je rappelle aussi que les ampoules Philips Hue doivent être constamment alimentées en 220v de façon à être pilotable même après avoir fermé les lumières !</p>
<p>Le module Fibaro est simplement connecté sur le réseau électrique 220v pour son alimentation et aux deux boutons poussoir Legrand de la façon suivante :</p>
<p style="text-align: center;"><a href="https://developer.myconstellation.io/wp-content/uploads/2017/05/image-87.png"><img loading="lazy" class="alignnone colorbox-4853" style="background-image: none; padding-top: 0px; padding-left: 0px; display: inline; padding-right: 0px; border-width: 0px;" title="Connexion du FGS-211" src="https://developer.myconstellation.io/wp-content/uploads/2017/05/image_thumb-86.png" alt="Connexion du FGS-211" width="450" height="321" border="0" /></a></p>
<p>Cela permettant d&rsquo;avoir deux boutons connectés sur le même interrupteur : l&rsquo;un servira pour allumer ou éteindre toutes les lumières du salon et l&rsquo;autre permettra de changer la configuration lumineuse de la pièce.</p>
<p style="text-align: center;"><img loading="lazy" class="aligncenter colorbox-4853" style="background-image: none; padding-top: 0px; padding-left: 0px; display: inline; padding-right: 0px; border-width: 0px;" title="image" src="https://developer.myconstellation.io/wp-content/uploads/2017/05/image-86.png" alt="image" width="240" height="232" border="0" /></p>
<p style="text-align: left;">Ce module Fibaro a été appairé sur mon contrôleur Z-Wave qui est une Vera Lite. Après avoir déployé le package <a href="/package-library/vera/">Vera </a>sur une des sentinelles de ma Constellation, on obtient différents StateObjects représentant l&rsquo;état en temps réel de chaque device Z-Wave et des MessageCallbacks permettant de les piloter.</p>
<p style="text-align: left;">Les deux relais du FGS-221 sont considérés comme deux devices distincts de type « Switchs » (On ou Off). On a donc deux StateObjects dans Constellation pour représenter l&rsquo;état de ces deux relais. Chacun de ces StateObjects contient la propriété « Status », un booléen indiquant si le relais est ouvert ou fermé.</p>
<p style="text-align: center;" align="center"><a href="https://developer.myconstellation.io/wp-content/uploads/2017/05/image-89.png"><img loading="lazy" class="aligncenter colorbox-4853" style="background-image: none; padding-top: 0px; padding-left: 0px; display: inline; padding-right: 0px; border-width: 0px;" title="StateObject du FGS-211" src="https://developer.myconstellation.io/wp-content/uploads/2017/05/image_thumb-88.png" alt="StateObject du FGS-211" width="354" height="293" border="0" /></a></p>
<p style="text-align: left;">On peut permuter l&rsquo;état du relais informatiquement parlant par la Vera (ou par Constellation via le MessageCallback « <em>SetSwitchState</em> » du package Vera) ou directement en appuyant sur les boutons poussoirs.</p>
<p>Ainsi dès lors que l&rsquo;utilisateur va appuyer sur l&rsquo;un des boutons poussoirs, l&rsquo;état du relais changera et donc le StateObject le représentant sera également mis à jour dans votre Constellation. On pourra donc s&rsquo;abonner à ces deux StateObjects via l&rsquo;API.NET, Python, Arduino ou autre pour réagir à ces changements d&rsquo;état, par exemple pour allumer ou éteindre les ampoules Hue.</p>
<h3>Etape 2 : connecter des lampes</h3>
<p>Deuxième étape pour mener à bien notre projet : connecter des lampes dans Constellation. Il y a différentes solutions comme nous avons pu le découvrir dans <a href="/tutorials/synchroniser-lampe-bureau-avec-session-windows/#Etape_1_piloter_une_lampe_par_Constellation">cet autre tutoriel</a> : solutions DIY, prises connectées en Wifi, RF, en Z-Wave, lampes ou ampoules connectées en Wifi, en ZeeBee, etc.. etc..</p>
<p>Dans mon cas, j&rsquo;ai équipé les huit appliques de mon salon avec des ampoules Philips Hue.</p>
<p style="text-align: center;"><a href="https://developer.myconstellation.io/wp-content/uploads/2017/05/hue.jpg"><img loading="lazy" class="aligncenter colorbox-4853" style="background-image: none; padding-top: 0px; padding-left: 0px; display: inline; padding-right: 0px; border-width: 0px;" title="hue" src="https://developer.myconstellation.io/wp-content/uploads/2017/05/hue_thumb.jpg" alt="hue" width="400" height="210" border="0" /></a></p>
<p style="text-align: left;">Toutes les ampoules communiquent en ZeeBee à un pont Ethernet, nommé le bridge (à gauche de la photo ci-dessus). Grace au package <a href="/package-library/hue/">Hue</a>, vous disposez de différents MessageCallbacks pour contrôler chaque lampes Hue (état, intensité lumineuse, couleur, effet, etc..) et d&rsquo;un StateObject par luminaire représentant son état en temps réel.</p>
<p style="text-align: center;" align="center"><a href="https://developer.myconstellation.io/wp-content/uploads/2017/05/image-90.png"><img class="colorbox-4853"  loading="lazy" style="background-image: none; padding-top: 0px; padding-left: 0px; display: inline; padding-right: 0px; border-width: 0px;" title="StateObject d'une ampoule Hue" src="https://developer.myconstellation.io/wp-content/uploads/2017/05/image_thumb-89.png" alt="StateObject d'une ampoule Hue" width="354" height="258" border="0" /></a></p>
<p style="text-align: center;" align="center"><a href="https://developer.myconstellation.io/wp-content/uploads/2017/05/image-91.png"><img class="colorbox-4853"  loading="lazy" style="background-image: none; padding-top: 0px; padding-left: 0px; display: inline; padding-right: 0px; border-width: 0px;" title="MessageCallbacks du package Hue" src="https://developer.myconstellation.io/wp-content/uploads/2017/05/image_thumb-90.png" alt="MessageCallbacks du package Hue" width="354" height="358" border="0" /></a></p>
<h3>Etape 3 : synchroniser l’interrupteur avec les lampes</h3>
<p>Passons au chose sérieuse, nous avons d’un côté deux StateObjects nous indiquant l&rsquo;état des deux relais qu&rsquo;on contrôle par les boutons poussoirs et de l&rsquo;autre des MessageCallbacks nous permettant de contrôler les ampoules Hue du salon, reste juste à faire le lien !</p>
<p>Pour cela nous allons <a href="https://developer.myconstellation.io/getting-started/creez-votre-premier-package-constellation-en-csharp/">créer un package .NET en C#</a> depuis Visual Studio.</p>
<p>Dans la classe principale (<em>Program</em>), nous allons ajouter deux <a href="https://developer.myconstellation.io/client-api/net-package-api/consommer-des-stateobjects/">StateObjectLinks</a>, c’est à dire des propriétés dans notre code liées aux StateObjects représentant les états des interrupteurs :</p>
<p></p><pre class="crayon-plain-tag">[StateObjectLink("Vera", "Interrupteur Hue 1")]
public StateObjectNotifier InterrupteurHue1 { get; set; }

[StateObjectLink("Vera", "Interrupteur Hue 2")]
public StateObjectNotifier InterrupteurHue2 { get; set; }</pre><p></p>
<p>Nous allons commencer par le bouton de gauche, c&rsquo;est à dire l&rsquo;interrupteur n°1 qui se chargera d&rsquo;allumer ou d’éteindre toutes les ampoules du salon.</p>
<p>Pour cela nous allons attacher un « handler » qui réagira à la mise à jour du StateObject « Interrupteur Hue 1 ». Le handler commencera par vérifier que l&rsquo;état à bien changé, c&rsquo;est à dire que la propriété « Status » du « OldState » versus le « NewState » est bien différente (le StateObject peut être mis à jour par exemple dans le cas d&rsquo;un « poll » Z-Wave à intervalle régulier sans pour autant que son Status ait changé !).</p>
<p>Ensuite on invoque simplement le MessageCallback « <em>SetState</em> » du package Hue. Le 1er argument est le n° de la lampe, 0 indiquant « toutes les lampes » et le 2ème argument est l&rsquo;état (On ou Off) de la lampe. Ici on passera l&rsquo;état du relais (propriété du Status).</p>
<p></p><pre class="crayon-plain-tag">this.InterrupteurHue1.ValueChanged += (s, e) =&gt;
{
    if ((bool)e.OldState.DynamicValue.Status != (bool)e.NewState.DynamicValue.Status)
    {
        PackageHost.CreateMessageProxy("Hue").SetState(0, (bool)e.NewState.DynamicValue.Status);
    }
};</pre><p></p>
<p>Ainsi dès que vous appuyez sur le bouton poussoir de gauche, le relais change d&rsquo;état donc le code ci-dessus est invoqué ce qui allumera ou éteindra toutes vos lampes Hue !</p>
<p>Et voilà comment en quelques lignes on peut synchroniser des choses ensembles ! Au final, on obtient un interrupteur connecté pilotant plusieurs ampoules connectées.</p>
<p>Une fois votre package testé et validé, vous pouvez <a href="/constellation-platform/constellation-sdk/publier-package-visual-studio/">le publier</a> dans votre Constellation et le déployer sur une de vos sentinelles (<a href="/getting-started/creez-votre-premier-package-constellation-en-csharp/#Publier_son_package_dans_Constellation">voir le guide</a>). Simple et efficace !</p>
<h3>Etape 4 : contrôler les ambiances lumineuses</h3>
<p>Ce que nous avons fait jusqu&rsquo;à présent est relativement simple : on synchronise simplement l&rsquo;état du relais Fibaro (piloté par l’interrupteur) à l&rsquo;état (state On/Off) des lampes Hue.</p>
<p>Le MessageCallback « <em>SetState</em> » allume ou éteint des lampes Hue. Dans le cas d&rsquo;un allumage, les lampes reprendront leurs dernières configurations en terme de couleur et d&rsquo;intensité.</p>
<p style="text-align: left;">Il existe d&rsquo;autre MC sur ce package comme le <em>SetColor</em>, <em>SetBrightness</em>, ou le <em>Set</em> qui combine les 3 en un en prenant en paramètre à la fois l&rsquo;état, la couleur et l&rsquo;intensité.</p>
<p style="text-align: left;">Nous allons donc perfectionner notre package en utilisant <a href="/client-api/net-package-api/settings/">un setting au format JSON</a> pour décrire nos différentes ambiances lumineuses. L’interrupteur de gauche ne se contentera plus de faire un simple <em>SetState</em> sur chaque lampe mais appliquera la configuration dite par défaut que nous pourrons à tout moment mettre à jour dans les settings depuis la Console.</p>
<p style="text-align: left;">L&rsquo;interrupteur n°2 quant à lui, celui de droite, servira pour appliquer la configuration suivante de façon cyclique (arrivé à la dernière, on revient au début).</p>
<p align="center"><img class="colorbox-4853"  loading="lazy" title="Hue2" src="https://developer.myconstellation.io/wp-content/uploads/2017/05/Hue2_thumb-gap.jpg" data-gif="https://developer.myconstellation.io/wp-content/uploads/2017/05/Hue2_thumb.gif" alt="Hue2" width="150" height="266" border="0" /></p>
<p style="text-align: left;" align="center">Commençons d&rsquo;abord par définir nos configurations lumineuses dans un setting JSON.</p>
<h4>Créer des « configurations lumineuses »</h4>
<p>Pour cela je vous propose de créer une page Web pour générer le setting de configuration sur base de l&rsquo;état actuelle de vos lampes.</p>
<p>En clair, avec l&rsquo;application officielle Hue, réglez vos lampes pour créer l&rsquo;ambiance lumineuse souhaitée et en temps réel notre page Web générera l&rsquo;objet JSON représentant votre configuration.</p>
<p>Nous allons simplement créer un simple page HTML en y ajoutant le module Constellation / AngularJS <a href="/client-api/javascript-api/consommer-constellation-angular-js/">comme vu ici</a>.</p>
<p>Lorsque nous sommes connecté, on enregistre un StateObjectLink sur tous les StateObjects du type « <em>Q42.HueApi.Light</em> » du package Hue. Pour chaque lampe Hue, on stocke la valeur du StateObject dans une variable de scope nommée « lights » :</p>
<p></p><pre class="crayon-plain-tag">constellation.registerStateObjectLink("*", "Hue", "*", "Q42.HueApi.Light", function (stateObject) { 
    $scope.$apply(function () {
        $scope.lights[stateObject.Name] = stateObject.Value;
    });
});</pre><p></p>
<p>Ainsi l&rsquo;état de chacune de nos lampes sera synchronisée en temps réel dans cette variable Javascript.</p>
<p>Maintenant dans le code HTML, générons une liste pour afficher le nom de chaque lampe, son ID, son état (on/off), sa couleur (Hue et Saturation) et son intensité (bri) avec un « ng-repeat » Angular :</p>
<p></p><pre class="crayon-plain-tag">&lt;ul&gt;
    &lt;li ng-repeat="(name, value) in lights" title="{{value}}"&gt;{{name}} = #{{value.id}} On:{{value.state.on}} Hue:{{value.state.hue}} Sat:{{value.state.sat}} Bri:{{value.state.bri}}&lt;/li&gt;
&lt;/ul&gt;</pre><p></p>
<p>C&rsquo;est aussi simple que cela !</p>
<p>Maintenant ajoutons une méthode « <em>ExportCurrentConfig</em> » qu&rsquo;on appellera dans notre StateObjectLink dès qu&rsquo;un StateObject est mis à jour :</p>
<p></p><pre class="crayon-plain-tag">$scope.ExportCurrentConfig = function() {
    var config = { ConfigName: "MyConfig", Lights: []};
    for(var name in $scope.lights) {
        var value = $scope.lights[name];
        config.Lights.push({ id: value.id, state: value.state.on, hue: value.state.hue, sat:value.state.sat, bri:value.state.bri });
    }
    $scope.strConfigs = JSON.stringify([ config ]).replace(/"/g, "'");
};</pre><p></p>
<p>On crée un objet avec une propriété « <em>ConfigName</em> » pour nommer notre configuration et un tableau « <em>Lights</em> » qu&rsquo;on remplit avec l&rsquo;état connu de chaque lampe. Pour finir on « <em>stringify</em> » notre objet en JSON qu&rsquo;on affichera ensuite dans un « <em>textarea</em> » sur la page :</p>
<p align="center"><a href="https://developer.myconstellation.io/wp-content/uploads/2017/05/image-88.png"><img class="colorbox-4853"  loading="lazy" style="background-image: none; padding-top: 0px; padding-left: 0px; display: inline; padding-right: 0px; border-width: 0px;" title="image" src="https://developer.myconstellation.io/wp-content/uploads/2017/05/image_thumb-87.png" alt="image" width="454" height="274" border="0" /></a></p>
<p style="text-align: left;" align="center">Il ne reste plus qu&rsquo;à générer différentes configurations notre « extracteur » pour la suite de notre tutoriel.</p>
<p style="text-align: left;" align="center">Le code complet de la page :</p>
<p></p><pre class="crayon-plain-tag">&lt;!DOCTYPE html&gt;
&lt;html xmlns="http://www.w3.org/1999/xhtml" ng-app="hue"&gt;
&lt;head&gt;
    &lt;title&gt;Hue Configuration&lt;/title&gt;
        
    &lt;script type="text/javascript" src="/Scripts/jquery-2.1.3.min.js"&gt;&lt;/script&gt;
    &lt;script type="text/javascript" src="/Scripts/angular.min.js"&gt;&lt;/script&gt;
    &lt;script type="text/javascript" src="/Scripts/jquery.signalR-2.2.0.min.js"&gt;&lt;/script&gt;
    &lt;script type="text/javascript" src="/Scripts/Constellation-1.8.1.js"&gt;&lt;/script&gt;
    &lt;script type="text/javascript" src="/Scripts/ngConstellation-1.8.1.js"&gt;&lt;/script&gt; 
    
    &lt;script&gt;
        var hue = angular.module('hue',  ['ngConstellation'])
            .controller('HueController', ['$scope', 'constellationConsumer', function ($scope, constellation) {
                $scope.lights = {};
                $scope.strConfigs = "";
            
                constellation.initializeClient("http://xxxxxxx:8088/", "demo123", "Hue Configurator");
                
                $scope.ExportCurrentConfig = function() {
                    var config = { ConfigName: "MyConfig", Lights: []};
                    for(var name in $scope.lights) {
                        var value = $scope.lights[name];
                        config.Lights.push({ id: value.id, state: value.state.on, hue: value.state.hue, sat:value.state.sat, bri:value.state.bri });
                    }
                    $scope.strConfigs = JSON.stringify([ config ]).replace(/"/g, "'");
                };

                constellation.onConnectionStateChanged(function (change) {
                    if (change.newState === $.signalR.connectionState.connected) {
                        console.log("Connected");
                        constellation.registerStateObjectLink("*", "Hue", "*", "Q42.HueApi.Light", function (stateObject) {  
                            $scope.$apply(function () {
                                $scope.lights[stateObject.Name] = stateObject.Value;    
                                $scope.ExportCurrentConfig();
                            });
                        });                        
                    }
                    else if (change.newState === $.signalR.connectionState.disconnected) {    
                        constellation.connect();
                    }
                });
                
                constellation.connect();
            }]);
    &lt;/script&gt;
&lt;/head&gt;
&lt;body&gt;
    &lt;ul&gt;
        &lt;li ng-repeat="(name, value) in lights" title="{{value}}"&gt;{{name}} = #{{value.id}} On:{{value.state.on}} Hue:{{value.state.hue}} Sat:{{value.state.sat}} Bri:{{value.state.bri}}&lt;/li&gt;
    &lt;/ul&gt;
    &lt;hr/&gt;
    &lt;p&gt;Current configuration :&lt;/p&gt;
    &lt;textarea rows="40" cols="50"&gt;{{strConfigs}}&lt;/textarea&gt;
    
&lt;/body&gt;
&lt;/html&gt;</pre><p></p>
<h4>Activer les configurations depuis interrupteur</h4>
<p>Premièrement nous allons déclarer dans le <a href="/concepts/package-manifest/">manifeste de notre package</a> (<em>PackageInfo.xml</em>) le setting « <em>Hue.Configuration</em> » par la ligne :</p>
<p></p><pre class="crayon-plain-tag">&lt;Setting name="Hue.Configurations" type="JsonObject" isRequired="true" description="Configurations lumineuses" /&gt;</pre><p></p>
<p>Le contenu de ce setting sera un tableau des différentes configurations générées par notre extracteur ci-dessus.</p>
<p>Pour ma part voici mes configurations à titre d&rsquo;exemple :</p>
<p></p><pre class="crayon-plain-tag">[
   {
      'ConfigName':'Blanc chaud',
      'DefaultConfig':true,
      'Lights':[
         {
            'id':'1',
            'state':true,
            'hue':6479,
            'sat':252,
            'bri':254
         },
         {
            'id':'2',
            'state':true,
            'hue':13907,
            'sat':187,
            'bri':179
         },
         {
            'id':'3',
            'state':true,
            'hue':13907,
            'sat':187,
            'bri':254
         },
         {
            'id':'4',
            'state':true,
            'hue':14101,
            'sat':180,
            'bri':141
         },
         {
            'id':'5',
            'state':true,
            'hue':14101,
            'sat':180,
            'bri':254
         },
         {
            'id':'6',
            'state':true,
            'hue':14101,
            'sat':180,
            'bri':161
         },
         {
            'id':'7',
            'state':true,
            'hue':12778,
            'sat':219,
            'bri':120
         },
         {
            'id':'8',
            'state':true,
            'hue':12778,
            'sat':219,
            'bri':254
         }
      ]
   },
   {
      'ConfigName':'Film du soir',
      'Lights':[
         {
            'id':'1',
            'state':true,
            'hue':7157,
            'sat':243,
            'bri':104
         },
         {
            'id':'2',
            'state':false,
            'hue':13907,
            'sat':187,
            'bri':179
         },
         {
            'id':'3',
            'state':true,
            'hue':13122,
            'sat':211,
            'bri':80
         },
         {
            'id':'4',
            'state':true,
            'hue':12778,
            'sat':219,
            'bri':142
         },
         {
            'id':'5',
            'state':true,
            'hue':13122,
            'sat':211,
            'bri':80
         },
         {
            'id':'6',
            'state':false,
            'hue':14101,
            'sat':180,
            'bri':161
         },
         {
            'id':'7',
            'state':false,
            'hue':13122,
            'sat':211,
            'bri':120
         },
         {
            'id':'8',
            'state':false,
            'hue':4712,
            'sat':241,
            'bri':254
         }
      ]
   },
   {
      'ConfigName':'Cheminée',
      'Lights':[
         {
            'id':'2',
            'state':false,
            'hue':7980,
            'sat':252,
            'bri':79
         },
         {
            'id':'8',
            'state':true,
            'hue':4712,
            'sat':241,
            'bri':254
         },
         {
            'id':'5',
            'state':true,
            'hue':13122,
            'sat':211,
            'bri':91
         },
         {
            'id':'4',
            'state':false,
            'hue':7862,
            'sat':252,
            'bri':53
         },
         {
            'id':'3',
            'state':true,
            'hue':13122,
            'sat':211,
            'bri':91
         },
         {
            'id':'6',
            'state':true,
            'hue':8774,
            'sat':252,
            'bri':56
         },
         {
            'id':'7',
            'state':true,
            'hue':13122,
            'sat':211,
            'bri':120
         },
         {
            'id':'1',
            'state':true,
            'hue':6196,
            'sat':247,
            'bri':104
         }
      ]
   },
   {
      'ConfigName':'Tout éteind',
      'OffConfig':true,
      'Lights':[
         {
            'id':'1',
            'state':false,
            'hue':7157,
            'sat':243,
            'bri':104
         },
         {
            'id':'2',
            'state':false,
            'hue':13907,
            'sat':187,
            'bri':179
         },
         {
            'id':'3',
            'state':false,
            'hue':3584,
            'sat':252,
            'bri':254
         },
         {
            'id':'4',
            'state':false,
            'hue':12778,
            'sat':219,
            'bri':142
         },
         {
            'id':'5',
            'state':false,
            'hue':13122,
            'sat':211,
            'bri':80
         },
         {
            'id':'6',
            'state':false,
            'hue':14101,
            'sat':180,
            'bri':161
         },
         {
            'id':'7',
            'state':false,
            'hue':12778,
            'sat':219,
            'bri':120
         },
         {
            'id':'8',
            'state':false,
            'hue':12778,
            'sat':219,
            'bri':254
         }
      ]
   }
]</pre><p></p>
<p>Vous remarquerez que j&rsquo;ai ajouté sur la première configuration la propriété « <em>DefaultConfig = true</em> » et « <em>OffConfig =true</em> » sur la dernière.  On se servira de ces deux propriétés pour savoir quelles sont les configurations à appliquer en cas de « On » et de « Off » sur notre interrupteur n°1.</p>
<p>Le setting est de type « JsonObject », on aura donc un bel éditeur dans la Console Constellation pour le déclarer ou le modifier. Pour vos développements vous pouvez aussi utiliser le <a href="/client-api/net-package-api/settings/">fichier App.config</a>.</p>
<p align="center"><a href="https://developer.myconstellation.io/wp-content/uploads/2017/05/image-92.png"><img class="colorbox-4853"  loading="lazy" style="background-image: none; padding-top: 0px; padding-left: 0px; display: inline; padding-right: 0px; border: 0px;" title="Configuration du setting" src="https://developer.myconstellation.io/wp-content/uploads/2017/05/image_thumb-91.png" alt="Configuration du setting" width="454" height="278" border="0" /></a></p>
<p>Pour revenir à notre code C#, nous allons tout d&rsquo;abord déclarer les variables privées suivantes :</p>
<p></p><pre class="crayon-plain-tag">private int currentConfigurationId = 0, defaultConfigurationId = 0, offConfigurationId = 0;
private List&lt;dynamic&gt; hueConfiguration = new List&lt;dynamic&gt;();</pre><p></p>
<p>Dans la méthode démarrage (<em>OnStart</em>) on charge notre setting JSON dans la variable « <em>hueConfiguration</em> » avec la méthode « <em>GetSettingAsJson</em> » puis on récupère dans ce tableau l&rsquo;index de la configuration « Default » et « Off » par la méthode .NET « <em>FindIndex</em> » :</p>
<p></p><pre class="crayon-plain-tag">hueConfiguration = new List&lt;dynamic&gt;(PackageHost.GetSettingAsJsonObject("Hue.Configurations"));
defaultConfigurationId = this.hueConfiguration.FindIndex(c =&gt; c.DefaultConfig == true);
offConfigurationId = this.hueConfiguration.FindIndex(c =&gt; c.OffConfig == true);</pre><p></p>
<p>Créons maintenant la méthode « <em>ApplyHueConfiguration</em> » qui se chargera d&rsquo;appliquer la configuration sur nos lampes Hue.</p>
<p>En quelques mots elle itère sur chaque « <em>Light</em> » de la configuration spécifiée par son index puis invoque le MessageCallback « <em>Set</em> » du package Hue en passant l&rsquo;ID de la lampe avec son état (state, hue/sat et brightness). La configuration courante est sauvegardée dans la variable « <em>currentConfigurationId</em>« .</p>
<p>Il est aussi possible de spécifier optionnellement l&rsquo;index de la configuration à exclure ce qui aura pour action d&rsquo;appliquer automatique la configuration suivante.</p>
<p></p><pre class="crayon-plain-tag">private int ApplyHueConfigration(List&lt;dynamic&gt; configurationList, int configIdx, int configToExclude = -1)
{
    // Si la config selectionnée est à exclure ...
    if (configToExclude &gt;= 0 &amp;&amp; configIdx == configToExclude)
    {
        // On passe à la configuration suivante :
        return this.ApplyHueConfigration(configurationList, (configIdx + 1) % configurationList.Count, configToExclude);
    }
    else
    {
        // On récupere la configuration à partir de son Index
        var config = configurationList[configIdx];
        PackageHost.WriteInfo("Applying Hue configuration '{0}'", config.ConfigName);
        // On applique la configuration en invoquant le MC "Set" à chaque lampe
        this.currentConfigurationId = configIdx;
        foreach (dynamic hue in config.Lights)
        {
            PackageHost.CreateMessageProxy("Hue").Set(hue.id, hue.state, hue.hue, hue.sat, hue.bri);
            Thread.Sleep(100);
        }
        // On retourne l'Index de la configuration appliquée
        return configIdx;
    }
}</pre><p></p>
<p>Maintenant modifions notre handler sur le StateObjectLink « InterrupteurHue1 » que nous avons créé précédemment.</p>
<p>Dès que cet interrupteur change d&rsquo;état on applique la configuration « Default » ou « Off » en fonction de l&rsquo;état du relais FGS-211 correspondant. On prendra garde de ne rien faire si l&rsquo;interrupteur change à « On » alors que l&rsquo;état des lampes n&rsquo;est pas éteint et inversement, on ne fera rien si l&rsquo;interrupteur change à « Off » alors que les lampes sont déjà éteintes.</p>
<p></p><pre class="crayon-plain-tag">this.InterrupteurHue1.ValueChanged += (s, e) =&gt;
{
    // Si InterrupteurHue1 change d'état
    if ((bool)e.OldState.DynamicValue.Status != (bool)e.NewState.DynamicValue.Status)
    {
        if ((bool)e.NewState.DynamicValue.Status &amp;&amp; this.currentConfigurationId != offConfigurationId)
        {
            // Ne rien faire si InterrupteurHue1 = ON et que la configuration actuelle n'est pas "tout eteint" !
            return;
        }
        else if ((bool)e.NewState.DynamicValue.Status == false &amp;&amp; this.currentConfigurationId == offConfigurationId)
        {
            // Ne rien faire si InterrupteurHue1 = OFF et que la configuration actuelle est déjà "tout eteint" !
            return;
        }
        else
        {
            // Autrement on applique la configuration "default" si InterrupteurHue1 = ON ou "off" si InterrupteurHue1 = Off
            this.ApplyHueConfigration(hueConfiguration, (bool)e.NewState.DynamicValue.Status ? defaultConfigurationId : offConfigurationId);
        }
    }
};</pre><p></p>
<p>Maintenant pour le deuxième interrupteur, dès qu&rsquo;il changera d&rsquo;état, deux cas :</p>
<ul>
<li>Si l&rsquo;interrupteur n°1 n&rsquo;est pas allumé, on invoque le MC « <em>SetSwitchState</em> » du package Vera pour l&rsquo;allumer. Ainsi son SO sera mis à jour et donc le code ci-dessus sera invoqué pour appliquer la configuration « Default » (synchronisation parfaite entre l&rsquo;état du relais Fibaro et nos lampes)</li>
<li>Si l&rsquo;interrupteur n°1 est déjà allumé, on appelle notre méthode « <em>ApplyHueConfiguration</em> » en spécifiant l&rsquo;index de la prochaine configuration et en excluant la configuration « tout éteint » (Off)</li>
</ul>
<p></p><pre class="crayon-plain-tag">// On permute les configurations avec InterrupteurHue2
this.InterrupteurHue2.ValueChanged += (s, e) =&gt;
{
    // Si InterrupteurHue2 change d'état
    if ((bool)e.OldState.DynamicValue.Status != (bool)e.NewState.DynamicValue.Status)
    {
        // Si InterrupteurHue1 = OFF, on l'allume pour garder InterrupteurHue1 syncrhonisé !
        if ((bool)this.InterrupteurHue1.DynamicValue.Status == false)
        {
            // Cela déclenchera le handler ci-dessus ce qui appliquera la configuration "default".
            PackageHost.CreateMessageProxy("Vera").SetSwitchState(new { DeviceID = (int)this.InterrupteurHue1.DynamicValue.Id, State = true });
        }
        else // Si InterrupteurHue1 est déjà ON
        {
            // ON applique la configuration suivante de facon cyclique en excluant la configuration " tout éteint"
            this.ApplyHueConfigration(hueConfiguration, (this.currentConfigurationId + 1) % hueConfiguration.Count, configToExclude: offConfigurationId);
        }
    }
};</pre><p></p>
<p>Ainsi on a bien l&rsquo;interrupteur n°1 qui contrôle le relais n° 1 du Fibaro, lui même parfaitement synchronisé avec nos lampes. Si le relais est éteint, on applique la configuration « OffConfig » de notre setting et si le relais est allumé, on applique la configuration « DefaultConfig ».</p>
<p>Quand on appuie sur l&rsquo;interrupteur n°2, on permute l&rsquo;état du relais n° 2 du Fibaro ce qui applique donc, de manière cyclique, les différentes configurations de notre setting sur nos lampes Hue.</p>
<p>On peut modifier comme bon nous semble le setting depuis la Console Constellation pour changer la configuration par défaut, ajouter ou supprimer de nouvelles ambiances ou modifier celles existantes ! De même, si ajoutez des lampes dans votre pièce vous n&rsquo;aurez qu&rsquo;à les déclarer dans votre JSON;</p>
<p>De plus, avec n&rsquo;importe quelle application ou contrôleur Z-Wave comme un Minimote par exemple, vous pouvez contrôler l&rsquo;interrupteur n°1 qui se synchronisera parfaitement avec vos lampes Hue !</p>
<h4>Pour aller plus loin</h4>
<p>Ajoutons une dernière méthode nommée « <em>ApplyHueConfiguration</em> » qui accepte en paramètre le nom de la configuration à appliquer. On l&rsquo;invoque avec le nom de la configuration (et non l&rsquo;index) et elle se chargera d&rsquo;appliquer cette configuration si elle existe bien dans votre setting.</p>
<p>Une fois n&rsquo;est pas coutume, on enverra des messages au package Vera pour synchroniser l&rsquo;état du relais n°1 si nécessaire.</p>
<p></p><pre class="crayon-plain-tag">[MessageCallback]
public int ApplyHueConfigration(string configName)
{
    // On récupere l'ID de la configuration à partir de son nom
    int configId = this.hueConfiguration.FindIndex(c =&gt; c.ConfigName == configName);
    if (configId &gt;= 0)
    {
        // On synchronise l'interrupteur Fibaro avec les lampes (sens Hue -&gt; Fibaro)
        if (configId != offConfigurationId &amp;&amp; (bool)this.InterrupteurHue1.DynamicValue.State == false)
        {
            PackageHost.CreateMessageProxy("Vera").SetSwitchState(new { DeviceID = (int)this.InterrupteurHue1.DynamicValue.Id, State = true });
        }
        else if (configId == offConfigurationId &amp;&amp; (bool)this.InterrupteurHue1.DynamicValue.State == true)
        {
            PackageHost.CreateMessageProxy("Vera").SetSwitchState(new { DeviceID = (int)this.InterrupteurHue1.DynamicValue.Id, State = false });
        }

        // On applique la configuration
        return this.ApplyHueConfigration(hueConfiguration, configId);
    }
    else
    {
        return configId;
    }
}</pre><p></p>
<p>Vous remarquerez que nous avons ajouté l&rsquo;attribut <em>[MessageCallback]</em> sur cette méthode ce qui veut dire que votre package exposera cette méthode, que l&rsquo;on nomme <em>MessageCallback</em>, pour toute votre Constellation.</p>
<p>C&rsquo;est à dire que n&rsquo;importe quel autre package C#, Python, un script Powershell ou Bash, un Arduino ou ESP8266, une page Web, etc&#8230; Tous pourront envoyer un message à votre package pour appliquer des configurations lumineuses sur vos lampes Hue en fonction des configurations que nous avez configuré dans votre setting !</p>
<p>The post <a rel="nofollow" href="https://developer.myconstellation.io/tutorials/synchroniser-interrupteur-mural-ampoules-connectee/">Synchroniser un interrupteur mural avec des ampoules connectées et contrôler l&rsquo;ambiance lumineuse de votre pièce</a> appeared first on <a rel="nofollow" href="https://developer.myconstellation.io">Constellation</a>.</p>
]]></content:encoded>
					
					<wfw:commentRss>https://developer.myconstellation.io/tutorials/synchroniser-interrupteur-mural-ampoules-connectee/feed/</wfw:commentRss>
			<slash:comments>1</slash:comments>
		
		
			</item>
	</channel>
</rss>

<!--
Performance optimized by W3 Total Cache. Learn more: https://www.boldgrid.com/w3-total-cache/?utm_source=w3tc&utm_medium=footer_comment&utm_campaign=free_plugin

Mise en cache de page à l’aide de Disk: Enhanced 

Served from: developer.myconstellation.io @ 2026-01-24 22:23:23 by W3 Total Cache
-->