artnetOctows.ino 6.0 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200
  1. /*
  2. This example will receive multiple universes via Artnet and control a strip of ws2811 leds via
  3. Paul Stoffregen's excellent OctoWS2811 library: https://www.pjrc.com/teensy/td_libs_OctoWS2811.html
  4. This example may be copied under the terms of the MIT license, see the LICENSE file for details
  5. */
  6. #include <SPI.h>
  7. #include <Artnet.h>
  8. #include <Ethernet.h>
  9. #include <EthernetUdp.h>
  10. #include <OctoWS2811.h>
  11. boolean debug = 0; //activate serial printing, !! waits for a serial input to start loop
  12. // OctoWS2811 settings
  13. const int ledsPerStrip = 300; // change for your setup
  14. const byte numStrips= 5; // change for your setup
  15. const byte wiredStrips[]={0 ,1 ,2 ,4 ,5};
  16. DMAMEM int displayMemory[ledsPerStrip*6];
  17. int drawingMemory[ledsPerStrip*6];
  18. const int config = WS2811_GRB | WS2811_800kHz;
  19. OctoWS2811 leds(ledsPerStrip, displayMemory, drawingMemory, config);
  20. // Artnet settings
  21. Artnet artnet;
  22. const int startUniverse = 0; // CHANGE FOR YOUR SETUP most software this is 1, some software send out artnet first universe as zero.
  23. const int numberOfChannels = ledsPerStrip * numStrips * 3; // Total number of channels you want to receive (1 led = 3 channels)
  24. byte channelBuffer[numberOfChannels]; // Combined universes into a single array
  25. const int DMXmax = 510; // limit number of channels read from each universe (in case the artnet software always sends 512 value)
  26. // Check if we got all universes
  27. const int maxUniverses = (int) numberOfChannels / DMXmax + ((numberOfChannels % DMXmax) ? 1 : 0);
  28. bool universesReceived[maxUniverses];
  29. bool sendFrame = 1;
  30. // Change ip and mac address for your setup
  31. boolean autoIP = 0;
  32. byte ip[] = {192, 168, 0, 101};
  33. char mac_string[20];
  34. //everything on the network needs a unique MAC
  35. #if defined(__MK20DX128__) || defined(__MK20DX256__)
  36. // Teensy 3.x has MAC burned in
  37. static byte mac[6];
  38. void read(uint8_t word, uint8_t *mac, uint8_t offset) {
  39. FTFL_FCCOB0 = 0x41; // Selects the READONCE command
  40. FTFL_FCCOB1 = word; // read the given word of read once area
  41. // launch command and wait until complete
  42. FTFL_FSTAT = FTFL_FSTAT_CCIF;
  43. while(!(FTFL_FSTAT & FTFL_FSTAT_CCIF));
  44. *(mac+offset) = FTFL_FCCOB5; // collect only the top three bytes,
  45. *(mac+offset+1) = FTFL_FCCOB6; // in the right orientation (big endian).
  46. *(mac+offset+2) = FTFL_FCCOB7; // Skip FTFL_FCCOB4 as it's always 0.
  47. }
  48. void read_mac() {
  49. read(0xe,mac,0);
  50. read(0xf,mac,3);
  51. }
  52. #else
  53. void read_mac() {}
  54. byte mac[] = {
  55. 0xDE, 0xAD, 0xBE, 0xEF, 0xFE, 0xED }; // you can find this written on the board of some Arduino Ethernets or shields
  56. #endif
  57. void print_mac() {
  58. size_t count = 0;
  59. for(uint8_t i = 0; i < 6; ++i) {
  60. if (i!=0) count += Serial.print(":");
  61. count += Serial.print((*(mac+i) & 0xF0) >> 4, 16);
  62. count += Serial.print(*(mac+i) & 0x0F, 16);
  63. }
  64. sprintf(mac_string, "%02X:%02X:%02X:%02X:%02X:%02X",mac[0],mac[1],mac[2],mac[3],mac[4],mac[5]);
  65. Serial.println();
  66. }
  67. void setup()
  68. {
  69. pinMode(9, OUTPUT);
  70. digitalWrite(9, LOW); // begin reset the WIZ820io
  71. pinMode(10, OUTPUT);
  72. digitalWrite(10, HIGH); // de-select WIZ820io
  73. pinMode(4, OUTPUT);
  74. digitalWrite(4, HIGH); // de-select the SD Card
  75. digitalWrite(9, HIGH); // end reset pulse
  76. Serial.begin(115200);
  77. artnet.begin(mac, ip);
  78. //if (autoIP){ ip [4]= ( startUniverse == 0 ) ? 1 : startUniverse ;} //
  79. if (autoIP){ ip [3]= (startUniverse + 1);} //avoid ip 0
  80. read_mac();
  81. if (debug){
  82. Serial.begin(115200);
  83. while(!Serial.available()){;} //if debug, wait until you send something to start the sketch
  84. Serial.print("mac : ");
  85. print_mac();
  86. // for (int i ; i<3 ; i++){
  87. // Serial.print(mac[i],HEX);
  88. // Serial.print("-");
  89. // }
  90. // Serial.println(mac[3],HEX);
  91. Serial.print("IP : ");
  92. for (int i ; i<3 ; i++){
  93. Serial.print(ip[i]);
  94. Serial.print(".");
  95. }
  96. Serial.println(ip[3]);
  97. Serial.print(numStrips);
  98. Serial.print(" strips of ");
  99. Serial.print(ledsPerStrip);
  100. Serial.println(" leds");
  101. }
  102. artnet.begin(mac, ip);
  103. leds.begin();
  104. initTest();
  105. // this will be called for each packet received
  106. artnet.setArtDmxCallback(onDmxFrame);
  107. }
  108. void loop()
  109. {
  110. // we call the read function inside the loop
  111. artnet.read();
  112. }
  113. void onDmxFrame(uint16_t universe, uint16_t length, uint8_t sequence, uint8_t* data)
  114. {
  115. sendFrame = 1;
  116. // Store which universe has got in
  117. if (universe < maxUniverses)
  118. if (debug){ Serial.print(universe);}
  119. universesReceived[universe] = 1;
  120. // for (int i = 0 ; i < maxUniverses ; i++)
  121. // {
  122. // if (universesReceived[i] == 0)
  123. // {
  124. // if (debug){Serial.println("Broke");}
  125. // sendFrame = 0;
  126. // break;
  127. // }
  128. // }
  129. /* ICI length serait à 512 mais devrait etre 510, d'ou décalage de deux valeurs. Il lit les valeurs 511 et 512 (qui sont à 0), la premiere
  130. valeur de l'univers suivant est donc appliquée au channel trois. Verifier, les 2-3 dernieres leds devraient etre éteintes
  131. Tester en forçant length à 510 ?
  132. cf. http://forum.pjrc.com/threads/24688-...toWS2811/page5 post #119
  133. Tester également de ne pas démarrer à l'univers 0 sur la teensy*/
  134. // read universe and put into the right part of the display buffer
  135. for (int i = 0 ; i < min(length, DMXmax) ; i++)
  136. {
  137. int bufferIndex = i + ((universe - startUniverse) * min(length, DMXmax));
  138. if (bufferIndex < numberOfChannels) // to verify
  139. channelBuffer[bufferIndex] = byte(data[i]);
  140. }
  141. // send to leds
  142. for (int i = 0; i < ledsPerStrip * numStrips; i++)
  143. {
  144. leds.setPixel(i, channelBuffer[(i) * 3], channelBuffer[(i * 3) + 1], channelBuffer[(i * 3) + 2]);
  145. }
  146. //for (int i = 0; i < numStrips; i++)
  147. //{
  148. // for (int j = 0 ; j < ledsPerStrip ; j++)
  149. // {
  150. // leds.setPixel(wiredStrips[i] * j , channelBuffer[(i) * 3], channelBuffer[(i * 3) + 1], channelBuffer[(i * 3) + 2]);
  151. // }
  152. //}
  153. if (sendFrame)
  154. {
  155. leds.show();
  156. // Reset universeReceived to 0
  157. memset(universesReceived, 0, maxUniverses);
  158. }
  159. }
  160. void initTest()
  161. {
  162. for (int i = 0 ; i < ledsPerStrip * numStrips ; i++)
  163. leds.setPixel(i, 127, 0, 0);
  164. leds.show();
  165. delay(500);
  166. for (int i = 0 ; i < ledsPerStrip * numStrips ; i++)
  167. leds.setPixel(i, 0, 127, 0);
  168. leds.show();
  169. delay(500);
  170. for (int i = 0 ; i < ledsPerStrip * numStrips ; i++)
  171. leds.setPixel(i, 0, 0, 127);
  172. leds.show();
  173. delay(500);
  174. for (int i = 0 ; i < ledsPerStrip * numStrips ; i++)
  175. leds.setPixel(i, 0, 0, 0);
  176. leds.show();
  177. }