Navigation

    M5Stack Community

    • Register
    • Login
    • Search
    • Categories
    • Recent
    • Tags
    • Popular
    • Users
    • Groups
    • Search
    1. Home
    2. cepics
    C
    • Continue chat with cepics
    • Start new chat with cepics
    • Flag Profile
    • Profile
    • Following
    • Followers
    • Blocks
    • Topics
    • Posts
    • Best
    • Groups
    Save
    Saving

    cepics

    @cepics

    3
    Reputation
    143
    Posts
    1432
    Profile views
    0
    Followers
    0
    Following
    Joined Last Online

    cepics Follow

    Posts made by cepics

    • Neoflash HAT

      Hi all, I'm testing Neoflash HAT with M5StickC but with this code:

      /*
          Please install FastLED library first.
          In arduino library manage search FastLED
      */
      #include <M5StickC.h>
      #include "FastLED.h"
      
      #include "FastLED.h"
      
      FASTLED_USING_NAMESPACE
      
      // FastLED "100-lines-of-code" demo reel, showing just a few 
      // of the kinds of animation patterns you can quickly and easily 
      // compose using FastLED.  
      //
      // This example also shows one easy way to define multiple 
      // animations patterns and have them automatically rotate.
      //
      // -Mark Kriegsman, December 2014
      
      #if defined(FASTLED_VERSION) && (FASTLED_VERSION < 3001000)
      #warning "Requires FastLED 3.1 or later; check github for latest code."
      #endif
      
      #define DATA_PIN    26
      //#define CLK_PIN   4
      #define LED_TYPE    WS2811
      #define COLOR_ORDER GRB
      #define NUM_LEDS    126
      CRGB leds[NUM_LEDS];
      
      #define BRIGHTNESS          30
      #define FRAMES_PER_SECOND  120
      
      // -- The core to run FastLED.show()
      #define FASTLED_SHOW_CORE 0
      
      // -- Task handles for use in the notifications
      static TaskHandle_t FastLEDshowTaskHandle = 0;
      static TaskHandle_t userTaskHandle = 0;
      
      /** show() for ESP32
       *  Call this function instead of FastLED.show(). It signals core 0 to issue a show, 
       *  then waits for a notification that it is done.
       */
      void FastLEDshowESP32()
      {
          if (userTaskHandle == 0) {
              // -- Store the handle of the current task, so that the show task can
              //    notify it when it's done
              userTaskHandle = xTaskGetCurrentTaskHandle();
      
              // -- Trigger the show task
              xTaskNotifyGive(FastLEDshowTaskHandle);
      
              // -- Wait to be notified that it's done
              const TickType_t xMaxBlockTime = pdMS_TO_TICKS( 200 );
              ulTaskNotifyTake(pdTRUE, xMaxBlockTime);
              userTaskHandle = 0;
          }
      }
      
      /** show Task
       *  This function runs on core 0 and just waits for requests to call FastLED.show()
       */
      void FastLEDshowTask(void *pvParameters)
      {
          // -- Run forever...
          for(;;) {
              // -- Wait for the trigger
              ulTaskNotifyTake(pdTRUE, portMAX_DELAY);
      
              // -- Do the show (synchronously)
              FastLED.show();
      
              // -- Notify the calling task
              xTaskNotifyGive(userTaskHandle);
          }
      }
      
      void setup() {
        M5.begin();
        delay(3000); // 3 second delay for recovery
        Serial.begin(115200);
        M5.Lcd.setRotation(3);
        M5.Lcd.fillScreen(BLACK);
        M5.Lcd.setTextSize(2);
        M5.Lcd.setCursor(10, 0);
        M5.Lcd.setTextColor(TFT_LIGHTGREY);
      
        M5.Lcd.print("NeoFlash HAT\r\n");
        M5.Lcd.setCursor(60, 30);
        M5.Lcd.setTextColor(TFT_NAVY);
        M5.Lcd.print("RGB");
      
        M5.Lcd.setCursor(30, 50);
        M5.Lcd.print("EFFICTION");
        
        // tell FastLED about the LED strip configuration
        FastLED.addLeds<LED_TYPE,DATA_PIN,COLOR_ORDER>(leds, NUM_LEDS).setCorrection(TypicalLEDStrip);
        //FastLED.addLeds<LED_TYPE,DATA_PIN,CLK_PIN,COLOR_ORDER>(leds, NUM_LEDS).setCorrection(TypicalLEDStrip);
      
        // set master brightness control
        FastLED.setBrightness(BRIGHTNESS);
      
          int core = xPortGetCoreID();
          Serial.print("Main code running on core ");
          Serial.println(core);
      
          // -- Create the FastLED show task
          xTaskCreatePinnedToCore(FastLEDshowTask, "FastLEDshowTask", 2048, NULL, 2, &FastLEDshowTaskHandle, FASTLED_SHOW_CORE);
      }
      
      
      // List of patterns to cycle through.  Each is defined as a separate function below.
      typedef void (*SimplePatternList[])();
      SimplePatternList gPatterns = { rainbow, rainbowWithGlitter, confetti, sinelon, juggle, bpm };
      
      uint8_t gCurrentPatternNumber = 0; // Index number of which pattern is current
      uint8_t gHue = 0; // rotating "base color" used by many of the patterns
        
      void loop()
      {
        // Call the current pattern function once, updating the 'leds' array
        gPatterns[gCurrentPatternNumber]();
      
        // send the 'leds' array out to the actual LED strip
        FastLEDshowESP32();
        // FastLED.show();
        // insert a delay to keep the framerate modest
        FastLED.delay(1000/FRAMES_PER_SECOND); 
      
        // do some periodic updates
        EVERY_N_MILLISECONDS( 20 ) { gHue++; } // slowly cycle the "base color" through the rainbow
        EVERY_N_SECONDS( 10 ) { nextPattern(); } // change patterns periodically
      }
      
      #define ARRAY_SIZE(A) (sizeof(A) / sizeof((A)[0]))
      
      void nextPattern()
      {
        // add one to the current pattern number, and wrap around at the end
        gCurrentPatternNumber = (gCurrentPatternNumber + 1) % ARRAY_SIZE( gPatterns);
      }
      
      void rainbow() 
      {
        // FastLED's built-in rainbow generator
        fill_rainbow( leds, NUM_LEDS, gHue, 7);
      }
      
      void rainbowWithGlitter() 
      {
        // built-in FastLED rainbow, plus some random sparkly glitter
        rainbow();
        addGlitter(80);
      }
      
      void addGlitter( fract8 chanceOfGlitter) 
      {
        if( random8() < chanceOfGlitter) {
          leds[ random16(NUM_LEDS) ] += CRGB::White;
        }
      }
      
      void confetti() 
      {
        // random colored speckles that blink in and fade smoothly
        fadeToBlackBy( leds, NUM_LEDS, 10);
        int pos = random16(NUM_LEDS);
        leds[pos] += CHSV( gHue + random8(64), 200, 255);
      }
      
      void sinelon()
      {
        // a colored dot sweeping back and forth, with fading trails
        fadeToBlackBy( leds, NUM_LEDS, 20);
        int pos = beatsin16( 13, 0, NUM_LEDS-1 );
        leds[pos] += CHSV( gHue, 255, 192);
      }
      
      void bpm()
      {
        // colored stripes pulsing at a defined Beats-Per-Minute (BPM)
        uint8_t BeatsPerMinute = 62;
        CRGBPalette16 palette = PartyColors_p;
        uint8_t beat = beatsin8( BeatsPerMinute, 64, 255);
        for( int i = 0; i < NUM_LEDS; i++) { //9948
          leds[i] = ColorFromPalette(palette, gHue+(i*2), beat-gHue+(i*10));
        }
      }
      
      void juggle() {
        // eight colored dots, weaving in and out of sync with each other
        fadeToBlackBy( leds, NUM_LEDS, 20);
        byte dothue = 0;
        for( int i = 0; i < 8; i++) {
          leds[beatsin16( i+7, 0, NUM_LEDS-1 )] |= CHSV(dothue, 200, 255);
          dothue += 32;
        }
      }
      

      but only fist line of neoflash Hat works....

      ideas??
      tnks a lot

      posted in M5 Stick/StickC
      C
      cepics
    • RE: TAIL485

      nobody?

      posted in Modules
      C
      cepics
    • TAIL485

      hi all,
      I'm reading a serial machine data out , on ATOM, with this RS422/TTL YL-128 adaptor
      datasheet

      with this code

      void setup() {
      
        Serial.begin(115200);
        delay(1000);
      
      //              speed, mode,      rx, tx
        Serial2.begin(9600, SERIAL_8N1, 26, 32);
        delay(1000);
      
      void loop() {
        recvBytesWithStartEndMarkers();
        showNewData();
      }
      
      void recvBytesWithStartEndMarkers() {
        static boolean recvInProgress = false;
        static byte ndx = 0;
        byte startMarker = 0x7C; // "|"
        byte endMarker = 0x0A; // (LF) "/n"
      
        //  byte startMarker = 0x0A; // "/n"
        //  byte endMarker = 0x0D; // (CR) "/r"
      
      
        byte rb;
      
        while (Serial2.available() > 0 && newData == false) {
          rb = Serial2.read();
      
          if (recvInProgress == true) {
            if (rb != endMarker) {
              receivedBytes[ndx] = rb;
              ndx++;
              if (ndx >= numBytes) {
                ndx = numBytes - 1;
              }
            }
            else {
              receivedBytes[ndx] = '\0'; // terminate the string
              recvInProgress = false;
      
              numReceived = ndx;  // save the number for use when printing
              ndx = 0;
              newData = true;
            }
          }
      
          else if (rb == startMarker) {
            recvInProgress = true;
          }
        }
      }
      
      void showNewData() {
        if (newData == true) {
      
          //    Serial.print(" ... HEX Value.. ");
          for (byte n = 0; n < numReceived; n++) {
            Serial.print(receivedBytes[n], HEX);
            Serial.print(' ');
      
            if (receivedBytes[numReceived - 3] == 0x36 && receivedBytes[numReceived - 6] == 0x30) {
              unit = 0; // CM ARRI 60
            }
      
            if (receivedBytes[numReceived - 3] == 0x37 && receivedBytes[numReceived - 6] == 0x30) {
              unit = 1; //FT ARRI 70
            }
      
            if (unit == 0 && receivedBytes[numReceived - 6] == 0x31) {
              cm = receivedBytes[numReceived - 4] * 100 + receivedBytes[numReceived - 3] * 10 + receivedBytes[numReceived - 2];
      
            }
            if (unit == 1 && receivedBytes[numReceived - 6] == 0x31) {
              ft = receivedBytes[numReceived - 5] * 10 + receivedBytes[numReceived - 4];
              inc = receivedBytes[numReceived - 3] * 10 + receivedBytes[numReceived - 2];
      
            }
          }
          Serial.println();
          Serial.print ("cm ");
          Serial.println (cm);
          Serial.print ("ft ");
          Serial.println (ft);
          Serial.print ("inc ");
          Serial.println (inc);
      
          newData = false;
      
        }
      }
      

      and this connections:

      machine----------------------------- RS422/TTL
      grd ------------------------------------ A ............. Y-----NC
      sgl ------------------------------------- B ............. Z----NC
      12V ----- +12v

      RS422/TTL ---------- ATOM
      TX ---------------------- RX
      RX -----------------------TX
      5V ---------------------- 5V
      GRD -------------------- GRD

      the newbie question is:

      can I use instead RS485 module based on SP485EEN-L ??

      tnks a lot

      posted in Modules
      C
      cepics
    • RE: KinoWheels M5Stack porting WIP...

      RESERVED

      posted in PROJECTS
      C
      cepics
    • KinoWheels M5Stack porting WIP...

      Hi All, this is my porting of KinoWheels to m5stack using espnow to play wireless with R0nin

      tested with:
      R0nin 1

      KinoWheels
      R0nin Forum

      TX: M5Stack + PROTO MODULE
      RX: M5Atom Lite + GROVE cable

      SOFTWARE:

      first we upload rx code to know the mac address on serial monitor

      in the arduino IDE select M5StickC board for ATOM

      #include "M5Atom.h"
      #include <esp_now.h>
      #include <WiFi.h>
      
      #define WIFI_CHANNEL 1
      uint8_t localCustomMac[] = {0x36, 0x33, 0x33, 0x33, 0x33, 0x33};
      const byte maxDataFrameSize = 200;
      
      // must match the controller struct
      struct __attribute__((packed)) DataStruct {
        int X;
        int Y;
        int Z;
      };
      DataStruct myData;
      
      #define BAUDRATE 100000  // oder  100000 115200
      #define SERIALPORT Serial2  // - uncomment this line if using an arduino based board with more than one HW serial port
      
      
      class BMC_SBUS
      {
        public:
          uint8_t sbusData[25];
          int16_t servos[18];
          void begin(void);
          void Servo(uint8_t ch, int16_t position);
          void Send(void);
          void Update(void);
      
        private:
          uint8_t byte_in_sbus;
          uint8_t bit_in_sbus;
          uint8_t ch;
          uint8_t bit_in_servo;
      };
      
      
      void BMC_SBUS::begin()
      {
        //intialise private data arrays
        //sbus_data is formatted for correct serial output
        //note that the actual 11bit sbus data for each channel is embedded across multiple data bytes in a very stange order
        //byte 1 and bytes 24 and 25 should be left as is
        //the first is a start byte, the last is a stop byte and the second last holds various flags
        //servos is the internal per channel position and is more straightforward - one int_16 per channel
      
        uint8_t loc_sbusData[25] = {0x0f, 0x01, 0x04, 0x20, 0x00, 0xff, 0x07, 0x40, 0x00, 0x02, 0x10, 0x80, 0x2c, 0x64, 0x21, 0x0b, 0x59, 0x08, 0x40, 0x00, 0x02, 0x10, 0x80, 0x00, 0x00};
        int16_t loc_servos[18]   = {1023, 1023, 1023, 1023, 1023, 1023, 1023, 1023, 1023, 1023, 1023, 1023, 1023, 1023, 1023, 1023, 0, 0};
      
        //setup serial port to transmit at 100k baud and use 1 parity and 2 stop bits
        //               (baud-rate/protocol/RXpin/TXpin/INVERT)
          SERIALPORT.begin(BAUDRATE, SERIAL_8E2, 32, 26, true); // ATOM GROVE PORT 
      
        //setup public data arrays
      
        memcpy(sbusData, loc_sbusData, 25);
        memcpy(servos, loc_servos, 18);
      }
      
      void BMC_SBUS::Servo(uint8_t ch, int16_t position)
      {
        //set servo position on single channel
      
        if ((ch > 0) && (ch <= 16))
        {
          constrain (position, 0, 2048); //keep within min/max values
          servos[ch - 1] = position; //expects a non zero starting index to the channel
        }
      }
      
      void BMC_SBUS::Send(void)
      {
        //send data over serial port
        SERIALPORT.write(sbusData, 25); //according to docs for Serial we can send the array along as is without a loop
      }
      
      void BMC_SBUS::Update(void)
      {
        //update positions for all servo channels within the SBUS data frame
        //ignores digital servos and any failsafe mode stuff that was originally written
      
        //clear out existing sbus data for all channel data bytes
        //ignores first and last bytes in the array (start and stop bytes)
        //mapping loop relies on initial 0 values - do not omit this step!
      
        uint8_t i;
        for (i = 1; i < 24; i++)
        {
          sbusData[i] = 0;
        }
      
        //reset counters
      
        ch = 0;
        bit_in_servo = 0;
        byte_in_sbus = 1;
        bit_in_sbus = 0;
      
        //format sbus data - maps sevo data array to sbus data array 1bit at a time
        //correctly deals with the little endian byte order in the process
      
        for (i = 0; i < 176; i++) //16channels*11bits = 176bits
        {
          if (servos[ch] & (1 << bit_in_servo)) //bitwise AND to check if the correct servo databit is set to 1
          {
            sbusData[byte_in_sbus] |= (1 << bit_in_sbus); //bitwise OR sets the correct sbus databit if true
          }
      
          //increment bit counters
      
          bit_in_sbus++;
          bit_in_servo++;
      
          //if end of sbus byte reset sbus bit counter and increment sbus byte counter
      
          if (bit_in_sbus == 8)
          {
            bit_in_sbus = 0;
            byte_in_sbus++;
          }
      
          // if we have reached bit 11 in the servo data increment channel index and reset servo bit counter
      
          if (bit_in_servo == 11)
          {
            bit_in_servo = 0;
            ch++;
          }
        }
      }
      
      //Declare BMC_SBUS Object
      BMC_SBUS mySBUS;
      
      // Sbus delay value
      const int sbusWAIT = 7;      //frame timing delay in msecs
      
      // Declare sbus control channels
      int panChannel = 1;
      int tiltChannel = 2;
      int rollChannel = 4;
      
      
      int sentX;
      int sentY;
      int sentZ;
      
      
      /* ********************************************************
        /*                      Void setup                           *
        /* ****************************************************** */
      void setup() {
      
        //  M5.begin();
        M5.begin(true, false, true);
        Serial.begin(115200);
        delay(200);
        Serial.print("\r\n\r\n");
        WiFi.mode(WIFI_AP);
        Serial.println( WiFi.softAPmacAddress() );
        WiFi.disconnect();
        if (esp_now_init() == ESP_OK)
        {
          Serial.println("ESPNow Init Success!");
        }
        else
        {
          Serial.println("ESPNow Init Failed....");
        }
        esp_now_register_recv_cb(OnDataRecv);
      
        sentX = 1023;
        sentY = 1023;
        sentZ = 1023;
      
        // Start BMC_SBUS object
        mySBUS.begin();
      
      }
      
      /* ********************************************************
        /*                      Void Loop                           *
        /* ****************************************************** */
      void loop() { 
      
        sentX = (myData.X);
        sentY = (myData.Y);
        sentZ = (myData.Z);
      
      //  Serial.print("sentX ");
      //  Serial.println(sentX);
      //  Serial.print("sentY ");
      //  Serial.println(sentY);
      //  Serial.print("sentZ ");
      //  Serial.println(sentZ);
      
        for (int i = 0; i < 1; i++) {   //SBUS needs data every 7 Milliseconds. I repeat it three times for some time to pass for calculating speeds.
      
          mySBUS.Servo(panChannel, sentX);
          mySBUS.Servo(tiltChannel, sentY);
          mySBUS.Servo(rollChannel, sentZ);
      
          // Update SBUS object and send data
          mySBUS.Update();
          mySBUS.Send();
      
          delay(sbusWAIT);
      
        }
      
        if (M5.Btn.wasPressed())
        {}
      
        M5.update();
      }
      
      
      void OnDataRecv(const uint8_t *mac_addr, const uint8_t *incomingData, int data_len)
      {
        memcpy(&myData, incomingData, sizeof(myData));
        Serial.print ("MAC ADDRES = ");
        for (byte n = 0; n < 6; n++) {
          Serial.print (mac_addr[n], HEX);
        }
        stato ++;
        Serial.println ();
      }
      

      open arduino serial monitor and pick the receiver MAC ADDRESS.

      put the receiver MAC ADDRESS, in the TX code instead of "XX"

      
      #include <M5Stack.h>
      
      #include <ESP32Encoder.h>
      
      ESP32Encoder encoderX;
      ESP32Encoder encoderY;
      
      ////////////////////ESPNOW/////////////////////////
      #include <esp_now.h>
      #include <WiFi.h>
      
      #define WIFI_CHANNEL 1
      
      esp_now_peer_info_t slave;
      
      // RX MAC ADDRESS HERE
      uint8_t remoteMac[] = {0xXX, 0xXX, 0xXX, 0xXX, 0xXX, 0xXX};
      
      const uint8_t maxDataFrameSize = 200;
      
      // must match the controller struct
      struct __attribute__((packed)) DataStruct {
      
        int X;
        int Y;
        int Z;
      
      };
      DataStruct myData;
      const esp_now_peer_info_t *peer = &slave;
      uint8_t dataToSend[maxDataFrameSize];
      
      unsigned long lastSentMillis;
      unsigned long sendIntervalMillis = 10;
      unsigned long sentMicros;
      unsigned long ackMicros;
      
      ///////////////////////////FINE ESPNOW///////////////
      
      int xStampEnd = 0, yStampEnd = 0, timeStampEnd = 0;
      int xPassed, yPassed, timePassed;
      int X = 1023, Y = 1023, Z = 1023;
      int pulsesX, pulsesY;
      int  potiX = 100,  potiY = 100;
      
      byte gearX = 2;
      byte gearY = 2;
      
      bool toggleZ;
      bool toggleUSD;
      
      //bool StatoRX;
      
      
      void setup() {
        M5.begin();
        Serial.begin(115200);
      
        M5.Lcd.clear(BLACK);
      
        M5.Lcd.fillRoundRect(5, 10, 310, 150, 10, TFT_BLACK);
        M5.Lcd.fillRoundRect(15, 20, 290, 130, 5, TFT_YELLOW);
        M5.Lcd.fillRoundRect(25, 30, 270, 110, 55, TFT_BLACK);
      
        M5.Lcd.fillRoundRect(5, 150, 310, 90, 10, TFT_BLACK);
        M5.Lcd.fillRoundRect(15, 160, 290, 70, 5, TFT_YELLOW);
        M5.Lcd.fillRoundRect(25, 170, 270, 50, 25, TFT_BLACK);
      
        M5.Lcd.setTextColor(RED);
        M5.Lcd.setTextSize(5);
        M5.Lcd.setCursor(80, 60);
        M5.Lcd.println("RONIN");
        M5.Lcd.setTextColor(YELLOW);
        M5.Lcd.setCursor(55, 180);
        M5.Lcd.println("P");
        M5.Lcd.setCursor(245, 180);
        M5.Lcd.println("T");
      
        M5.update();
      
        Serial.print("\r\n\r\n");
        WiFi.mode(WIFI_STA);
        Serial.println( WiFi.softAPmacAddress() );
        WiFi.disconnect();
        if (esp_now_init() == ESP_OK)
        {
          Serial.println("ESP NOW INIT!");
        }
        else
        {
          Serial.println("ESP NOW INIT FAILED....");
        }
        memcpy( &slave.peer_addr, &remoteMac, 6 );
        slave.channel = WIFI_CHANNEL;
        slave.encrypt = 0;
        if ( esp_now_add_peer(peer) == ESP_OK)
        {
          Serial.println("Added Peer!");
          Serial.println();
        }
        esp_now_register_send_cb(OnDataSent);
      
        ///////////////////////////////////////////////////////////////////////////////
      
        // clear the encoder's raw count and set the tracked count to zero
        encoderX.clearCount();
        encoderY.clearCount();
      
        // Attache pins for use as encoder pins
        encoderX.attachHalfQuad(2, 3);
        encoderY.attachHalfQuad(34, 35);
      
        //////////////////////////////////////////////////////////
        Serial.println("<ready>");
      }
      
      void loop() {
        M5.update();
        ariloop();
        M5.update();
        sendData();
        Serial.print("x");
        Serial.print(pulsesX);
        Serial.print("y");
        Serial.print(pulsesY);
        Serial.println("end");
        delay(20); // PROVARE A TOGLIERLA
      }
      
      void ariloop() {
        pulsesX = encoderX.getCount();
        pulsesY = encoderY.getCount();
      
        timePassed = millis() - timeStampEnd;
        xPassed = xStampEnd - pulsesX;
        yPassed = pulsesY - yStampEnd;
      
        if (M5.BtnC.wasReleased()) {
          gearY ++;
          if (gearY == 4) {
            gearY = 1;
          }
          M5.Lcd.fillRoundRect(25, 170, 270, 50, 25, TFT_BLACK);
          if (toggleUSD) {
            M5.Lcd.setCursor(140, 180);
            M5.Lcd.println("UP");
          }
          M5.Lcd.setCursor(55, 180);
          M5.Lcd.println("P");
          M5.Lcd.setCursor(105, 180);
          M5.Lcd.println(gearX);
          M5.Lcd.setCursor(205, 180);
          M5.Lcd.println("T");
          M5.Lcd.setCursor(255, 180);
          M5.Lcd.println(gearY);
          delay(200);
        } else if (M5.BtnB.wasReleased()) {
          toggleZ = !toggleZ;
          if (toggleZ) {
            M5.Lcd.fillRoundRect(25, 170, 270, 50, 25, TFT_BLACK);
            M5.Lcd.setCursor(55, 180);
            M5.Lcd.println("(");
            M5.Lcd.setCursor(120, 180);
            M5.Lcd.println("ROLL");
            M5.Lcd.setCursor(255, 180);
            M5.Lcd.println(")");
          } else {
            M5.Lcd.fillRoundRect(25, 170, 270, 50, 25, TFT_BLACK);
            if (toggleUSD) {
              M5.Lcd.setCursor(140, 180);
              M5.Lcd.println("UP");
            }
            M5.Lcd.setCursor(55, 180);
            M5.Lcd.println("P");
            M5.Lcd.setCursor(105, 180);
            M5.Lcd.println(gearX);
            M5.Lcd.setCursor(205, 180);
            M5.Lcd.println("T");
            M5.Lcd.setCursor(255, 180);
            M5.Lcd.println(gearY);
            delay(200);
          }
          delay(200);
      
        } else if (M5.BtnA.wasReleased()) {
          gearX ++;
          if (gearX == 4) {
            gearX = 1;
          }
          M5.Lcd.fillRoundRect(25, 170, 270, 50, 25, TFT_BLACK);
          if (toggleUSD) {
            M5.Lcd.setCursor(140, 180);
            M5.Lcd.println("UP");
          }
          M5.Lcd.setCursor(55, 180);
          M5.Lcd.println("P");
          M5.Lcd.setCursor(105, 180);
          M5.Lcd.println(gearX);
          M5.Lcd.setCursor(205, 180);
          M5.Lcd.println("T");
          M5.Lcd.setCursor(255, 180);
          M5.Lcd.println(gearY);
          delay(200);
      
        } else if (M5.BtnB.wasReleasefor(700)) {
          toggleUSD = !toggleUSD;
          if (toggleUSD) {
            M5.Lcd.fillRoundRect(25, 170, 270, 50, 25, TFT_BLACK);
            M5.Lcd.setCursor(140, 180);
            M5.Lcd.println("UP");
            M5.Lcd.setCursor(55, 180);
            M5.Lcd.println("P");
            M5.Lcd.setCursor(105, 180);
            M5.Lcd.println(gearX);
            M5.Lcd.setCursor(205, 180);
            M5.Lcd.println("T");
            M5.Lcd.setCursor(255, 180);
            M5.Lcd.println(gearY);
            delay(200);
          } else {
            M5.Lcd.fillRoundRect(25, 170, 270, 50, 25, TFT_BLACK);
            M5.Lcd.setCursor(55, 180);
            M5.Lcd.println("P");
            M5.Lcd.setCursor(105, 180);
            M5.Lcd.println(gearX);
            M5.Lcd.setCursor(205, 180);
            M5.Lcd.println("T");
            M5.Lcd.setCursor(255, 180);
            M5.Lcd.println(gearY);
            delay(200);
          }
      
        }
      
        if (M5.BtnA.isPressed() && toggleZ) {
          Z = 723;   //823, 1023, 1223
          delay(100);
      
        }   else if (M5.BtnC.isPressed() && toggleZ) {
          Z = 1323;//823, 1023, 1223
          delay(100);
      
        } else {
          Z = 1023;  //823, 1023, 1223
        }
      
        if (gearX == 1) {
          potiX = 100;
        }
        if (gearX == 2) {
          potiX = 200;
        }
        if (gearX == 3) {
          potiX = 300;
        }
      
        if (gearY == 1) {
          potiY = 100;
        }
        if (gearY == 2) {
          potiY = 200;
        }
        if (gearY == 3) {
          potiY = 300;
        }
      
        if (toggleUSD) {
          // GRAFICA UPSIDEDOWN
          potiX = potiX * - 1;
          potiY = potiY * - 1;
        } else {
          // GRAFICA DRITTA
        }
      
        X = 1023 + potiX * xPassed / timePassed;
        Y = 1023 + potiY * yPassed / timePassed;
      
        pulsesX = encoderX.getCount();
        pulsesY = encoderY.getCount();
      
        xStampEnd = pulsesX;
        yStampEnd = pulsesY;
        timeStampEnd = millis();
      
      }
      
      void sendData() {
        if (millis() - lastSentMillis >= sendIntervalMillis) {
          lastSentMillis += sendIntervalMillis;
      
          myData.X = X;
          myData.Y = Y;
          myData.Z = Z;
      
          uint8_t bs[sizeof(myData)];
          memcpy(bs, &myData, sizeof(myData));
          sentMicros = micros();
          esp_now_send(NULL, bs, sizeof(myData)); // NULL means send to all peers
          Serial.println("  sent data");
          Serial.println();
        }
      }
      
      void OnDataSent(const uint8_t *mac_addr, esp_now_send_status_t status)
      {
        if (status == ESP_NOW_SEND_SUCCESS) {
          Serial.println("RX ACCESO");
          M5.Lcd.fillCircle(60, 60, 10, TFT_GREEN);
          //    StatoRX = 1;
        } else {
          Serial.println("RX SPENTO");
          M5.Lcd.fillCircle(60, 60, 10, TFT_RED);
          //    StatoRX = 0;
        }
        Serial.println();
      }
      

      HARDWARE
      encoders wiring on M5Stack is a bit different of original kinowheels (arduino mega) one.

      0_1590398679133_Screen Shot 2020-05-25 at 11.21.09.png

      with esp32 based board you can invert ttl signal in serial.begin declaration... so no need to add a serial inverter IC for D-Bus, so ATOM GROVE cable go straight to R0nin D-Bus

      GROVE ------ D-BUS
      GRD ---------- Black
      5V ------------ Red
      TX ------------ White
      RX ------------- Yellow (not connected on R0nin1) to test on R0nin2

      this is the code to use M5Stack kinowheels in the simulator:

      #include <M5Stack.h>
      #include <ESP32Encoder.h>
      
      ESP32Encoder encoderX;
      ESP32Encoder encoderY;
      
      float pulsesX, pulsesY;
      
      void setup() {
        M5.begin();
      
        M5.Lcd.clear(BLACK);
      
        M5.Lcd.fillRoundRect(5, 10, 310, 150, 10, TFT_BLACK);
        M5.Lcd.fillRoundRect(15, 20, 290, 130, 5, TFT_YELLOW);
        M5.Lcd.fillRoundRect(25, 30, 270, 110, 55, TFT_BLACK);
      
        M5.Lcd.fillRoundRect(5, 150, 310, 90, 10, TFT_BLACK);
        M5.Lcd.fillRoundRect(15, 160, 290, 70, 5, TFT_YELLOW);
        M5.Lcd.fillRoundRect(25, 170, 270, 50, 25, TFT_BLACK);
      
        M5.Lcd.setTextColor(RED);
        M5.Lcd.setTextSize(5);
        M5.Lcd.setCursor(130, 40);
        M5.Lcd.println("PC");
        M5.Lcd.setTextColor(YELLOW);
        M5.Lcd.setCursor(55, 180);
        M5.Lcd.println("T");
        M5.Lcd.setCursor(245, 180);
        M5.Lcd.println("P");
      
        M5.update();
      
        Serial.begin(115200);
      
        // clear the encoder's raw count and set the tracked count to zero
        encoderX.clearCount();
        encoderY.clearCount();
      
        // Attache pins for use as encoder pins
        encoderX.attachHalfQuad(2, 3);
        encoderY.attachHalfQuad(34, 35);
      
      }
      
      void loop() {
      
        pulsesX = encoderX.getCount();
        pulsesY = encoderY.getCount();
      
        Serial.print("x");
        Serial.print(pulsesX);
        Serial.print("y");
        Serial.print(pulsesY);
        Serial.println("end");
        delay(20);
      }
      

      I want to use this case in the future...
      NaKino

      posted in PROJECTS
      C
      cepics
    • Automotive Infrared Short Range Lidar Sensor

      Hi all,
      I'm trying to read the output of this automotive lidar sensor..

      after powering (12v DC) I can see the illuminator..

      I tested the output of the two twisted couple of wire with a oscilloscope:
      attached images..
      1

      2

      the datasheet say two can interface output...

      I would like to read the sensor output with M5Stack..

      do the oscilloscope waves looks like a CAN output?

      is it ok to connect to M5Stack by COMMU module?

      tnk a lot!

      posted in PROJECTS
      C
      cepics
    • RE: (SOLVED)SD Uploader can't flash new code

      I solved like that:

      with M5Burner flash a different firmware in the stack like uiflow
      and than flash again lovian firmware..

      tnks

      posted in Arduino
      C
      cepics
    • BMC_SBUS M5Stack porting

      Hi all
      I'm trying to port an Arduino Mega sketch, using BMC_SBUS, to M5Stack!!
      https://github.com/boldstelvis/BMC_SBUS ... /README.md
      to use this: https://www.kinowheels.com/
      with this: https://forum.dji.com/thread-167232-1-1.html
      this is the connections: https://forum11.djicdn.com/data/attachm ... htjjsl.png

      this is the Arduino Mega sketch connected to the ronin D-bus (it works!! I can move the ronin X and Y axis):

      #define BAUDRATE 100000  // oder  100000 115200
      #define SERIALPORT Serial  // - uncomment this line if using an arduino based board with more than one HW serial port
      
      class BMC_SBUS
      {
        public:
          uint8_t sbusData[25];
          int16_t servos[18];
          void begin(void);
          void Servo(uint8_t ch, int16_t position);
          void Send(void);
          void Update(void);
      
        private:
          uint8_t byte_in_sbus;
          uint8_t bit_in_sbus;
          uint8_t ch;
          uint8_t bit_in_servo;
      };
      
      
      void BMC_SBUS::begin()
      {
        //intialise private data arrays
        //sbus_data is formatted for correct serial output
        //note that the actual 11bit sbus data for each channel is embedded across multiple data bytes in a very stange order
        //byte 1 and bytes 24 and 25 should be left as is 
        //the first is a start byte, the last is a stop byte and the second last holds various flags
        //servos is the internal per channel position and is more straightforward - one int_16 per channel
      
        uint8_t loc_sbusData[25] = {0x0f,0x01,0x04,0x20,0x00,0xff,0x07,0x40,0x00,0x02,0x10,0x80,0x2c,0x64,0x21,0x0b,0x59,0x08,0x40,0x00,0x02,0x10,0x80,0x00,0x00};
        int16_t loc_servos[18]   = {1023,1023,1023,1023,1023,1023,1023,1023,1023,1023,1023,1023,1023,1023,1023,1023,0,0};
      
        //setup serial port to transmit at 100k baud and use 1 parity and 2 stop bits
      
        SERIALPORT.begin(BAUDRATE, SERIAL_8E2);
      
        //setup public data arrays
      
        memcpy(sbusData,loc_sbusData,25);
        memcpy(servos,loc_servos,18);
      }
      
      void BMC_SBUS::Servo(uint8_t ch, int16_t position) 
      {
        //set servo position on single channel
      
        if ((ch>0)&&(ch<=16)) 
        {
          constrain (position, 0, 2048); //keep within min/max values
          servos[ch-1] = position; //expects a non zero starting index to the channel
        }
      }
      
      void BMC_SBUS::Send(void)
      {
        //send data over serial port
        SERIALPORT.write(sbusData, 25); //according to docs for Serial we can send the array along as is without a loop
      }
      
      void BMC_SBUS::Update(void) 
      {
        //update positions for all servo channels within the SBUS data frame
        //ignores digital servos and any failsafe mode stuff that was originally written
      
        //clear out existing sbus data for all channel data bytes
        //ignores first and last bytes in the array (start and stop bytes)
        //mapping loop relies on initial 0 values - do not omit this step!
      
        uint8_t i;
        for (i=1; i<24; i++) 
        {
          sbusData[i] = 0;
        }
      
        //reset counters
      
        ch = 0;
        bit_in_servo = 0;
        byte_in_sbus = 1;
        bit_in_sbus = 0;
      
        //format sbus data - maps sevo data array to sbus data array 1bit at a time
        //correctly deals with the little endian byte order in the process
      
        for (i=0; i<176; i++) //16channels*11bits = 176bits
        {
          if (servos[ch] & (1<<bit_in_servo)) //bitwise AND to check if the correct servo databit is set to 1
          {
            sbusData[byte_in_sbus] |= (1<<bit_in_sbus); //bitwise OR sets the correct sbus databit if true
          }
      
          //increment bit counters
      
          bit_in_sbus++;
          bit_in_servo++;
      
          //if end of sbus byte reset sbus bit counter and increment sbus byte counter
      
          if (bit_in_sbus == 8) 
          {
            bit_in_sbus = 0;
            byte_in_sbus++;
          }
      
          // if we have reached bit 11 in the servo data increment channel index and reset servo bit counter
      
          if (bit_in_servo == 11) 
          {
            bit_in_servo = 0;
            ch++;
          }
        }
      }
      
      
      //Declare BMC_SBUS Object
      BMC_SBUS mySBUS;
      
      // Sbus delay value
      const int sbusWAIT = 7;      //frame timing delay in msecs
      
      // Declare sbus control channels
      int panChannel = 1;
      int tiltChannel = 2;
      int rollChannel = 4;
      
      
      // Declare Kinowheels Stuff
      int XA_SIG=0, XB_SIG=1, YA_SIG=0, YB_SIG=1, pulsesX, pulsesY;
      
      // Declare Stuff for calculating Speed
      int xStampEnd=0, yStampEnd=0, timeStampEnd=0, xPassed, yPassed, timePassed, sendX=1023, sendY=1023;
      
      
      
      
      void setup() {
        // Serial.begin(100000); überflüssig, weil in MC_SBUS enthalten
      
      
        // Start  KinoWheels Stuff
        attachInterrupt(0, XA_RISE, RISING); // Pin 2
        attachInterrupt(1, XB_RISE, RISING); // Pin 3
        attachInterrupt(4, YA_RISE, RISING); // Pin 19
        attachInterrupt(5, YB_RISE, RISING); // Pin 18
         
        
         // Start BMC_SBUS object
        mySBUS.begin();
        
      }
      
      void loop() {
      
        for (int i=0; i<1; i++){        //SBUS needs data every 7 Milliseconds. I repeat it three times for some time to pass for calculating speeds.
      
        mySBUS.Servo(tiltChannel,sendY);
        mySBUS.Servo(panChannel,sendX);
      
        // Update SBUS object and send data
        mySBUS.Update();
        mySBUS.Send();
       
        delay(sbusWAIT);
        
      }
      
        
       timePassed = millis() - timeStampEnd;
       xPassed = xStampEnd - pulsesX;
       yPassed = pulsesY - yStampEnd;
      
       sendX = 1023 + 100* xPassed / timePassed;
       sendY = 1023 + 100* yPassed / timePassed;
      
      for (int i=0; i<1; i++){          //Maybe this one is not needed. Will find it out later
      
        mySBUS.Servo(tiltChannel,sendY);
        mySBUS.Servo(panChannel,sendX);
      
        // Update SBUS object and send data
        mySBUS.Update();
        mySBUS.Send();
       
        delay(sbusWAIT);
        
      }
      
       xStampEnd = pulsesX;
       yStampEnd = pulsesY;
       timeStampEnd = millis(); 
      }
      
      
      
      //Rotary Encoder Stuff by KinoWheels
      
      void XA_RISE(){
       detachInterrupt(0);
       //delay(1);
       XA_SIG=1;
       
       if(XB_SIG==0)
       pulsesX++;//moving forward
       if(XB_SIG==1)
       pulsesX--;//moving reverse
      
       attachInterrupt(0, XA_FALL, FALLING);
      }
      
      void XA_FALL(){
        detachInterrupt(0);
        //delay(1);
       XA_SIG=0;
       
       if(XB_SIG==1)
       pulsesX++;//moving forward
       if(XB_SIG==0)
       pulsesX--;//moving reverse
      
       attachInterrupt(0, XA_RISE, RISING);  
      }
      
      void XB_RISE(){
       detachInterrupt(1);
       //delay(1);
       XB_SIG=1;
       
       if(XA_SIG==1)
       pulsesX++;//moving forward
       if(XA_SIG==0)
       pulsesX--;//moving reverse
      
       attachInterrupt(1, XB_FALL, FALLING);
      }
      
      void XB_FALL(){
       detachInterrupt(1);
       //delay(1);
       XB_SIG=0;
       
       if(XA_SIG==0)
       pulsesX++;//moving forward
       if(XA_SIG==1)
       pulsesX--;//moving reverse
      
       attachInterrupt(1, XB_RISE, RISING);
      }
      
      
      void YA_RISE(){
       detachInterrupt(4);
       //delay(1);
       YA_SIG=1;
       
       if(YB_SIG==0)
       pulsesY++;//moving forward
       if(YB_SIG==1)
       pulsesY--;//moving reverse
      
      
       attachInterrupt(4, YA_FALL, FALLING);
      }
      
      void YA_FALL(){
        detachInterrupt(4);
        //delay(1);
       YA_SIG=0;
       
       if(YB_SIG==1)
       pulsesY++;//moving forward
       if(YB_SIG==0)
       pulsesY--;//moving reverse
      
       attachInterrupt(4, YA_RISE, RISING);  
      }
      
      void YB_RISE(){
       detachInterrupt(5);
       //delay(1);
       YB_SIG=1;
       
       if(YA_SIG==1)
       pulsesY++;//moving forward
       if(YA_SIG==0)
       pulsesY--;//moving reverse
      
       attachInterrupt(5, YB_FALL, FALLING);
      }
      
      void YB_FALL(){
       detachInterrupt(5);
       //delay(1);
       YB_SIG=0;
       
       if(YA_SIG==0)
       pulsesY++;//moving forward
       if(YA_SIG==1)
       pulsesY--;//moving reverse
      
       attachInterrupt(5, YB_RISE, RISING);
      }
      

      How can I port to M5Stack?

      this in what I done ... but I have not Y axe control....
      M5Stack----------ronin D-bus
      grd-------------------grd
      5V--------------------5V
      TXD2(G17)------data

      #include <M5Stack.h>
      #include <ESP32Encoder.h>
      
      ESP32Encoder encoderX;
      ESP32Encoder encoderY;
      
      #define BAUDRATE 100000  // oder  100000 115200
      #define SERIALPORT Serial2  // - uncomment this line if using an arduino based board with more than one HW serial port
      
      
      class BMC_SBUS
      {
        public:
          uint8_t sbusData[25];
          int16_t servos[18];
          void begin(void);
          void Servo(uint8_t ch, int16_t position);
          void Send(void);
          void Update(void);
      
        private:
          uint8_t byte_in_sbus;
          uint8_t bit_in_sbus;
          uint8_t ch;
          uint8_t bit_in_servo;
      };
      
      
      void BMC_SBUS::begin()
      {
        //intialise private data arrays
        //sbus_data is formatted for correct serial output
        //note that the actual 11bit sbus data for each channel is embedded across multiple data bytes in a very stange order
        //byte 1 and bytes 24 and 25 should be left as is
        //the first is a start byte, the last is a stop byte and the second last holds various flags
        //servos is the internal per channel position and is more straightforward - one int_16 per channel
      
        uint8_t loc_sbusData[25] = {0x0f, 0x01, 0x04, 0x20, 0x00, 0xff, 0x07, 0x40, 0x00, 0x02, 0x10, 0x80, 0x2c, 0x64, 0x21, 0x0b, 0x59, 0x08, 0x40, 0x00, 0x02, 0x10, 0x80, 0x00, 0x00};
        int16_t loc_servos[18]   = {1023, 1023, 1023, 1023, 1023, 1023, 1023, 1023, 1023, 1023, 1023, 1023, 1023, 1023, 1023, 1023, 0, 0};
      
        //setup serial port to transmit at 100k baud and use 1 parity and 2 stop bits
      
        SERIALPORT.begin(BAUDRATE, SERIAL_8E2);
      
        //setup public data arrays
      
        memcpy(sbusData, loc_sbusData, 25);
        memcpy(servos, loc_servos, 18);
      }
      
      void BMC_SBUS::Servo(uint8_t ch, int16_t position)
      {
        //set servo position on single channel
      
        if ((ch > 0) && (ch <= 16))
        {
          constrain (position, 0, 2048); //keep within min/max values
          servos[ch - 1] = position; //expects a non zero starting index to the channel
        }
      }
      
      void BMC_SBUS::Send(void)
      {
        //send data over serial port
        SERIALPORT.write(sbusData, 25); //according to docs for Serial we can send the array along as is without a loop
      }
      
      void BMC_SBUS::Update(void)
      {
        //update positions for all servo channels within the SBUS data frame
        //ignores digital servos and any failsafe mode stuff that was originally written
      
        //clear out existing sbus data for all channel data bytes
        //ignores first and last bytes in the array (start and stop bytes)
        //mapping loop relies on initial 0 values - do not omit this step!
      
        uint8_t i;
        for (i = 1; i < 24; i++)
        {
          sbusData[i] = 0;
        }
      
        //reset counters
      
        ch = 0;
        bit_in_servo = 0;
        byte_in_sbus = 1;
        bit_in_sbus = 0;
      
        //format sbus data - maps sevo data array to sbus data array 1bit at a time
        //correctly deals with the little endian byte order in the process
      
        for (i = 0; i < 176; i++) //16channels*11bits = 176bits
        {
          if (servos[ch] & (1 << bit_in_servo)) //bitwise AND to check if the correct servo databit is set to 1
          {
            sbusData[byte_in_sbus] |= (1 << bit_in_sbus); //bitwise OR sets the correct sbus databit if true
          }
      
          //increment bit counters
      
          bit_in_sbus++;
          bit_in_servo++;
      
          //if end of sbus byte reset sbus bit counter and increment sbus byte counter
      
          if (bit_in_sbus == 8)
          {
            bit_in_sbus = 0;
            byte_in_sbus++;
          }
      
          // if we have reached bit 11 in the servo data increment channel index and reset servo bit counter
      
          if (bit_in_servo == 11)
          {
            bit_in_servo = 0;
            ch++;
          }
        }
      }
      
      //Declare BMC_SBUS Object
      BMC_SBUS mySBUS;
      
      // Sbus delay value
      const int sbusWAIT = 7;      //frame timing delay in msecs
      
      // Declare sbus control channels
      int panChannel = 1;
      int tiltChannel = 2;
      int rollChannel = 4;
      
      float pulsesX, pulsesY;
      
      int xStampEnd = 0;
      int yStampEnd = 0;
      int timeStampEnd = 0;
      int xPassed;
      int yPassed;
      int timePassed;
      int sendX;// ??????
      int sendY;// ??????
      
      // Declare Poti Values
      int potiX = 100;
      int potiY = 100;
      
      bool PANTILTtoggle = 0;
      
      
      void setup() {
        M5.begin();
      
        // clear the encoder's raw count and set the tracked count to zero
        encoderX.clearCount();
        encoderY.clearCount();
      
        // Attache pins for use as encoder pins
        encoderX.attachHalfQuad(2, 3);
        encoderY.attachHalfQuad(36, 35);
        
        M5.update();
      
        sendX = 1023;
        sendY = 1023;
      
        // Start BMC_SBUS object
        mySBUS.begin();
      }
      
      void loop() {
      
        pulsesX = encoderX.getCount();
        pulsesY = encoderY.getCount();
      
        for (int i = 0; i < 1; i++) {   //SBUS needs data every 7 Milliseconds. I repeat it three times for some time to pass for calculating speeds.
      
          mySBUS.Servo(tiltChannel, sendY);
          mySBUS.Servo(panChannel, sendX);
      
          // Update SBUS object and send data
          mySBUS.Update();
          mySBUS.Send();
      
          delay(sbusWAIT);
      
        }
      
      
        timePassed = millis() - timeStampEnd;
        xPassed = xStampEnd - pulsesX;
        yPassed = pulsesY - yStampEnd;
      
        M5.update();
      
          sendX = 1023 + 100 * xPassed / timePassed;
          sendY = 1023 + 100 * yPassed / timePassed;
      
        if (sendX > 2047) {
          sendX = 2047;
        }
        if (sendX < 0) {
          sendX = 0;
        }
        if (sendY > 2047) {
          sendY = 2047;
        }
        if (sendY < 0) {
          sendY = 0;
        }
      
        for (int i = 0; i < 1; i++) {     //Maybe this one is not needed. Will find it out later
      
          mySBUS.Servo(tiltChannel, sendY);
          mySBUS.Servo(panChannel, sendX);
      
          // Update SBUS object and send data
          mySBUS.Update();
          mySBUS.Send();
      
          delay(sbusWAIT);
      
        }
      
        xStampEnd = pulsesX;
        yStampEnd = pulsesY;
        timeStampEnd = millis();
      
        M5.update();
      }
      

      the strange thing is that the information about X axe, go to the machine connected at G17 (TXD2), but not the Y one..
      I'm using an inverter on the TX-----RX line...for (d-bus/s-bus)

      tnks a lot

      posted in General
      C
      cepics
    • RE: (SOLVED)Power ATOM Lite

      @m5stack We are talking about M5Atom here....

      posted in Cores
      C
      cepics
    • (SOLVED)SD Uploader can't flash new code

      Hi all,
      I was trying a code on a stack running SD Updater
      I forgot to put inside the bin file this part of code

      #include "M5StackUpdater.h"
      

      and

      
        if (digitalRead(BUTTON_A_PIN) == 0) {
          Serial.println("Will Load menu binary");
          updateFromFS(SD);
          ESP.restart();
        }
      

      now I really don't know how to exit the app...
      M5Burner don't do the job!! and say: timeout waiting for packet header

      please

      posted in Arduino
      C
      cepics