Girouette électronique - ESP32 - serveur WiFi -code gray

Cette girouette est basée sur une roue codeuse à 16 positions codée avec un code gray réalisée avec une imprimante 3D. Elle comprend un serveur WiFi et elle est destinée à compléter ma station météo à ESP32 cliente WiFi.

1 en vidéo :


L'angle est capté par 4 phototransistors qui attaquent directement un ESP32. Ce dernier programmé en tant que serveur WiFi, décode cette information et la transmet par WiFi à tout client qui se connecte.

C'est le cas ici ; le petit afficheur LCD 3.5" est piloté par un autre ESP32 programmé en tant que client WiFi, et affiche l'angle en temps (presque) réel (2 connexions par secondes, paramétrable...)

Nous allons maintenant démonter tout ça et étudier chaque pièce en détail.

2 Vue d'ensemble

L'électronique est protégée de la pluie par un "gobelet doseur" de 160ml fournis avec une lessive liquide dont je ne me rappelle plus la marque.

3 Détail de la partie tournante

.

L'axe est un arbre rectifié de 3mm récupéré sur un ancien lecteur de disquettes 3"1/2. Les deux éléments de dominos d'électricien sont soudés sur un petit morceau de circuit imprimé en "L". La tige horizontale est un jonc de carbone. L’empennage est une carte d'alu teinté, très fine (0.2mm) au format carte de visite, découpée en biais. L'étanchéité est assurée par un petit cône en plastique qui tourne avec l'axe et englobe (sans le toucher) l'extrémité d'un tube fixé au gobelet.

4 La queue en alu léger

Je vous montre d'où provient la plaque en alu, moi je ne vends rien. Ces plaques très fines (0.2mm) sont destinées à être gravées au laser. J'ai fixé la plaque par des petites agrafes utilisées en couture 😉️

5 Le petit tube de sortie de l'axe

C'est un tube en laiton (diam 5.5mm ext, 3.5mm int) soudé sur une rondelle métallique elle même collée sur le fond du gobelet préalablement percé.

6 Le mécanisme

La roue codeuse est enfermée dans un boîtier en PLA noir imprimé en 3D.

7 Le boitier

8 La roue codeuse et le capteur à phototransisors

La plaquette de circuit imprimé sur laquelle sont soudés les phototransistors en boîtier smd 0603 est fixée à la partie plastique par deux vis de 2mm. Les trous de fixation sont oblongs ce qui permet de positionner les phototransistors exactement à l'aplomb des pistes perforées de la roue.

Comme on peut le voir, l'axe principal est monté sur roulements à billes.

9 Positionnement précis des phototransistors

Il faut pour cela desserrer très légèrement les deux écrous de M2 qui fixent la plaquette.

Côté ESP32, j'ai soudé des picots sur le bord de la platine afin de pouvoir connecter un oscilloscope à tour de rôle sur chaque capteur.

10 Test à l'oscilloscope

Pour desserrer les écrous de 2 facilement (les doigts c'est un peu trop gros, une pince plate c'est pas pratique) on peut utiliser la tête d'une vis BTR.

Il ne reste plus qu'à régler le positionnement de la platine pour obtenir des niveaux de tension bien francs vus à l'oscilloscope, lorsqu'on fait tourner manuellement le disque, et ce pour chaque capteur. On lit ici une amplitude de 3V. C'est normal, les phototransistors sont alimentés par les R de pull-up internes à l'ESP32 qui fonctionne, lui, sous 3V3. Voir schéma plus bas. Le +5V présent sur le pin "Vin" n'est utilisé (en ce qui nous concerne) que pour alimenter les LEDS d'illumination (au travers de résistances, voir schéma).

11 Test par liaison série USB

Une fois que les signaux vus à l'oscilloscope (ou mesurés avec un multimètre, si vous préférez) sont corrects, il reste à vérifier leur bonne interprétation logique. Pour cela j'ai ajouté quelques lignes au programme (voir les "Serial.println()") qui sortent l'information par la liaison série USB. Voici ci-contre ce qu'il faut obtenir (dans un moniteur série comme par exemple celui inclus dans l'IDE Arduino) lorsqu'on fait tourner lentement la girouette dans le sens horaire. Au passage on vérifie qu'il n'y a qu'un bit qui change à la fois conformément au code gray du disque. Pour connaître l'angle réel, il faut multiplier par 22.5° (=360°/16).

Je dois ici préciser que l'informaion angulaire étant également transmise par WiFi, il n'est nullement obligatoire de connecter l'ESP par le port USB, il suffit en fait de l'alimenter, par exemple par une tension de 5V appliquée entre un pin "GND" et le pin "Vin". Deux fils donc, ne véhiculant aucune information. La carte "ESP32 dev module 30 pins" comporte en outre un régulateur 3V3 pour alimenter la puce ESP32.


12 Les phototransistors

Vous avez vu la taille de ces bestioles ? 0,8mm ! Autant dire que la soudure est légèrement délicate à réaliser. J'ai gravé la plaquette directement avec une CNC. Je vous fournis d'ailleurs le g-code qui va bien.

13 Taille du phototransistor PT1921C

Le voici vu au microscope, posé sur une pièce de 1€, puis sur l'ongle de l'annulaire de ma main gauche.
Il faut en souder quatre, plus quatre LED de la même taille plus quatre résistances d'alim pour les led. Et le tout bien aligné, bien espacé, au poil quoi.

14 Vue au microscope des P1921 soudés

Une machine peut faire mieux, c'est sûr.

15 La roue codeuse code gray

J'ai imprimé la roue codeuse en PLA noir avec une imprimante 3D (une Creality Ender-3 Pro)

Pourquoi recourir au code gray plutôt qu'a un code binaire "ordinaire" ? Parce que dans le cas du code gray, lors de la rotation, il n'y a jamais plusieurs bits qui changent d'état simultanément contrairement au code binaire (ex: passage de 01 à 10 ou pire de 0000 à 1111). l'avantage ? Pour le binaire, le passage de l'état 01 à 10 peut se faire de deux façons :
01 -> 11 -> 10
ou bien :
01 -> 00 -> 10
suivant que c'est le premier ou le second bit le plus prompt à réagir (le "en même temps" est illusoire si on regarde à l'échelle de la nanoseconde)
et pour 4 bits, il y a 4! (factorielle 4) façons de passer de 1111 à 0000 soit 24 états intermédiaires différents possibles (permutations de l'ordre dans lequel les 4 bits commutent), ce qui constitue un aléas total.
Je me rappelle avoir trouvé la cause du déclenchement intempestif d'un système d'alarme (du commerce), due à ce type d'aléa (la transmission de la tension de la pile des détecteurs IR se faisait par radio, sur le même canal logique que celui servant à déclencher l'alarme. Et cette dernière se déclenchait donc de façon apparemment aléatoire lorsque l'information binaire codant la tension passait par un état imprévu mais correspondant à l'alarme. Je vous laisse compter les failles de conception de ce système ! Rassurez-vous, dans le domaine aéronautique la chose est connue et bien maîtrisée!)
Oui mais alors les ordinateurs qui utilisent le code binaire sont plein d'aléas ? En fait non, parce qu'en logique séquentielle synchrone on utilise un chef d'orchestre (une horloge à quartz) qui cadence les circuits de façon à ce que les états logiques soient pris en compte lorsque les niveaux électriques sont bien établis (sur les paliers et pas lors des commutations). Mais dans le cas qui nous occupe, il s'agit de logique combinatoire, sans horloge, les niveaux changent à des instants indéterminés, inconnus (à l'avance) du microcontrôleur. D'où la nécessité d'utiliser ce code gray.

Voici les 24 façons de passer de 1111 à 0000 : Appelons ABCD les 4 bits représentant ce nombre; Il peuvent basculer dans cet ordre A puis B puis c puis D... mais aussi A puis C puis... Voici les combinaisons possibles : ABCD, ABDC, ACBD, ACDB, ADBC, ADCB, BACD, BADC, BCAD, BCDA, BDAC, BDCA, CABD, CADB, CBAD, CBDA, CDAB, CDBA, DABC, DACB, DBAC, DBCA, DCAB, DCBA, soit 24 possibilités différentes passant par des états qui n'ont pas grand chose à voir avec la valeur finale !

Je vous fournis le fichier stl et même les sources pour FreeCAD qui vous permettent d'imprimer cette roue codeuse.

16 Dimensions du disque


Sur cette image le quadrillage est millimétrique.
  • Le trait bleu c'est le bord du disque, on voit qu'il est à 13mm du centre. Son diamètre fait donc 26mm.
  • Les encoches font 1mm de large et 1mm de matière les séparent. Leurs entraxes sont donc de 2mm, c'est ce qu'il faut retenir pour la disposition des phototransistors.
  • Le trou central fait 3mm de diamètre
  • La première encoche débute à 5mm du centre de rotation, et donc à 3,5mm du bord du trou.
J'ai utilisé une grille en mm, j'aurais pu prendre une grille en 20eme de pouces pour simplifier le placement des phototransistors avec un logiciel de CAO comme Kicad. Toutefois j'ai gravé le minuscule circuit imprimé supportant les phototransistors directement avec ma CNC (Alfawise C10 Pro) et une fraise en V (voir image ci-dessus).

17 Gravure du cuivre à la CNC

Il faudra que je vous présente l'application que j'ai programmée sous Qt5 pour générer un g-code pour graver des formes simples, traits, rectangles, cercles, facilement, sans utiliser Inkscape (dessin vectoriel, conversion en chemins, export g-code... avec plus ou moins de bonheur...)

18 Les leds d'illumination sous la roue codeuse

Ces led, ainsi que leurs résistances d'alimentation, sont elles aussi en boîtiers smd 0603.

On voit au passage que l'axe principal est monté sur roulements à billes.

19 La conception de la roue codeuse

J'ai dessiné la pièce avec le logiciel FreeCAD sous linux.

20 Dessin du boitier

Lui aussi réalisé avec FreeCAD, de même que les autres pièces, supports etc... Je vous fournis tous les fichier stl.

21 Le schéma

22 Le code source de la girouette en C++

CODE SOURCE en C++
  1. /**
  2. Girouette16pos ()
  3.  
  4. pour ESP32 30 pins
  5.  
  6.  
  7. --------------------------------------------------------------------------------------------
  8.  
  9. --------------------------------------------------------------------------------------------
  10. */
  11.  
  12.  
  13. #include <WiFi.h>
  14. #include "ESPAsyncWebServer.h"
  15.  
  16. const char* ssid = "WIND_srv";
  17. const char* password = "62z4exW58";
  18.  
  19. AsyncWebServer server(80); // Create AsyncWebServer object on port 80
  20.  
  21.  
  22. const int GPIO_input0 = 13;
  23. bool input0_etat;
  24.  
  25. const int GPIO_input1 = 12;
  26. bool input1_etat;
  27.  
  28. const int GPIO_input2 = 14;
  29. bool input2_etat;
  30.  
  31. const int GPIO_input3 = 27;
  32. bool input3_etat;
  33.  
  34.  
  35.  
  36. uint8_t v_inputs=0; // états des inputs
  37.  
  38. String angle_txt;
  39. char angle_array[3];
  40. int nb1, nb2;
  41. int angle;
  42.  
  43. uint8_t compte1=0;
  44.  
  45. String s1;
  46.  
  47.  
  48. /*
  49. void test1()
  50. {
  51. String s1;
  52. float nombre1;
  53. int nb_decimales;
  54.  
  55. nombre1= 12.6831;
  56. nb_decimales =3;
  57.  
  58. s1 = String(nombre1, nb_decimales);
  59. Serial.println(s1);
  60. }
  61. */
  62.  
  63.  
  64.  
  65.  
  66.  
  67. void setup()
  68. {
  69. Serial.begin(115200);
  70.  
  71. pinMode(GPIO_input0, INPUT_PULLUP);
  72. pinMode(GPIO_input1, INPUT_PULLUP);
  73. pinMode(GPIO_input2, INPUT_PULLUP);
  74. pinMode(GPIO_input3, INPUT_PULLUP);
  75.  
  76.  
  77. Serial.println("Setup");
  78. delay(300);
  79.  
  80.  
  81. WiFi.persistent(false);
  82. WiFi.softAP(ssid, password); // ok, ça marche, crée un réseau. mode privé
  83. IPAddress IP = WiFi.softAPIP();
  84.  
  85.  
  86. server.on("/AGL", HTTP_GET, [](AsyncWebServerRequest *request)
  87. {
  88. request->send_P(200, "text/plain", angle_array);
  89. });
  90.  
  91. server.begin();
  92.  
  93.  
  94. //Serial.println("Serveur WiFi actif!");
  95. delay(300);
  96.  
  97.  
  98.  
  99. }
  100.  
  101.  
  102.  
  103. void teste_inputs()
  104. {
  105. char array_inputs[5]= {'0','0','0','0'};
  106.  
  107.  
  108. //array_out[0] = 'G';
  109. //array_out[1] = '=';
  110.  
  111. nb1=0;
  112.  
  113. input0_etat = digitalRead(GPIO_input0);
  114. if (input0_etat==1) {array_inputs[0]='1'; nb1+=1;}
  115.  
  116. input1_etat = digitalRead(GPIO_input1);
  117. if (input1_etat==1) {array_inputs[1]='1'; nb1+=2;}
  118.  
  119.  
  120. input2_etat = digitalRead(GPIO_input2);
  121. if (input2_etat==1) {array_inputs[2]='1'; nb1+=4;}
  122.  
  123. input3_etat = digitalRead(GPIO_input3);
  124. if (input3_etat==1) {array_inputs[3]='1'; nb1+=8;}
  125.  
  126. array_inputs[4]=0; // zéro terminal
  127.  
  128. Serial.println("");
  129. Serial.print("bits=");
  130. Serial.println(array_inputs);
  131.  
  132. /*
  133. code gray :
  134. 0000
  135. 0001
  136. 0101
  137. 0100 0111
  138. 0110 1111
  139. 0111 1101
  140. 1111 1001
  141. 1110 1000
  142. 1100 1010
  143. 1101 1011
  144. 1000 0011
  145. 1010 0010
  146. 1011 0000
  147. 0011 0001
  148. 0010 0011
  149. 0000 0111
  150. 1111
  151. */
  152. }
  153.  
  154.  
  155. int decode_gray(int nb_i)
  156. {
  157. if (nb_i == 0) {return 0;}
  158. if (nb_i == 8) {return 1;}
  159. if (nb_i == 10) {return 2;}
  160. if (nb_i == 2) {return 3;}
  161. if (nb_i == 6) {return 4;}
  162. if (nb_i == 14) {return 5;}
  163. if (nb_i == 15) {return 6;}
  164. if (nb_i == 7) {return 7;}
  165. if (nb_i == 3) {return 8;}
  166. if (nb_i == 11) {return 9;}
  167. if (nb_i == 9) {return 10;}
  168. if (nb_i == 1) {return 11;}
  169. if (nb_i == 5) {return 12;}
  170. if (nb_i == 13) {return 13;}
  171. if (nb_i == 12) {return 14;}
  172. if (nb_i == 4) {return 15;}
  173. return 0;
  174. }
  175.  
  176.  
  177. void encodage_array()
  178. {
  179. angle_txt="angle=";
  180. if (angle<10) {angle_txt+="0";} // formatage sur 2 chiffres
  181. angle_txt += (String) angle;
  182.  
  183. for(int n=0; n<8; n++) {angle_array[n]=angle_txt[n];}
  184.  
  185. angle_array[8]=0; // zéro terminal -> chaine C
  186. }
  187.  
  188.  
  189.  
  190. void loop()
  191. {
  192.  
  193. nb2=0;
  194. teste_inputs();
  195. angle = decode_gray(nb1); // = 0..15 -> 16 positions de 22,5 deg chacune
  196. encodage_array(); // prépare pour envoi par wifi (qui n'interviendra qu'à la demande du client)
  197.  
  198. Serial.println(angle_array);
  199. //Serial.print("nb1="); Serial.println(nb1);
  200. //Serial.print("nb2="); Serial.println(nb2);
  201. compte1++;
  202.  
  203.  
  204. delay(500);
  205.  
  206.  
  207. }
  208.  
  209.  
  210.  

23 Le code source du client WiFi (pour test affichage)

CODE SOURCE en C++
  1. /*
  2. Horloge_TFT () + client girouette
  3.  
  4. pour ESP32 Wroom + afficheur 3.5 TFT 480x320
  5.  
  6. par Silicium628
  7.  
  8. */
  9.  
  10.  
  11. /*=====================================================================================================
  12. CONCERNANT L'AFFICHAGE TFT: connexion:
  13.  
  14. (Pensez à configurer le fichier User_Setup.h de la bibliothèque ~/Arduino/libraries/TFT_eSPI/ )
  15.  
  16. les lignes qui suivent ne sont qu'un commentaire pour vous indiquer la config à utiliser
  17. placée ici, elle ne sont pas fonctionnelles
  18. Il FAUT modifier le fichier User_Setup.h installé par le système Arduino dans ~/Arduino/libraries/TFT_eSPI/
  19.  
  20. // ESP32 pins used for the parallel interface TFT
  21. #define TFT_CS 27 // Chip select control pin
  22. #define TFT_DC 14 // Data Command control pin - must use a pin in the range 0-31
  23. #define TFT_RST 26 // Reset pin
  24.  
  25. #define TFT_WR 12 // Write strobe control pin - must use a pin in the range 0-31
  26. #define TFT_RD 13
  27.  
  28. #define TFT_D0 16 // Must use pins in the range 0-31 for the data bus
  29. #define TFT_D1 4 // so a single register write sets/clears all bits
  30. #define TFT_D2 2 // 23
  31. #define TFT_D3 22
  32. #define TFT_D4 21
  33. #define TFT_D5 15 // 19
  34. #define TFT_D6 25 // 18
  35. #define TFT_D7 17
  36. =====================================================================================================*/
  37.  
  38.  
  39. String version="1.0";
  40.  
  41. #include <stdint.h>
  42. #include <TFT_eSPI.h> // Hardware-specific library
  43. #include "Free_Fonts.h"
  44.  
  45. TFT_eSPI TFT480 = TFT_eSPI(); // Configurer le fichier User_Setup.h de la bibliothèque TFT480_eSPI au préalable
  46.  
  47. #include <WiFi.h>
  48. #include <HTTPClient.h>
  49.  
  50.  
  51. const char* ssid2 = "WIND_srv";
  52. const char* password2 = "62z4exW58";
  53.  
  54. //IP address with URL path
  55. const char* srvName_ANGLE = "http://192.168.4.1/AGL"; //.4.2 ?
  56.  
  57. const uint32_t connectTimeoutMs = 10000;
  58.  
  59. uint8_t mode = 0; // 0 ou 1
  60.  
  61. String recp_HR = "{}";
  62. String recp_ANGLE = "{}";
  63.  
  64. uint8_t WiFi_status=0;
  65.  
  66. uint32_t memoMillis = 0;
  67. uint32_t currentMillis;
  68.  
  69.  
  70. uint16_t compte1=1;
  71. float angle1=0;
  72.  
  73.  
  74.  
  75. #define NOIR 0x0000
  76. #define MARRON 0x9240
  77. #define ROUGE 0xF800
  78. #define ROSE 0xFBDD
  79. #define ORANGE 0xFBC0
  80. #define JAUNE 0xFFE0
  81. #define JAUNE_PALE 0xF7F4
  82. #define VERT 0x07E0
  83. #define VERT_FONCE 0x02E2
  84. #define OLIVE 0x05A3
  85. #define CYAN 0x07FF
  86. #define BLEU_CLAIR 0x455F
  87. #define AZUR 0x1BF9
  88. #define BLEU 0x001F
  89. #define MAGENTA 0xF81F
  90. #define VIOLET1 0x781A
  91. #define VIOLET2 0xECBE
  92. #define GRIS_TRES_CLAIR 0xDEFB
  93. #define GRIS_CLAIR 0xA534
  94. #define GRIS 0x8410
  95. #define GRIS_FONCE 0x5ACB
  96. #define GRIS_TRES_FONCE 0x2124
  97. #define BLANC 0xFFFF
  98.  
  99.  
  100.  
  101. static void smartdelay(unsigned long ms)
  102. {
  103. unsigned long start = millis();
  104. while (millis() - start < ms) {;}
  105. }
  106.  
  107.  
  108.  
  109. void httpGetAngle()
  110. {
  111. // Serial.println("envoi req HR");
  112. TFT480.fillCircle(470, 20, 5,BLEU );
  113. delay(200);
  114.  
  115.  
  116. HTTPClient http2;
  117. http2.begin(srvName_ANGLE);
  118.  
  119. int httpResponseCode = http2.GET();
  120.  
  121. if (httpResponseCode>0)
  122. {
  123. recp_ANGLE = http2.getString();
  124. TFT480.fillCircle(470, 20, 5,VERT );
  125. }
  126. http2.end();
  127.  
  128. }
  129.  
  130.  
  131. void affi_pointe(uint16_t x0, uint16_t y0, uint16_t r, double angle_i, float taille, uint16_t couleur_i)
  132. {
  133. // trace une pointe de flèche sur un cercle de rayon r
  134. // angle_i en degrés décimaux - sens trigo
  135.  
  136. float angle =angle_i/57.3; // (57.3 ~ 180/pi)
  137. int16_t x1, x2, x3;
  138. int16_t y1, y2, y3;
  139.  
  140. x1=x0+r* cos(angle); // pointe
  141. y1=y0-r* sin(angle); // pointe
  142.  
  143. x2=x0+(r-7)* cos(angle-taille); // base A
  144. y2=y0-(r-7)* sin(angle-taille); // base A
  145.  
  146. x3=x0+(r-7)* cos(angle+taille); // base B
  147. y3=y0-(r-7)* sin(angle+taille); // base B
  148.  
  149. TFT480.fillTriangle(x1, y1, x2, y2, x3, y3, couleur_i);
  150. }
  151.  
  152.  
  153. void affi_angle()
  154. {
  155. String s1, s2;
  156.  
  157. //s1="";
  158. //if(angle_i<10){s1+="0";}
  159. //s1 += String(angle_i);
  160.  
  161. s1 = String(angle1);
  162. s2= recp_ANGLE;
  163.  
  164. TFT480.setTextColor(NOIR, BLANC);
  165. TFT480.setFreeFont(FF5);
  166. TFT480.setTextSize(1);
  167. TFT480.drawString(" ANGLE > ",0,90);
  168.  
  169. TFT480.fillRect(120, 90, 90, 14, NOIR); // efface
  170. TFT480.setTextColor(VERT);
  171. TFT480.drawString(s1, 120, 90);
  172. }
  173.  
  174.  
  175.  
  176.  
  177. void affi_boussole(int x0, int y0, int dx, int dy, float angle_i)
  178. {
  179. int a1;
  180.  
  181. TFT480.drawRect(x0, y0, dx, dy, BLANC);
  182.  
  183. TFT480.fillRect(x0+1, y0+1, dx-2, dy-2, NOIR); // efface
  184.  
  185. TFT480.setFreeFont(FF0);
  186. TFT480.setTextSize(1);
  187. TFT480.drawString("N", x0+35, y0+5);
  188.  
  189. TFT480.setTextColor(BLANC);
  190.  
  191. TFT480.setFreeFont(FF5);
  192. TFT480.setTextSize(1);
  193.  
  194. TFT480.fillRect(x0+15, y0+1, 50, 53, NOIR); // efface
  195.  
  196. affi_pointe(x0+dx/2, y0+dy/2, (dy/2)-5, 90-angle_i, 2.5, CYAN);
  197.  
  198. TFT480.drawCircle(x0+dx/2, y0+dy/2, (dy/2)-2, BLANC);
  199.  
  200. TFT480.setTextColor(ROUGE);
  201. TFT480.drawString("N", -6+x0+dx/2, y0+5);
  202. TFT480.setTextColor(JAUNE);
  203. TFT480.drawString("W", x0+6, -8+y0+dy/2);
  204. TFT480.setTextColor(JAUNE);
  205. TFT480.drawString("E", x0+dx-14, -8+y0+dy/2);
  206. TFT480.setTextColor(BLEU);
  207. TFT480.drawString("S", -6+x0+dx/2, y0+dy-20);
  208.  
  209. TFT480.setFreeFont(FF0);
  210. TFT480.setTextSize(1);
  211. TFT480.setTextColor(BLANC);
  212.  
  213. a1=(int)angle_i;
  214. String s1 =String(a1);
  215. TFT480.fillRect(x0+60, y0+5, 25, 8, NOIR); // efface
  216. TFT480.drawString(s1, x0+65, y0+5);
  217. }
  218.  
  219.  
  220.  
  221. void connexion_serveur_ANGLE()
  222. {
  223. //TFT480.fillScreen(NOIR);
  224. TFT480.fillRect(0, 0, 480, 75, GRIS_TRES_FONCE); // efface
  225. TFT480.setCursor(0, 20, 4);
  226. TFT480.setFreeFont(FF5);
  227. TFT480.setTextSize(1);
  228. TFT480.setTextColor(JAUNE, NOIR);
  229. TFT480.print("Connexion au serveur ANGLE :");
  230.  
  231. WiFi.persistent(false);
  232. WiFi.begin(ssid2, password2);
  233.  
  234. delay(100);
  235.  
  236. TFT480.setTextColor(BLANC, NOIR);
  237. TFT480.setCursor(0, 40, 1);
  238. while(WiFi.status() != WL_CONNECTED)
  239. {
  240. delay(100);
  241. TFT480.print(".");
  242. }
  243.  
  244. TFT480.setCursor(0, 60, 1);
  245. TFT480.print(WiFi.localIP());
  246. }
  247.  
  248.  
  249. void affi_accueil()
  250. {
  251. TFT480.fillScreen(NOIR);
  252.  
  253. TFT480.setTextColor(BLANC, NOIR);
  254.  
  255. TFT480.setFreeFont(FF1);
  256. uint16_t y=0;
  257. TFT480.drawString("TEST AFFI", 0, y);
  258. y+=20;
  259. String s1="version " + version;
  260. TFT480.drawString(s1, 0, y);
  261. y+=20;
  262. TFT480.setTextColor(JAUNE, NOIR);
  263. TFT480.drawString("Client WiFi", 0, y);
  264. y+=40;
  265.  
  266. }
  267.  
  268.  
  269.  
  270. void setup()
  271. {
  272. Serial.begin(115200);
  273. Serial.println("Setup");
  274.  
  275. TFT480.init();
  276. TFT480.setRotation(3); // 0..3 à voir, suivant disposition de l'afficheur et sa disposition
  277. affi_accueil();
  278. delay (2000);
  279.  
  280.  
  281. TFT480.fillScreen(NOIR);
  282.  
  283. TFT480.setCursor(130, 0, 2); // Set "cursor" at top left corner of display (0,0) and select font 4
  284. TFT480.setTextColor(TFT_BLUE, TFT_BLACK);
  285. TFT480.println("Client WiFi");
  286.  
  287. delay(500);
  288.  
  289. TFT480.fillScreen(NOIR);
  290.  
  291. }
  292.  
  293. int angl_1 =0;
  294.  
  295. void loop()
  296. {
  297. //if ((compte1 % 5)==0) // toutes les 5s
  298. //if(0) // POUR TEST
  299. {
  300. WiFi.disconnect();
  301. connexion_serveur_ANGLE();
  302. recp_ANGLE = "{}";
  303. if(WiFi.status()== WL_CONNECTED )
  304. {
  305. httpGetAngle();
  306. }
  307. }
  308.  
  309. Serial.println(recp_ANGLE);
  310. String s1=recp_ANGLE.substring(0, 6);
  311. Serial.println(s1);
  312.  
  313. if(recp_ANGLE.substring(0, 6)=="angle=")
  314. {
  315. Serial.println("ok");
  316. String s2=recp_ANGLE.substring(6, 8);
  317. Serial.println(s2);
  318. angl_1 = s2.toInt();
  319. }
  320.  
  321. angle1 = 22.5*angl_1;
  322. //angle1=22.5 * compte1; // POUR TEST
  323.  
  324. affi_angle();
  325.  
  326. //affi_boussole(10, 10, 15*compte1, 10*compte1, angle1); // POUR TEST de la taille
  327.  
  328. affi_boussole(10, 150, 150, 100, angle1);
  329.  
  330. //delay(500);
  331. //angle1+=22.5;
  332. //if (angle1>359) {angle1=0;}
  333.  
  334. compte1++; if (compte1>30)
  335. {
  336. compte1=1;
  337. TFT480.fillScreen(NOIR);
  338. }
  339.  
  340. smartdelay(300);
  341.  
  342. }
  343.  
  344.  
  345.  

24 Documents

Vous trouverez ici tous les codes sources, les fichiers stl et bien plus encore...

25 -

Liens...



451