text:
How to use SPI to set/ read registers for a sensor (Avoiding need for Github Lib)
Ok so as some readers might have seen, my current project involves using MPU's. The idea is sending data via CAN bus to a controlling MCU to then send to a raspberry pi to perform the calculations required for my MATLAB/ Simulink model.
After a lot of searching i found this great post/ blog on how to set I2C registers.
Setting I2C Registers
With this, i was able to avoid using a library from Github. I do NOT think i am better than the people writing the libraries, just it's difficult to truly understand code/ a project with a downloaded library and it just stuffed at the top of a piece of butchered example code.
Using the above blog, i learnt how to control an MPU6050 myself in a very basic sense. I am now trying to use an MPU9250 for the sake of extra speed over SPI. However i am trying to understand how to set registers using the SPI interface. For example below for I2C you could write;
  Wire.begin();
  Wire.beginTransmission(MPU_addr);
  Wire.write(0x6B);  // PWR_MGMT_1 register
  Wire.write(0);     // set to zero (wakes up the MPU-6050)
  Wire.endTransmission(true);

and then access the registers like below;
Wire.beginTransmission(MPU_addr);
  Wire.write(0x3B);  // starting with register 0x3B (ACCEL_XOUT_H)
  Wire.endTransmission(false);
  Wire.requestFrom(MPU_addr,14,true);  // request a total of 14 registers
  AcX=Wire.read()<<8|Wire.read();  // 0x3B (ACCEL_XOUT_H) & 0x3C (ACCEL_XOUT_L)
  AcY=Wire.read()<<8|Wire.read();  // 0x3D (ACCEL_YOUT_H) & 0x3E (ACCEL_YOUT_L)
  AcZ=Wire.read()<<8|Wire.read();  // 0x3F (ACCEL_ZOUT_H) & 0x40 (ACCEL_ZOUT_L)
  Tmp=Wire.read()<<8|Wire.read();  // 0x41 (TEMP_OUT_H) & 0x42 (TEMP_OUT_L)
  GyX=Wire.read()<<8|Wire.read();  // 0x43 (GYRO_XOUT_H) & 0x44 (GYRO_XOUT_L)
  GyY=Wire.read()<<8|Wire.read();  // 0x45 (GYRO_YOUT_H) & 0x46 (GYRO_YOUT_L)

my question, is how do you read and write to registers in a similar way via SPI. I've found lots of info on using SPI, but not configuring sensors etc with it in a nice, "SPI configuration for Dummies" type of thing. Is my googling just terrible?
EDIT - My goal is learn the theory behind making a basic library for a sensor, not to make my own SPI library. For example, make a library that can be used to control an MPU9250 using SPI commands to change registers. The last part is what i am struggling with. Interfacing with a sensor to change register values or read registers with SPI.
The link above is almost a crash course in how to use the wire library to interface with a sensor. How do you use the SPI library to change/ read register values.
EDIT2 - Is this the usual format for communicating with registers using SPI on arduino? Thanks
digitalWrite(SS, LOW);
SPI.transfer(0xF1);  // Read, Sensor 1...
SPI.transfer(0x02);  // ... RESA register
highByteA = SPI.transfer(0x00);  // Read High Byte of RESA
lowByteA = SPI.transfer(0x00);  // Read Low Byte of RESA
highByteB = SPI.transfer(0x00);  // Read High Byte of RESB
lowByteB = SPI.transfer(0x00);  // Read Low Byte of RESB
.
.
.
digitalWrite(SS, HIGH);

thanks

The Arduino IDE already has a SPI library, that you can use (like is also already has the Wire library for I2C). There are may tutorials, that explain, how to use it. And there is no general way to "configure sensores". It depends on the sensor. For the MPU it can be found in it's datasheet, though this is not a "... for Dummies" guide. I think you probably won't find such a guide, since the way "... for Dummies" is to use a premade library. But you might also learn much by looking at these premade libraries, that you don't want to use. Otherwise you just chose the hard tour.

This is what i like. Getting different perspectives. I am happy to use the SPI library, what i wanted to learn is almost how to make my own for each sensor. The link i put in explains the theory of communicating with the sensor to change parameters/ registers using I2C. (e.g measurement range or frequency). I will change my question to make it clearer what i am asking

Have you read page 36 of the datasheet (for example here https://cdn.sparkfun.com/assets/learn_tutorials/5/5/0/MPU9250REV1.0.pdf ) It explanes how it works. The first byte consists of a read/write bit and the address of the register, that you want to access. Next bytes are data (for example that should be written into the specified registers). Have you tried reading some registers that way?

forgive my ignorance. i did see that in the datasheet but my issue was trying to find how to actually write to or read from the register. I haven't figured out code tags in the comments, but i found some code from a post on arduino.cc that i overlooked because the OP hadn't found a working solution. It is at the bottom of my post.
is that the format to read to or write from a register for a sensor using SPI?

Do you have a logic analyzer? I was working on some similar things last year and it was infinitely helpful to be able to see what was actually happening on the wire.

no i don't have a logic analyzer, but might get one. i got it working in the end using the format above, it uses the same principle as i2c for writing to registers but just different names


text:
Ov7670 (without FIFO) captures the images twice at the same time
I recently started working on an security camera system, with an arduino uno and an OV7670 camera without FIFO memory, and an ESP-8266 to transfer the images to a webserver. Everything is working, except this:
The problem: My camera takes the images (QVGA resolution) twice every time, and collapse them into one image.
My images looks like this:

One (240*320) QVGA image is built by two (120*320) half image.
My camera takes the two images AFTER each other, not just duplicates the first part.
(After I got one line of the image ready I send it with SoftwareSerial to ESP8266, and that send it forward...)
I'm trying to changeing the scaling registers with different combinations, without success.
I followed this tutorial at the beginning, and modified its code.
https://hkalasua.wordpress.com/2017/09/11/ov7670-arduino-sd/
Arduino code:
#include <Wire.h>
#include <SoftwareSerial.h>

SoftwareSerial ESPserial(10, 11); // RX | TX

void Init_YUV422(){
  WriteOV7670(0x12, 0x00);//COM7
  WriteOV7670(0x8C, 0x00);//RGB444
  WriteOV7670(0x04, 0x00);//COM1
  WriteOV7670(0x40, 0xC0);//COM15
  WriteOV7670(0x14, 0x6A);//COM9
  WriteOV7670(0x3D, 0x40);//COM13
  }

void Init_QVGA(){
  WriteOV7670(0x0C, 0x04);//COM3 - Enable Scaling
  WriteOV7670(0x3E, 0x19);//COM14
  WriteOV7670(0x72, 0x11);//
  WriteOV7670(0x73, 0xF1);//
  WriteOV7670(0x17, 0x16);//HSTART
  WriteOV7670(0x18, 0x04);//HSTOP
  WriteOV7670(0x32, 0xA4);//HREF
  WriteOV7670(0x19, 0x02);//VSTART
  WriteOV7670(0x1A, 0x7A);//VSTOP
  WriteOV7670(0x03, 0x0A);//VREF
  WriteOV7670(0x70, 0x00);//SCALING_YSC

  }

void Init_OV7670() {
  //Reset All Register Values
  WriteOV7670(0x12, 0x80);
  delay(100);

  WriteOV7670(0x3A, 0x04); //TSLB

  WriteOV7670(0x13, 0xC0); //COM8
  WriteOV7670(0x00, 0x00); //GAIN
  WriteOV7670(0x10, 0x00); //AECH
  WriteOV7670(0x0D, 0x40); //COM4
  WriteOV7670(0x14, 0x18); //COM9
  WriteOV7670(0x24, 0x95); //AEW
  WriteOV7670(0x25, 0x33); //AEB
  WriteOV7670(0x13, 0xC5); //COM8
  WriteOV7670(0x6A, 0x40); //GGAIN
  WriteOV7670(0x01, 0x40); //BLUE
  WriteOV7670(0x02, 0x60); //RED
  WriteOV7670(0x13, 0xC7); //COM8
  WriteOV7670(0x41, 0x08); //COM16
  WriteOV7670(0x15, 0x20); //COM10 - PCLK does not toggle on HBLANK
}

void WriteOV7670(byte regID, byte regVal) {
  // Slave 7-bit address is 0x21.
  // R/W bit set automatically by Wire functions
  // dont write 0x42 or 0x43 for slave address
  Wire.beginTransmission(0x21);
  // Reset all register values
  Wire.write(regID);
  Wire.write(regVal);
  Wire.endTransmission();
  delay(1);

}

void ReadOV7670(byte regID) {
  // Reading from a register is done in two steps
  // Step 1: Write register address to the slave
  // from which data is to be read.
  Wire.beginTransmission(0x21); // 7-bit Slave address
  Wire.write(regID);  // reading from register 0x11
  Wire.endTransmission();

  // Step 2: Read 1 byte from Slave
  Wire.requestFrom(0x21, 1);
  Serial.print("Read request Status:");
  Serial.println(Wire.available());
  Serial.print(regID, HEX);
  Serial.print(":");
  Serial.println(Wire.read(), HEX);
}

void XCLK_SETUP(void) {
  pinMode(9, OUTPUT); //Set pin 9 to output

  //Initialize timer 1

  //WGM13, WGM12, WGM11 & WGM10 bits SET- Fast PWM mode
  //COM1A0 SET- Toggle OC1A on compare match
  TCCR1A = (1 << COM1A0) | (1 << WGM11) | (1 << WGM10);
  //SET CS10 bit for clock select with no prescaling
  TCCR1B = (1 << WGM13) | (1 << WGM12) | (1 << CS10);
  //Output Compare Register 1A(OCR1A) = 0
  //This will lead to a match on every clock cycle
  //Toggle OC1A output pin on every match instance
  //Therefore, the generated waveform will have half
  //the frequency of the driving clock i.e. 8Mhz
  //OC1A pin- PB1 (alternate functn) pin i.e. Arduino pin 9
  OCR1A = 0;

}

// Two Wire Interface Setup
// Sets the frequency of the SCL line
// Default is 100KHz so we won't use this function
void TWI_SETUP(void) {
  //Set prescaler bits in TWI Status Register (TWSR) to 0
  TWSR &= ~3;
  //Set SCL frequency to 100KHz
  //SCLfreq = CPUfreq/(16 + 2(TWBR) - 4^(TWPS))
  //TWBR = 72, TWPS(prescaler) = 0
  TWBR = 72;

}

void OV7670_PINS(void) {
  //Setup Data input pins and Interrupt pins
  //DDRC bits 3:0 = 0 =>  bits configured as Data Inputs
  //DDRC 3:0 - A3,A2,A1,A0
  DDRC &= ~15;//low d0-d3 camera

  //~(0b11111100) = 0b00000011
  //make DDRD 7:2 = 0 => Inputs
  //d7-d4 as data inputs, d3-INT1 is VSYNC and d2-INT0 is PCLK
  DDRD &= ~252;
}

void QVGA_Image() {
  int h, w;

  while (!(PIND & 8));//wait for high
  while ((PIND & 8));//wait for low

  byte dataBuffer[320];

  h = 240;
  while (h--) {
    w = 320 ;

    while (w--) {
      while ((PIND & 4));   //wait for low
      dataBuffer[319 - w] = (PINC & 15) | (PIND & 240);
      while (!(PIND & 4));  //wait for high
      while ((PIND & 4));   //wait for low
      while (!(PIND & 4));  //wait for high
    }

    //sendig the line to ESP
    ESPserial.write(dataBuffer, 320);
  }

  delay(100);
}

void setup() {
  Serial.begin(115200);
  ESPserial.begin(115200);
   noInterrupts(); //Disable all interrupts
  XCLK_SETUP();   //Setup 8MHz clock at pin 11
  OV7670_PINS();  // Setup Data-in and interrupt pins from camera
  delay(1000);
  TWI_SETUP();    // Setup SCL for 100KHz
  interrupts();
  Wire.begin();

  Init_OV7670();
  Init_QVGA();
  Init_YUV422();
  WriteOV7670(0x11, 0x1F); //Range 00-1F
  // noInterrupts();

 QVGA_Image();

}

void loop() {
 /* ..Not relevant for this problem.. */
}

I'd be very greatful, if you can help!..
...this is a really annoying problem..

and modified its code - what did you change? - besides adding WriteOV7670(0x70, 0x00);

nothing special, I just removed the SD card parts, and inserted the serial commmunication with the  ESP. I didn't change the register values except that.

and what does that register do?

source: Stack Exchange

license: Creative Commons - Attribution Share-Alike - https://creativecommons.org/licenses/by-sa/4.0/

sort: votes


text:
Digital Input using a button doesn't work properly when using it to control a relay
I'm trying to control a relay both via Bluetooth and using a switch. The problem is that, when the LED is off, I can turn it on with the switch but then if I turn off the switch the relay will stay on. Is there something wrong with my code? Thanks in advance. The switch is installed as follows:

Here is my code: Switch is connected to pin 3 and the relay is connected to pin 2.

//bluetooth hc-06
int ledPin = 2; // usamos un pin de salida al LED
int state = 0; // Variable lectrura serial
int interruptor=3;

void setup() {
    pinMode(ledPin, OUTPUT);   //Declara pin de Salida
    pinMode(interruptor, INPUT);
    digitalWrite(ledPin, LOW); //Normalmente Apagado
    Serial1.begin(9600);
    }

void loop() {
  int valor=digitalRead(interruptor);

  if(Serial1.available() > 0){
       state = Serial1.read();
  } // esta parte del código es para solo 1 Carácter o Unidad.

 if (state == '0'&& valor== LOW) {
    digitalWrite(ledPin, LOW);
    Serial1.println("LED: off");
 }

 else
 if (state == '1' || valor== HIGH) {
     digitalWrite(ledPin, HIGH);
     Serial1.println("LED: on");
 }

}

New code:
//bluetooth hc-06
int ledPin = 2; // usamos un pin de salida al LED
int state = 1; // Variable lectrura serial
int interruptor=3;

void setup() {
    pinMode(ledPin, OUTPUT);   //Declara pin de Salida
    pinMode(interruptor, INPUT);
    digitalWrite(ledPin, LOW); //Normalmente Apagado
    Serial1.begin(9600);
    }

void loop() {
  int valor=digitalRead(interruptor);
 //si el modulo ha mandado dato, guardarlo en estado.

  if(Serial1.available() > 0){
       state = Serial1.read();
  } // esta parte del código es para solo 1 Carácter o Unidad.

 // si el estado es 0 ese sería Apagado “OFF”
 if (valor== LOW) {
    digitalWrite(ledPin, LOW);
    Serial1.println("LED: off");
 }

 // de lo contrario si el estado es 1 ese sería Encendido “ON”
 else
 if (valor== HIGH) {
     if (state== 1){
     digitalWrite(ledPin, HIGH);
     Serial1.println("LED: on");
     }
     else if (state== 0){
     digitalWrite(ledPin, LOW);
     Serial1.println("LED: off");

     }
 }

}

The circuit is working properly when using bluetooth commands, in case that helps.

Should the switch work independently from the bluetooth command on the relay? Currently you can only turn it on with state='1' AND switch on, and you can only turn it off with state='0' AND switch off. It is not completely clear, what the desired behavior is. Please explain further, what the code should do.

@chrisl: No you can turn it on with state='1' OR switch is closed. That's why he can switch the LED on with the switch but not off.

Okay, I modified my code so I can only control via bluetooth when the switch is ON, however it is still not working...

You might be better off with boolean state = true, then using state = (bool)Serial1.read() and 'if (state)...' There's nothing shown here that guarantees Serial1.read()` will return a value of 1

The question lack critical information. What kind of data do you send over serial? Text or binary? First version of code works with characters '0' and '1'. Second version suddenly uses integer values 0 and 1. What gives? You have to make up your mind about what you want to send. Currently the question simply makes no sense.

"I'm trying to control a relay both via Bluetooth and using a switch."   You should explain this further.  How do you want it to act?  Does one override the other?

Well, there are a couple of problems.
In the original SW, you are checking for state = '0' and state = '1', but the initial value of state is 0 (not '0'). For this reason both tests always return false.
In addition, avoid setting conditions when not necessary. else already mean "all the other options", so if you have one variable that can be only A or B, don't write if A ... else if B ...; the second condition is necessary (and meaningful) only if the condition is actually something you care of (so you want to exclude condition C).
I started modifying your sketch from the new version, and here are the things I modified:

Variables were set to type uint8_t; int is not efficient on 8-bit platforms, so use 8-bit variables whenever you can
Instead of using multiple triggers, I used a single variable (ledState) to calculate the state in each loop. This way it is much easier to track the modifications
simplified the input management: now it turns on the led when the input is high, and does nothing (leaves it off) when it is low
simplified the bluetooth management. With a '1' it turns on the led, and all the other chars set it off; if you need only a '0' to turn it off you can easily modify the parentheses to ignore other chars

This is the code I wrote. NOTE: I did not test it, so there may be residual bugs. Let me know if it works as you expect or want some additional clarifications:
uint8_t ledPin = 2;
uint8_t interruptor = 3;
uint8_t bluetoothState = '0';

void setup() {
    pinMode(ledPin, OUTPUT);
    pinMode(interruptor, INPUT);
    digitalWrite(ledPin, LOW);
    Serial1.begin(9600);
}

void loop() {
    uint8_t ledState = LOW;

    if (digitalRead(interruptor)) {
        ledState = HIGH;
        Serial1.println("LED: on (switch)");
    }

    if(Serial1.available() > 0){
        bluetoothState = Serial1.read();
    }

    if (bluetoothState == '1') {
        ledState = HIGH;
        Serial1.println("LED: on (BT)");
    }

    digitalWrite(ledPin, ledState);
    if (ledState == LOW) {
        Serial1.println("LED: off");
    }
}

Things still to do (IMHO):

make a robust button handler (for instance using the debounce library)
get rid of the serial debug outputs
make a better serial protocol

Hopefully the problem was resolved in the intervening 2.5 yrs ;)

O_O why was it in the homepage then? I assumed it was something like 10 minutes old LOL.. sorry for the necroposting

:shrug: It's a low-traffic site so stuff gets bumped for visibility ;) And it's fine anyway--it'll help somebody, if not the OP :)

3.5 years now. :)

I assumed it was something like 10 minutes old ... yes, SE does do odd things like making posts look relevant when they are not.

You have to invalidate the state variable when Serial is not available, otherwise you will produce strange behaviours.
if (Serial1.available() > 0) {
    state = Serial1.read();
} else {
    state = -1; // not valid
}

Also, serial values will be characters, not integers, so compare with character values, e.g.,
if (state == '1')

all_licenses: Creative Commons - Attribution Share-Alike - https://creativecommons.org/licenses/by-sa/4.0/


text:
Decoding RF Signal
I have a motorized curtain and I'm trying to understand its rf control signal in order to control it from my arduino.
I got the times, and checked the code is not static. I believe it has some kind of "sequencial counter" but I could not decode and understand the logic. In resume, I'm trying the get the operations the manufacturer do in order to obfuscate the payload.
The timings I got for the same key, pressed in sequence, are:
396,400,396,804,396,408,800,800,396,408,396,408,396,408,396,408,800,400,400,796,404,400,804,800,804,396,400,800,804,800,400,400,404,404,400,404,400,400,404,400,804,396,404,796,24508,408,368,404,368,404,368,404,368,400,376,400,372,400,372,400,372,400,372,400,372,400,372,400,372,400,376,396,372,400,372,404,372,392,380,396,376,396,376,400,376,392,376,396,376,400,3872,396,384,392,384,420,384,420,384,420,384,416,792,408,388,812,388,416,388,416,388,416,388,416,388,412,796,408,392,400,392,408,392,808,388,412,392,412,392,412,796,404,396,804,796,404,392,404,392,404,396,804,796,404,396,400,396,804,800,400,396,400,396,400,396,804,396,408,800,804,392,408,396,408,396,408,396,408,800,400,400,800,396,408,804,796,804,396,400,800,804,800,400,404,400,404,400,400,404,404,400,400,808,392,404,796,24516,404,368,404,368,404,368,404,368,400,372,404,368,404,372,400,372,400,372,400,372,400,372,400,372,396,376,400,376,396,376,396,376,400,372,400,372,396,376,396,376,400,376,396,372,404,3868,400,380,392,384,420,384,416,388,420,384,420,788,408,388,812,388,416,388,416,388,416,384,416,392,412,796,404,392,404,392,404,392,804,396,416,388,408,396,412,796,404,392,808,796,404,392,404,392,404,392,808,796,400,396,400,400,800,804,400,392,404,396,400,396,800,400,404,804,800,396,408,396,408,400,400,400,404,804,396,404,796,400,404,804,800,804,396,400,800,804,796,400,404,400,404,400,404,400,400,404,404,804,392,404,796,24512,412,364,404,368,408,364,404,368,404,368,404,368,404,372,404,368,404,368,404,368,400,372,404,368,400,372,400,376,396,376,396,376,400,372,396,376,396,376,400,372,400,376,396,376,400,3868,400,380,392,384,420,384,416,388,416,388,420,788,412,384,816,384,416,388,416,388,416,388,416,388,416,792,408,388,404,392,408,388,812,388,416,388,412,392,412,796,400,396,808,796,404,392,404,396,400,396,804,800,400,396,400,396,804,800,400,396,400,396,400,396,804,396,408,800,804,396,404,400,408,396,404,400,404,804,396,400,800,396,408,804,796,808,396,400,796,808,796,400,404,400,404,400,404,400,404,400,400,808,392,404,796

392,412,796,400,396,404,396,800,396,408,396,408,396,408,396,408,396,404,400,408,396,404,804,396,400,396,400,396,400,800,804,800,804,396,400,800,400,404,804,796,404,400,400,404,404,400,804,396,404,392,404,392,404,380,24124,404,368,408,368,404,372,400,368,404,368,400,372,404,368,404,368,404,372,400,372,400,372,400,372,400,372,400,372,400,376,396,372,400,376,396,376,396,376,396,376,396,376,396,376,400,3872,396,384,392,384,420,384,420,384,420,788,408,392,404,388,412,388,808,388,416,388,412,392,416,792,404,396,404,388,808,800,808,388,412,392,412,796,404,392,400,400,400,396,400,396,400,396,404,392,400,396,404,396,400,396,400,396,804,396,408,796,404,396,400,396,800,396,412,392,408,396,408,396,408,396,408,396,408,396,408,800,396,400,400,400,396,400,800,804,800,800,400,400,800,396,404,808,796,400,404,400,404,400,404,804,396,400,396,400,396,404,380,24124,408,368,404,368,404,368,404,368,404,368,404,368,400,372,400,372,404,368,404,372,400,372,400,372,400,372,396,376,400,372,400,372,396,380,392,376,400,376,396,376,396,376,396,376,400,3868,400,380,392,384,420,388,416,388,412,796,408,388,408,388,408,388,812,388,416,388,412,392,412,796,408,388,408,388,812,792,808,392,408,396,408,800,400,396,404,392,404,392,404,392,404,392,404,396,396,400,400,396,400,396,404,392,804,396,408,800,400,396,400,400,800,396,408,396,408,396,404,400,408,396,408,396,404,400,404,804,396,400,400,396,396,400,800,804,800,804,396,400,800,400,404,804,800,400,404,400,400,404,400,808,392,404,392,404,396,400,380,24124,404,368,412,364,404,368,404,368,404,368,404,368,404,368,404,372,400,368,404,372,400,372,400,372,400,372,400,372,400,372,400,372,400,376,396,376,396,376,400,372,396,376,400,372,400,3872,396,384,392,384,420,384,424,380,416,792,408,388,408,388,412,384,816,384,416,388,416,392,416,788,408,392,404,392,808,796,808,388,416,388,416,792,404,396,404,388,408,392,404,392,404,392,404,392,404,396,400,396,400,396,404,392,804,396,408,800,400,396,400,396,804,396,408,396,408,396,408,396,404,400,404,396,408,396,408,800,400,396,400

This site helps visualize the timings  (just copy and paste)
I believe it uses modulation ASK and Manchester Encoding (not sure about that), and the binary data I got is (the timings for third key press I did not save):
1010101010100101101010101010010101011010101001011001010101100101011001010101101001101010101001011010011001011001101010101010010110

1010101010010101011010101001010110011010100101010101010101010101101001010110101010101010100101010110011001011010011010101001010101

1010101010011010101010101001101001011010100110101001010101011010011001010110010101101010100110101010011001011010101010101001101010

This link explain what I'm trying to do, but using a control from another manufacturer. The result, is better explained here.
If is useful, I press the same key 2 times in other identical control and the timings I got are (I believe it changes the address and the 'counter'):
408,400,408,400,412,396,408,396,416,400,816,388,412,792,820,796,816,792,416,396,820,384,412,796,416,388,416,396,412,396,416,392,412,396,820,384,420,788,24636,404,376,400,376,396,384,396,376,400,380,396,384,396,380,396,380,396,380,396,384,392,384,396,380,392,388,392,384,388,388,392,388,392,384,392,384,392,384,392,388,388,388,384,392,392,3900,392,392,384,396,412,396,408,404,412,392,412,804,404,400,804,400,408,404,408,396,408,400,412,396,408,808,400,404,400,400,400,404,800,404,408,400,404,408,400,812,392,408,804,400,408,400,404,408,400,408,400,816,800,404,400,408,400,816,800,408,400,408,400,404,404,816,388,412,796,408,400,408,400,408,396,412,400,412,396,820,388,412,792,820,792,816,796,416,392,820,388,412,796,412,396,412,392,416,392,416,396,416,388,824,384,416,792,24636,400,380,400,372,400,380,396,380,396,380,396,384,396,380,400,376,396,384,396,380,396,380,396,380,396,384,392,384,392,384,392,388,392,384,388,388,392,384,392,388,392,388,388,384,396,3896,392,392,388,396,408,400,412,392,416,396,412,800,404,400,808,396,412,400,408,396,412,400,408,400,408,804,400,404,400,400,396,404,808,400,408,400,408,404,404,808,396,404,804,404,400,408,400,408,404,404,404,812,800,404,404,404,404,816,796,408,400,408,400,408,400,816,388,412,792,412,400,412,396,412,396,412,396,412,396,820,388,412,792,820,796,816,796,412,392,820,392,412,792,416,392,412,396,416,392,412,396,416,392,824,384,420,788,24632,404,376,400,376,400,376,400,380,400,376,400,380,396,380,392,384,396,380,396,384,392,384,396,380,396,380,392,388,392,384,392,388,388,388,388,388,392,384,392,384,392,384,392,388,392,3896,392,396,384,392,416,396,408,400,412,396,412,804,400,400,808,400,408,400,408,400,408,400,408,400,408,808,396,404,396,408,396,400,804,404,408,400,408,400,404,812,396,404,804,408,400,404,400,408,400,408,400,816,800,408,400,408,400,812,800,408,400,408,400,408,400,816,388,412,800,408,396,412,396,412,396,412,396,412,396,820,388,412,796,816,796,816,792,416,392,820,388,420,788,412,396,416,388,420,392,416,392,412,396,820,384,420,788

808,400,400,396,408,396,404,804,404,404,404,400,408,404,404,404,404,404,404,404,812,392,408,796,412,400,408,400,816,392,408,392,408,388,412,800,412,392,412,400,408,400,816,388,412,388,412,392,412,388,412,796,816,796,412,396,820,792,820,796,408,396,412,392,416,396,820,388,412,384,420,384,416,372,24248,404,376,396,380,400,376,400,376,400,380,396,380,396,380,396,380,400,380,392,388,392,380,396,384,392,384,392,384,396,380,392,384,392,388,392,384,392,388,388,388,388,388,388,388,396,3896,392,392,388,396,408,400,412,396,412,800,404,400,404,396,400,404,804,400,408,400,408,400,408,808,400,404,396,404,800,812,804,400,408,400,404,812,400,404,396,404,396,404,804,400,408,404,404,404,400,412,400,404,404,408,400,816,388,412,792,412,400,408,400,816,388,412,392,412,388,412,796,412,396,412,396,408,400,816,392,412,388,412,388,412,388,416,792,820,792,412,396,820,792,820,792,416,392,416,392,416,392,820,388,416,384,420,384,416,368,24248,404,376,400,380,396,380,400,376,400,376,400,380,392,384,396,380,400,380,392,384,396,384,392,380,392,384,396,384,392,384,392,388,388,388,388,388,392,388,388,384,392,388,388,388,396,3896,392,392,384,396,416,396,412,396,412,800,404,400,404,396,400,404,808,396,408,400,408,400,408,804,404,400,400,400,808,808,800,404,408,404,400,816,392,408,396,404,396,404,804,404,400,408,404,404,404,404,404,408,396,408,404,812,396,404,800,408,400,408,400,816,388,412,392,412,388,412,796,408,400,408,400,408,400,816,392,412,388,412,388,412,388,416,792,820,792,412,396,820,792,820,792,416,392,416,392,416,392,820,388,416,384,416,384,416,372,24248,404,376,404,372,404,376,400,376,396,380,400,376,400,380,396,380,396,380,396,380,396,384,396,380,396,384,388,388,392,384,392,384,392,384,392,388,388,384,392,392,388,388,384,388,392,3900,392,396,384,396,412,396,412,396,412,804,404,396,404,396,404,400,804,400,408,400,408,404,408,808,396,400,400,404,804,812,800,404,404,404,404,808,400,404,396,404,396,404,804,404,404,404,404,400,404,408,404,404,404,408,396,816,392,404,804,408,400,408,400,820,384,412,388

Do you have a specific question?

you may have decoded  the first two data streams incorrectly .... i  got these      00000011000000111100001100000100010000110000001101010011000000110 .....
00000111100001110100011111111111001110000000011110101100100001111

What happens if you just replay the recorded data? Does the curtain not respond if the 'counter' isn't updated?


text:
Esp8266 -12E v3
So I have this ESP 8266 v3 board that has a program. Running on it currently, it’s the example scan Network Program. No matter what program I send to it now I get a error complaining for board NodeMCU 1.0 (ESP-12E).
I have checked to assure that the com port is correct and is showing upload 11500 , cpu 80 MHz, flash size 4M, debug disabled. Debug level - none, iwip v2 low memory
Viable”flash”, exception enable, erase flash only sketch
Port 6 .
   Arduino 1.8.8 Windows 10
In error box print in red
Board nodemcuv2. (platform, esp8266, package edp8266 is Unknown.
Error compiling for board NodeMCU 1.0 (ESP-12E Module)

Used this board a few times without an issue, now no matter what I try it maintains the current scan program and I am unanticipated compile or upload to the board. Is it stuck in some sort of loop or what? Any help would be appreciated, thanks

Sorry for typos here, should read I am unable to compile or upload any program. I tried and when I opened the serial window it showed my network being scanned. Thanks

go to Board Manager in IDE and reinstall the esp8266 boards package

why are you posting a comment about the typos, instead of correcting the typos?

I am unable to compile - then the issue is not with the hardware ... package edp8266 is Unknown ... what is this package edp8266 - looks like an obvious typo, but is that typo yours (i.e. you typed it wrong here) or is that the actual message you are getting


text:
Dynamically create functions for AccelStepper that use Adafrut_StepperMotor.oneStep methods?
In the Adafruit_MotorShieldV2Library>Accel_MultiStepper example, AccelSteppers are initialized using the following static forwardstep1 and backwardstep1:
#include <Wire.h>
#include <AccelStepper.h>
#include <Adafruit_MotorShield.h>

//First, get an Adafruit_MotorShield
Adafruit_MotorShield AFMStop(0x60); // Default address, no jumpers

//Then, get a stepper motor from it
Adafruit_StepperMotor *myStepper1 = AFMStop.getStepper(200, 1);

//Then, create callbacks for the AccelStepper's constructor
void forwardstep1() {
    myStepper1->onestep(FORWARD, SINGLE);
}
void backwardstep1() {
    myStepper1->onestep(BACKWARD, SINGLE);
}

//Finally, create the stepper motor
AccelStepper stepper1(forwardstep1, backwardstep1);

I intend to then use these AccelSteppers as members in a MultiStepper, which I'm skipping here because it shouldn't be relevant.
I want to make a function that automates this process. Ideally it would work something like this:
typedef void(*mover)();
AccelStepper makeStepper(Adafruit_StepperMotor myStepper){
    // create functions of type mover
    mover forward = []{myStepper->onestep(FORWARD, DOUBLE);};
    mover back = []{myStep->onestep(BACKWARD, DOUBLE);};
    return AccelStepper step(forward, back);
}

What I've tried:

Obviously the above solution. This doesn't work because myStepper isn't captured, but if you capture it it's not a mover object and can't be passed to AccelStepper.
Using an object's function. This doesn't work because object functions have the implicit first parameter this. See this for more info
Making the parameter myStepper static after it's passed in. This doesn't work because it gets over-written on every call to the function.
Using std::forward. This would probably work, but I don't think std::forward is defined in ArduinoSTL because I keep getting the error 'forward' is not a member of 'std'. See the code below:

Note, In an attempt to make this work, I upgraded the following folders to -std=gnu++17 on my ubuntu machine, resulting in __cplusplus == 201500:

~/.local/share/umake/ide/arduino/hardware/arduino/avr/platform.txt
~/.local/share/umake/ide/arduino/hardware/hardware/platform.txt

std::forward attempt
#include <ArduinoSTL.h>
using namespace std;
#include <iostream>
#include <functional>
#include <utility>

typedef void(*mover)();

template <classF>
mover lambda_to_ptr(F&& f){
    static F fn = std::forward<F>(f);
    return []{ return fn();};
}
AccelStepper makeStepper(Adafruit_StepperMotor myStepper){
    // create functions of type mover
    mover forward = []{myStepper->onestep(FORWARD, DOUBLE);};
    mover back = []{myStep->onestep(BACKWARD, DOUBLE);};
    return AccelStepper step(lambda_to_prt(forward), lambda_to_ptr(back));
}

p.s. Of course, I could always change the functions in the library, but this is (almost) always a bad idea.

I ended up just inheriting AccelStepper, and extending the
AccelStepper::AccelStepper  (   uint8_t interface = AccelStepper::FULL4WIRE,uint8_t pin1 = 2,uint8_t pin2 = 3, uint8_t pin3 = 4, uint8_t pin4 = 5, bool enable = true ) constructor to add my own Adafruit_StepperMotor instance variable and using it in an overridden step0 (which is the only function those callbacks were used in).
class MyAccelStepper: public AccelStepper
{
   public:
       MyAccelStepper(Adafruit_StepperMotor *myStepper):AccelStepper(0,0,0,0,0,false)
       {
         //MyStepper(0, 0, 0, 0, 0, false);
         _myStepper = myStepper;
       }
   protected:
       void step0(long step){
          (void)(step);
          if(speed() > 0){
            _myStepper->onestep(FORWARD, DOUBLE);
          }else{
            _myStepper->onestep(BACKWARD, DOUBLE);
          }
       }
    private:
       Adafruit_StepperMotor *_myStepper;
};


text:
Problem sending SMS from a GSM SIM900
I have a laser security system project with a GSM SIM900 and a few sensors. I'm using an Arduino Mega 2560, and everything is working normally, except the GSM is not sending an SMS to the phone and I don't know why!
this is  my code:
#include <Wire.h>
#include <LiquidCrystal_I2C.h>
#include <Keypad.h>
#include <SoftwareSerial.h>

SoftwareSerial sim900(0,1);
String  TextForSMS;

int dataldr =0;
int sensorldr = A0;
int ldrState = LOW;
int ldrthres = 900;

int pir = A1;
int pirState = LOW;
int val = 0;

int gas = A8;
int sensorgasThres = 400;

#define Password_Length 8
#define PINNUMBER ""

int signalPin = 2;
int led1 = 12;
int led2 = 11;
int led3 = 10;
int led4 = 9;
int led5 = 8;
int led6 = 7;
int laser =6;

char Data[Password_Length];
char Master[Password_Length] = "123A456";
byte data_count = 0, master_count = 0;
bool Pass_is_good;
char customKey;

const byte ROWS = 4;
const byte COLS = 4;

char hexaKeys[ROWS][COLS] = {
  {'1', '2', '3', 'A'},
  {'4', '5', '6', 'B'},
  {'7', '8', '9', 'C'},
  {'*', '0', '#', 'D'}
};

byte rowPins[ROWS] = {30,31,32, 33};
byte colPins[COLS] = {34, 35, 36, 37};

Keypad customKeypad = Keypad(makeKeymap(hexaKeys), rowPins, colPins, ROWS, COLS);

LiquidCrystal_I2C lcd(0x3F, 20, 4);

void setup(){

  lcd.init();
  lcd.backlight();

  pinMode(signalPin, OUTPUT);
  pinMode(led1, OUTPUT);
  pinMode(led2, OUTPUT);
  pinMode(led3, OUTPUT);
  pinMode(led4, OUTPUT);
  pinMode(led5, OUTPUT);
  pinMode(led6, OUTPUT);
  pinMode(laser, OUTPUT);

  pinMode(gas, INPUT);
  pinMode(pir, INPUT);
  pinMode(sensorldr,INPUT);

 randomSeed(analogRead(0));
  Serial.begin(9600);
  sim900.begin (9600);
  Serial.println(" loggin time completed");
delay(5000);

}

void loop(){

     digitalWrite(laser, HIGH);
     digitalWrite(led1, HIGH);

     lcd.setCursor(0,0);
     lcd.print("Enter Password:");

   char customKey = customKeypad.getKey();

  if (customKey){

    Data[data_count] = customKey;
    lcd.setCursor(data_count,1);
    lcd.print(Data[data_count]);
    data_count++;
    }

  if(data_count == Password_Length-1){
    lcd.clear();

    if(!strcmp(Data, Master)){

      lcd.print("Correct");
      digitalWrite(led3, HIGH);
      tone(signalPin, 150,200);
      delay(5000);
      digitalWrite(signalPin, LOW);
      digitalWrite(led3, LOW);
      digitalWrite(laser, LOW);
      ldrState = LOW;
      delay(5000);
      digitalWrite(laser, HIGH);
      ldrState = HIGH;

      }
    else{
            lcd.print("Incorrect");
            digitalWrite(led4, HIGH);
            digitalWrite(signalPin, HIGH);

      delay(2000);

            digitalWrite(led4, LOW);
           digitalWrite(signalPin, LOW);
 TextForSMS="\nIntruder password wrong";
  sendSMS(TextForSMS);
 lcd.setCursor(10,2);
  lcd.print("sms2sent");      }

    lcd.clear();
    clearData();
  }

  int   dataldr =analogRead(sensorldr);
     lcd.setCursor(0,3);
     lcd.print("Laser:");
     lcd.setCursor(7,3);
     lcd.print(dataldr);

  if(dataldr<ldrthres){
    digitalWrite(signalPin, HIGH);
    digitalWrite(led2, HIGH);
  TextForSMS="\nIntruder detected";
  sendSMS(TextForSMS);
  lcd.setCursor(10,2);
  lcd.print("sms1sent");

  }
  else
  {
    digitalWrite(led2, LOW);
    noTone(signalPin);

  }
  delay(100);

 int analogSensor = analogRead(gas);
  lcd.setCursor(0,2);
  lcd.print("Gas:");
  lcd.setCursor(4,2);
  lcd.print(analogSensor);
  // Checks if it has reached the threshold value
  if (analogSensor > sensorgasThres)
  {
            digitalWrite(led5, HIGH);
            digitalWrite(signalPin, HIGH);

     TextForSMS="\nIntruder GAS";
  sendSMS(TextForSMS);
  lcd.setCursor(10,2);
  lcd.print("sms3sent");
  }
  else
  {
    digitalWrite(led5, LOW);
    noTone(signalPin);
  }
  delay(100);

  val = digitalRead(pir);
  if (val == HIGH) {
    digitalWrite(led6, HIGH);

    if (pirState == LOW) {
           Serial.println("Motion detected!");
           pirState = HIGH;
    }
  } else {
    digitalWrite(led6, HIGH);
 delay (5000);
    if (pirState == LOW){
           Serial.println("Motion ended!");
      pirState = LOW;
    }
  }

}

void clearData(){
  while(data_count !=0){
    Data[data_count--] = 0;
  }
  return;
}

void sendSMS (String message){
    sim900.print("AT+CMGF=1");
    delay(1000);

  sim900.println("AT+CMGS=\"+380633965886\"\r ");
      delay(1000);
sim900.println(message);
    delay(1000);
sim900.println((char)26);
    delay(1000);
sim900.println();
    delay(1000);

  }

Also on Github:
https://github.com/shiyaroo/gsm-sim900/blob/master/laser_security_system__gsm.ino

reduce your code to only send  a fixed text message ..... remove all code that is not related to sending the text message  ...... please post the result

its all related to each other but i will try to show u the main code about sending sms

can u see the last part of code void sendSMS (String message)   if i should change something ?

you are not understanding my comment

It’s not a good approach to put delay function between AT commands.
You have to parse SIM900 responses and check if module replies with OK.
If you don’t receive responses from module, could be different problems:

wrong baudrate
connection or power supply problem
SIM card problem (out of cash, sim lock with pin, etc..)

here you can find a useful guide:
https://randomnerdtutorials.com/sim900-gsm-gprs-shield-arduino/

the step 1,2,3 are checked and no problem , but i didn;t understood what u mean here (It’s not a good approach to put delay function between AT commands)

When you send an AT command like this sim900.print("AT+CMGF=1");, you shouldn’t put a delay function like this delay(1000);, but you should reading characters coming from Serial and check if module replies with OK or with some errors.

Try to do a fast test, Create a sketch that send only ‘’AT’’ command and check if SIM900 replies with OK.


text:
Invalid conversion from 'const char' to 'uint8_t*'
I am just a newbie, don't know how to solve this issue
void loop()
{
  UdpSend("Test", "192.168.0.240", 4210);
}

void UdpSend(const char* message, uint8_t * ipaddress, int port){
      Serial.println("Send message: ");
      Udp.beginPacket(ipaddress, port);
      Udp.write(message);
      Udp.endPacket();
}

Arduino IDE can't compile.
The error message:  invalid conversion from 'const char' to 'uint8_t* {aka unsigned char*}' [-fpermissive]*
Trying to change with this code:
void UdpSend(uint8_t * message, uint8_t * ipaddress, int port){
      Serial.println("Send message: ");
      Udp.beginPacket(ipaddress, port);
      Udp.write(message);
      Udp.endPacket();
}

Also doesn't work, the error message: invalid conversion from 'const char' to 'uint8_t* {aka unsigned char*}' [-fpermissive]*
Please help...

you changed the wrong one ... try changing uint8_t * ipaddress to const char * ipaddress ... then in Udp.beginPacket((uint8_t *) ipaddress, ...

Change the code like this:
void UdpSend(const char * message, const char * ipaddress, int port){       Serial.println("Send message: ");       Udp.beginPacket((uint8_t *)ipaddress, port);       Udp.write(message);       Udp.endPacket(); } Error: invalid conversion from 'const char*' to 'uint8_t {aka unsigned char}' in **Udp.write(message);**

void UdpSend(const char * message, const char * ipaddress, int port){       Serial.println("Send message: ");       Udp.beginPacket((uint8_t *)ipaddress, port);       Udp.write((uint8_t *)message);       Udp.endPacket(); } Error: invalid conversion from 'uint8_t* {aka unsigned char*}' to 'uint8_t {aka unsigned char}' in Udp.write((uint8_t *)message);

Please help....

hmm ... ok, I probably didn't look at the code properly

what library is Udp from? - you actually do not need the (uint8_t *) at all

#include <WiFiUdp.h>

Remove all (uint8_t ): void UdpSend(const char * message, const char * ipaddress, int port){       Serial.println("Send message: ");       Udp.beginPacket(ipaddress, port);       Udp.write(message);       Udp.endPacket(); } Error: _invalid conversion from 'const char' to 'uint8_t {aka unsigned char}'_ in Udp.write(message);

In ESP32 Arduino package the WiFiUdp.h doesn't pull in all Print class write functions. As consequence the WiFiUdp class doesn't know write(const char *str).
Use Udp.print(message); if message is a zero-terminated char array
or Udp.write(message, size); if message is a byte array

Wild guess that it's esp32. Props to you if you're right!!!

Juraj guess is correct, I am using ESP32

Thanks a lot Juraj, your solution works perfectly.

@JaromandaX, it was not so wild. there are not so many WiFiUdp.h (OP revealed it in comment)

I'm still impressed

Not sure why you're using uint8_t at all
The Udp.beginPacket function signature is
int WiFiUDP::beginPacket(const char *host, uint16_t port)

No hint of uint8_t there
and .write is either
WiFiUDP::write(uint8_t byte)
WiFiUDP::write(const uint8_t *buffer, size_t size)
WiFiUDP::write(const char *str)
WiFiUDP::write(const char *buffer, size_t size)

So, your other attempt to use write((uint8_t *)) is also wrong
Try this:
void loop()
{
  UdpSend("Test", "192.168.0.240", 4210);
}

void UdpSend(const char* message, const char * ipaddress, int port){
      Serial.println("Send message: ");
      Udp.beginPacket(ipaddress, port);
      Udp.write(message);
      Udp.endPacket();
}

Sorry, I am just a newbie, still don't know how and learning to do it in proper way. void UdpSend(const char* message, const char * ipaddress, int port){       Serial.println("Send message: ");       Udp.beginPacket(ipaddress, port);       Udp.write(message);       Udp.endPacket(); } Error: invalid conversion from 'const char*' to 'uint8_t {aka unsigned char}' in Udp.write(message);

which line is the error referring to - the code I posted works

The error referring to Udp.write(message); line. Error: invalid conversion from 'const char*' to 'uint8_t {aka unsigned char}' [-fpermissive]

you're doing something else wrong, since Udp.write can take a single const char * argument

Change in Loop function: UdpSend("T", "192.168.0.240", 4210); Also error in Udp.write(message); Error message: invalid conversion from 'const char*' to 'uint8_t {aka unsigned char}' [-fpermissive]

Previously I am using this code: Serial.println("Send: ");       Udp.beginPacket("192.168.0.240", 4210);       Udp.write("TESTING FROM 240");       Udp.endPacket(); And it works perfectly. But for simplicity, I am trying to write simple function for itvoid UdpSend(const char* message, const char * ipaddress, int port) (which doesn't work)

@wieb Provided "try" code is working on Arduino IDE 1.8.8 (if you compile it for the Arduino Uno + WiFi shield). You HAVE TO provide more details. Versions of everything (IDE, WiFi lib), setup info (board, shield if used)...


text:
Is there a relationship between RSSI and Power? If so, how are they connected and does it have a formula to extract one from the other?
I have searched on Google but to no avail. Perhaps you guys can help.
-Aj

Is there a relationship between RSSI and Power?

Yes

If so, how are they connected and does it have a formula to extract one from the other?

RSSI is in relation to the square-root of the power. See below references for the actual formula.
Holiday extra: RSSI for an RF433 module can be estimated by the time from end of transmission and noise. This is the time for the AGC circuit to increase gain from the received signal to the noise level. Please see Cosa RF433 library for an example.
References:

https://en.wikipedia.org/wiki/Received_signal_strength_indication
https://en.wikipedia.org/wiki/Signal_strength_in_telecommunications


text:
Generating and reading a PWM signal at the same time on Arduino Uno R3?
The code below should generate a PWM signal on digital pin 3. But know I want to see if it is even working. I was thinking about a Event triggering method like ISR. But somehow it does not work. I guess a ISR needs to a Input Pin, e.g. it would work, when I would've a PWM signal coming from somewhere.
Is it even possible to generate a PWM signal and read it to see some results on the serial monitor?
edited code:
byte const PWM_PIN = 3;

volatile unsigned long pwm_value = 0;
volatile unsigned long prev_time = 0;

void setup() {
  pinMode(PWM_PIN, OUTPUT);
  Serial.begin(9600);
  attachInterrupt(digitalPinToInterrupt(PWM_PIN), rising, RISING);
}

void loop() {
  digitalWrite(PWM_PIN, HIGH);
  delay(400);
  digitalWrite(PWM_PIN, LOW);
  delay(1600);
}

void rising() {
  attachInterrupt(digitalPinToInterrupt(PWM_PIN), falling, FALLING);
  prev_time = millis();
}

void falling() {
  attachInterrupt(digitalPinToInterrupt(PWM_PIN), rising, RISING);
  pwm_value = millis()-prev_time;
  Serial.println(pwm_value);
}

wire the pin to other pin and read the other pin. what you generate is not PWM. you don't attach any interrupt in setup. use CHANGE interrupt

If a digitalWrite is not working for an output pin, then you should not use that arduino board anymore. You create a extra code that can have bugs to test something very simple, it is therefor more likely that the extra code is wrong. It is allowed to do a digitalRead for an output pin, you can therefor make the pin high, and read if it is really high. But please don't do that. If that fails, then something else is very wrong. When you assign a value to a variable (for example int i = 3 ;), how do you know that does work? Do you want to add extra tests to check if the variables do work?

With your current code the delays are so long, that you  can see the code working by connecting a LED to the output pin. An on time of 400ms is well noticable by eye. Though I wouldn't call this slow signal PWM.

@Juraj Yes right. I tried to do it without Serial.println(); in loop() and I also added attachInterrupt to setup(). I set both delays to 1000 (which should be in ms). But the pwm_value is only 16984, which are micro seconds. ---> 16,9ms

But that makes no sense, the right pwm_value should be 1000000 us right?

And connecting pwm pin to another pin, which is used as interrupted pin doesn't make any difference.

You can use approach from this video: https://www.youtube.com/watch?v=p-kCPR42EtU

You are declaring the variables prev_time and pwm_value as int, which has (on a standard Arduino) 16 bits. Since you use the signed variant, you get a range of values from -32768 to 32767. But micros() is returning an unsigned long, which has 4 bytes (32 bits) and is not signed. With int there are only 32.767 ms (since it represents microseconds here), without letting the variable overflow. Even the full range would give you only about 65 ms. It simply cannot hold a value like 1000000. If you assign this value to an int, it will directly overflow (which - I think - would give you the value modulo 2^16), effectively loosing big parts of the information. You cannot get meaningful results with this in such a high time scale.
When measuring time (with millis() or micros()) you should always be sure to use unsigned long as type to prevent these problems.

Apart from the variable type, why do you use micros() here? You are measuring times in the hundreds of milliseconds, so why not use millis()? This would keep the values lower.

Yes! It works now. I've edited the code above. So you can attach an interrupt to both input and output. Through @leoc7 I probably even found an easier way to create a PWM signal with: https://playground.arduino.cc/code/timer1

If it works now, please consider to accept the answer as correct.

You aren’t generating a correct PWM, because Serial.println introduces a delay. The right way for generating PWM is to use analogWrite function.
You can’t use attachInterrupt function for detecting rising and falling edge of an output pin.
In order to detect the rising and falling edge of a PWM signal, you have to use the timer interrupt of PWM module. For doing this, You have to write/read directly ATmega registers without using Arduino libraries. What version of Arduino are you using?

there is a delay(1200) and you nitpick the Serial println()? 3. what?

I mean Timer Overflow Interrupt

is incorrect. You can.

@leoc7 Arduino 1.8.8

@Gamdschiee Sorry, I meant what model of Arduino

@leoc7 Elegoo Uno R3

@Gamdschiee Take a look to this guide for detecting rising edge using timer 1 overflow interrupt https://playground.arduino.cc/code/timer1


text:
Can't extract basic data using ThingspeakHTTP
I don't know anything about HTML, but I want to extract the % probability of the Northern lights being visible from this webpage
http://aurorawatch.ca/.
I entered this into the URL field, and selected HTML version 1.
When I inspect the text element I want and copy the Xpath I get the following:
"/html/body/div1/div[5]/table/tbody/tr1/td/div1/table[2]/tbody/tr[2]/td/div/table/tbody/tr/td[2]/span"
and enter this into the "parse string" field of the ThingSpeak API app, but get the following error:
"Error parsing document, try a different parse string."
Most people who get this error seem to be getting data that doesn't load with the original page, so I think I must be missing something.
If there is a better solution for pulling this number to my ESP8266 than creating a thingspeak API, I would love to hear it too!

Post your code for a better understand of question

Maybe the website is blocking thingspeak as a scraper. You would want to make the ESP8266 do the GET request and then parse the data. I'd suggest using http://www.aurorawatch.ca/index.php?option=com_content&task=view&id=28&Itemid=47 as it's a) less data, and b) less likely to change.

@Majenko Thanks for the quick response! That's a good suggestion, using the alternate page. I thought that was possible too, but when I leave the parser string blank, the thingspeak api request returns the full site.
I know this is beyond the scope of the question, but do you have any recommendation for where to start learning how to make the GET request I want from the ESP8266?

why do you select HTTP 1.0 (HTML 1?)

@Juraj I believe that's what version the website I'm attempting to get data from is build on

I can see no reason for it not to work. I have manually downloaded the webpage source, prettified it with xmllint, then worked through each node of the xpath, and it is exactly as it should be. Yet it can't parse it. Maybe there is something about the content that ThingSpeak's parser doesn't like.

I tested the date and it returned the logo. something is added into page with script or style?

Ok, I have it working. It doesn't like the first tbody. Remove that and it starts working.  Also it's good to add /text() to the end.  I have it parsing this page: http://www.aurorawatch.ca/index.php?option=com_content&task=view&id=28&Itemid=47 with this xpath: /html/body/div[1]/div[5]/table[2]/tr[3]/td/table/tbody/tr/td[2]/span/text()

just for interest:   here is another site that has aurora visibility percentages ....  https://services.swpc.noaa.gov/text/aurora-nowcast-map.txt

@jsotola that is where I looked first, which has a few awesome resources! The format of the text array is a little ambiguous though (is it -90deg to 90deg top to bottom, or bottom to top?), and I am lucky enough to go to the university that made Aurora watch for the city I live in

You should use this page, since the other is the front page of the site and more likely to be dynamic:

http://www.aurorawatch.ca/index.php?option=com_content&task=view&id=28&Itemid=47

The XPath is also slightly different. The first tbody in the reported path doesn't actually exist. You should also add /text() to the end of the path to just return the textual content of the node:

/html/body/div[1]/div[5]/table[2]/tr[3]/td/table/tbody/tr/td[2]/span/text()


text:
How can I distinguish values sent from Arduino
Having in my visual basic app something like:
private void serialPort1_DataReceived(object sender, SerialDataReceivedEventArgs e)
    {
        *whatever* value = serialPort1.Read*whatever*();
    }

Suppose my Arduino sends in every loop, the value read by a photoresistor. Suppose my Arduino also sends a 0 if certain led is LOW or a 1 if certain led is HIGH. Finally suppose my Arduino also sends a value that is equal to the number of times the loop has been executed.
In the 25th execution, lets suppose my Arduino sends something like:
Serial.write(LED_state) // 0 or 1 for LOW or HIGH
Serial.write(photoresistor_value) //lets suppose 25
Serial.write(loop_number) //25

Question: if all the values are sent using Serial.write or Serial.print, and all values are ints, how can I distinguish in my app if the value 25 received belongs to the photoresistor or to the loop? Is there any way to send something like (key, value) from Arduino so I can distinguish between the ints received so I can assign them correctly to my app variables?

Is there any way to send something like (key, value)

Sure:
Serial.print("LED state: ");
Serial.println(LED_state);

You will have to modify your VB code to parse that.


text:
Sending file from PC to Arduino
How can i send a (file) from PC to Arduino Yun at running time ?
There's a way to send some commands via Serial.
But how would a whole file goes ? Assuming the file can take place at RAM without any problems.
Thanks

Please be precise about what type of file and content.

Just use scp...

@leoc7 image file. JPEG extension.

@Majenko can you guide me to a link or a library ?

What OS are you using? And what do you want to do with the file?

I am using Windows10 @Majenko .

And what do you want to do with the file?

To send it to Internet via Yun. This is a firm part of the Project.

I don't understand. You want to send a file to the Yun from your PC to then send it on to "The Internet"? Why can't you just send it to "The Internet" direct from your PC?

It's a new challenge we are seeking to solve, It's an educational purpose.

Ohkay... seems pretty pointless to me. What kind of connection do you have avaliable to the Yun from your PC? WiFi? Ethernet? USB?

It's USB. to Serial pin. If it's better to use Ethernet, please guide me to a solution.

I would suggest using Ethernet or WiFi, then use scp (get Putty for Windows for that, or install one of the Linux subsystems) and scp the file over the network. Then you can access that file using Arduino code using the Bridge.h library and the FileSystem object.

See this, At the end of it they provide an example. But in our case, What would be our 'userid' and 'destination directory' ? We tried a similar approach with no success.
We've used the IP of the Yun (via Wi-Fi), In case of using Ethernet, What would be different ?

User ID is probably root. Destination directory? Whatever you want. /tmp is probably best.

Thanks, I'll try this at nearest time possible. I guess it's going to SD card directory So i don't need a command [at loop] to receive it. That's neat!

You can send a file, byte after byte, using Serial.
On the Arduino side, you parse serial communication and put bytes inside an array. At the end, you reconstruct the file.

What tool i can use to send that file from PC to Arduino ?

I think that not exist a tool like this. You should create this PC tool using, for example, Visual Studio.

The first question is what do you want to do with your image : Arduino Yun has a Linux chip & an Arduino chip.
And I don't think that image treatment must happen in the Arduino side...
So you can send your image with scp to Linux side, then do what you want with it and perhaps, eventually, send the result for action to the Arduino part.

I want to send an image, This image is to be attached to an email which would be sent to email address.

Back in the mists of time (late 1990s, if anyone's counting), there existed a file transfer protocol called XMODEM that was used to send a file across a link normally used for a terminal, on small, publicly available systems known as Bulletin Board Systems, or BBSes.
XMODEM divided a file into packets of 129 bytes, sent and acknowledged one packet at a time. It had a simple 8-bit checksum to verify the file contents which was just "ok" over a reasonably reliable line, line and inadequate on a noisy one. But it was one of the first experimenter-built and widely used protocols.
As it was pushed harder and harder (larger file sizes, higher line speeds intolerant of the small, single-packet handshake) and its weaknesses became more problematic,a number of derivatives were developed to address the weaknesses.
ZMODEM was one of those, which allowed the sender a "sliding window" of packets, so it could keep sending packets (up to the window maximum) without stopping to wait for each acknowledgement, and could use larger packet sizes, among other improvements.
They are relatively easy to implement, XMODEM more-so, and source code or specs can be found by looking around.
If your files aren't horrendously large and the lines are fairly reliable, even XMODEM may be adequate.


text:
Arduino Uno will not connect to MAC computer running Sierra
I purchased an Arduino Uno. I am trying to set it up, but when I got to the "port" on my MAC, there is no option to select anything related to my board. The only connections the port tab allows me to connect to is the bluetooth incoming port, which is not correct because it gives me errors when I try to set up the UNO to block on and off for 1 second. I know this is the legit Arduino Uno, so why is the bluetooth not connecting?

Your board is plugged into a the Mac via a USB cable, and the boards power LED is lit? There should be an entry in the Tools | Ports menu that doesn't appear when the board is not plugged in. And you have to close and reopen the menu each time you plug/unplug a board; the menu only updates each time you open it. Are you sure the USB cable is a full cable - data wires as well as power? Not all of them are. Then try another cable, another port, another Arduino, another Mac, until you've eliminated the faulty component.

I assume you have installed Arduino IDE on your mac and connecting board to mac using USB cable. Many time it happens due to driver or OS reason. Just plug the Arduino to another USB port and it should work.


text:
5V MCP2515 to 3.3V Teensy. How to reduce the MISO voltage
So to try and speed up my project, I have moved from using two UNO's to a UNO on the receive side, and teensy 3.6 on the sender side. However, no dice. The UNO  doesn't receive any data or even try to print it. I have found it gets to the line;
if(!digitalRead(CAN0_INT))

and then the program won't proceed. I have swapped out the teensy and run the same code on an UNO again on the sender to check all the connections work and it is fine, as soon as I plug in the teensy no messages are received.
As far as I can tell the MCP2515 module does not work on 3.3V, so I'm wondering if it is that. So, my plan is to power the MCP2515 from a 5V source, and drop the voltage on the interrupt and MISO line to 3.3V so the teensy is safe.
However I am unsure on how to do this, and I also need a quick fix as i'm away this afternoon until January and don't have a logic converter to hand. I have seen you can use a voltage divider to reduce voltage but will that be an issue as that solution is apparently only for slow signals?
Any other thoughts on why this setup won't work are welcome. So just incase I have added my code that works on UNO's but not on teensy. My only other thought why this won't work is that teensy 3.6 already has CAN bus and the code is not compatible?
Sender
// CAN Send Example
//

#include <mcp_can.h>
#include <SPI.h>
#include <Wire.h>

const int MPU_addr = 0x68; // I2C address of the MPU-6050

float lastTimeSent;
const float intervalSendMs = 0.000001; // Send period in milliseconds
float currMillis;

int16_t AccX, AccY, AccZ, Tmp, GyX, GyY, GyZ;
uint8_t dataArray[32];
uint8_t data1[8], data2[8];
int Switch = 7;
const int AS_Pin = 10;

#define CAN0_INT 2    // Set INT to pin 2
MCP_CAN CAN0(9);     // Set CS to pin 10

void setup()
{
    Serial.begin(115200);

    initializeMCP2515();

    pinMode(Switch, OUTPUT);
    digitalWrite(Switch, HIGH);

    initializeMPU9250();

}

void loop()
{
    currMillis = millis();

    if ((currMillis - lastTimeSent) >= intervalSendMs)
    {
        lastTimeSent += intervalSendMs;

        readFromMPU9250();

        //MPU_Data_to_CAN_Array();

        convertDataToPackets();

        // Send the two frames; if the first sending is successful send also the second, otherwise abort
        // send data frame 1:  ID = 0x100, Standard CAN Frame, Data length = 8 bytes, 'data' = array of data bytes to send
        // send data frame 2:  ID = 0x101, Standard CAN Frame, Data length = 8 bytes, 'data' = array of data bytes to send
        if (CAN0.sendMsgBuf(0x100, 0, 8, data1) == CAN_OK)
            CAN0.sendMsgBuf(0x101, 0, 8, data2);
    }

                  Serial.print(currMillis);
                  Serial.print("\t");
                  Serial.print(AccX);
                  Serial.print("\t");
                  Serial.print(AccY);
                  Serial.print("\t");
                  Serial.print(AccZ);
                  Serial.print("\t");
                  Serial.print(GyX);
                  Serial.print("\t");
                  Serial.print(GyY);
                  Serial.print("\t");
                  Serial.println(GyZ);

}

//===================================================================================
//                                  FUNCTIONS
//===================================================================================
void initializeMCP2515()
{
    // Initialize MCP2515 running at 16MHz with a baudrate of 500kb/s and the masks and filters disabled.
    if(CAN0.begin(MCP_ANY, CAN_1000KBPS, MCP_16MHZ) == CAN_OK)
        Serial.println("MCP2515 Initialized Successfully!");
    else
        Serial.println("Error Initializing MCP2515...");

    CAN0.setMode(MCP_NORMAL);   // Change to normal mode to allow messages to be transmitted
}

void initializeMPU9250()
{
  pinMode(AS_Pin, OUTPUT);
  digitalWrite(AS_Pin, HIGH);
  SPI.setClockDivider(SPI_CLOCK_DIV4);
  SPI.setDataMode(SPI_MODE0);
  SPI.begin();
}

void readFromMPU9250()
{
      digitalWrite(AS_Pin, LOW);
  SPI.transfer(0x80|0x3B);

  for(int i = 0; i < 14; i++){
  dataArray[i] = SPI.transfer(0);
  }
  digitalWrite(AS_Pin, HIGH);
delay(50);

AccX = dataArray[0]<<8|dataArray[1];
AccY = dataArray[2]<<8|dataArray[3];
AccZ = dataArray[4]<<8|dataArray[5];
GyX = dataArray[8]<<8|dataArray[9];
GyY = dataArray[10]<<8|dataArray[11];
GyZ = dataArray[12]<<8|dataArray[13];
}

void convertDataToPackets()
{
    long2Byte(currMillis, 0, data1);
    int2Byte(AccX, 4, data1);
    int2Byte(AccY, 6, data1);

    int2Byte(AccZ, 0, data2);
    int2Byte(GyX, 2, data2);
    int2Byte(GyY, 4, data2);
    int2Byte(GyZ, 6, data2);
}

void int2Byte(int16_t input, int pos, uint8_t *data)
{
    for (int i = 0; i < 2; i++)
    {
        data[i + pos] = ((input >> (i * 8)) & 0xff);
    }
}

void long2Byte(uint32_t input, int pos, uint8_t *data)
{
    for (int i = 0; i < 4; i++)
    {
        data[i + pos] = ((input >> (i * 8)) & 0xff);
    }
}

/*********************************************************************************************************
  END FILE
*********************************************************************************************************/

Receiver
// CAN Receive Example
//

#include <mcp_can.h>
#include <SPI.h>

long unsigned int rxId;
unsigned char len = 0;
unsigned char rxBuf[8];
uint8_t receivedFirstFrame;

char msgString[128];                        // Array to store serial string
uint32_t TimeMicro;
int16_t AccX, AccY, AccZ, GyX, GyY, GyZ;

#define CAN0_INT 2  // Set INT to pin 2
MCP_CAN CAN0(10);   // Set CS to pin 10

void setup()
{
    Serial.begin(115200);

    initializeMCP2515();

    Serial.println("MCP2515 Library Receive Example...");
    Serial.println("waiting for data");
    receivedFirstFrame = 0;
    Serial.println("data recived?");
}

void loop()
{
    if(!digitalRead(CAN0_INT))
    {
        // Received a message
        if (CAN0.readMsgBuf(&rxId, &len, rxBuf) == CAN_OK)
        {
            // Note: the above line is not like in the examples, but looking at the code the
            // function may return if no message was in the queue, so I think this is safer

            // Let's check if it is one of the known messages
            switch (rxId)
            {
            case 0x100:
                { // Received first frame
                    // Decode the content and store that the first frame was received
                    decodeFirstFrame(rxBuf);
                    receivedFirstFrame = 1;
                    Serial.print(TimeMicro);
                    Serial.print("\t");
                    Serial.print(AccX);
                    Serial.print("\t");
                    Serial.print(AccY);

                }
                break;
            case 0x101:
                if (receivedFirstFrame)
                { // Received second frame after a first frame
                    // Decode the content
                    decodeSecondFrame(rxBuf);

                  Serial.print("\t");
                  Serial.print(AccZ);
                  Serial.print("\t");
                  Serial.print(GyX);
                  Serial.print("\t");
                  Serial.print(GyY);
                  Serial.print("\t");
                  Serial.println(GyZ);

                    //printDataToSerial();

                    receivedFirstFrame = 0;
                }
                break;
            }
        }
    }

    TimeMicro = 0;
    AccX = 0;
    AccY = 0;
    AccZ = 0;
    GyX = 0;
    GyY = 0;
    GyZ = 0;
}

//===================================================================================
//                                  FUNCTIONS
//===================================================================================

void initializeMCP2515()
{
    // Initialize MCP2515 running at 16MHz with a baudrate of 500kb/s and the masks and filters disabled.
    if(CAN0.begin(MCP_ANY, CAN_1000KBPS, MCP_16MHZ) == CAN_OK)
        Serial.println("MCP2515 Initialized Successfully!");
    else
        Serial.println("Error Initializing MCP2515...");

    CAN0.setMode(MCP_NORMAL);   // Change to normal mode to allow messages to be transmitted

    pinMode(CAN0_INT, INPUT);                            // Configuring pin for /INT input
}

void decodeFirstFrame(uint8_t *rxBuff)
{
    TimeMicro = byte2Double(TimeMicro, 0, rxBuff);
    AccX = byte2Int(AccX, 4, rxBuff);
    AccY = byte2Int(AccY, 6, rxBuff);
}

void decodeSecondFrame(uint8_t *rxBuff)
{
    AccZ = byte2Int(AccZ, 0, rxBuff);
    GyX = byte2Int(GyX, 2, rxBuff);
    GyY = byte2Int(GyY, 4, rxBuff);
    GyZ = byte2Int(GyZ, 6, rxBuff);
}

uint32_t byte2Double(uint32_t output, int pos, uint8_t data[4]){
      for (int i = 0; i < 4; i++)
    {
      output += ((uint32_t)data[i + pos]) << (i * 8);
    }
    return output;
}

int16_t byte2Int(int16_t output, int pos, uint8_t data[2]){
      for (int i = 0; i < 2; i++)
    {
      output += ((int16_t)data[i + pos]) << (i * 8);
    }
    return output;
}
/*********************************************************************************************************
  END FILE
*********************************************************************************************************/

Thanks

search for arduino logic level converter

That is my plan for when I'm back but I wanted to test the setup before I left. Is there no quick fixes just so I can test for 10 seconds?

Why should a voltage divider only for slow signals? Is the parasite capacitance of the lines really that big?

The MCP2515 works fine at 3.3V. Check the Electrical Characteristics in the datasheet,  VDD: 2.7V to 5.5V

Thanks majenko, the seller I bought it from had it down as 5V only so must have made a mistake. The voltage divider question I'm not sure on. There seems to be a lot of conflicting views on methods for reducing voltage for sensors. I had read somewhere for things like spi voltage dividers weren't fast enough


text:
Using an OV7670, Arduino Uno, ESP8266 and SD card
I am planning to create a project which will take a picture with OV7670 and Arduino Uno with SD card and send it to server with ESP8266.
is it possible to use Arduino Uno(it has only 2k RAM memory)?

you now you can buy an IP camera?

I think if you want to save and deploy more than just simple still images in rather big time distances you won't get lucky with the Uno. All the data would have to go through the Uno, which is not a trivial task. Though it may be possible, you should consider using a more capable board.

And why do you want to use the Uno? The ESP is way more powerful (it's not just the wifi functionality)


text:
"AtLibUsbDfu.dll not found" when using FLIP on Uno R3
Attempting to flash a new firmware with FLIP results in a "AtLibUsbDfu.dll not found" error and windows says that "Arduino Uno" already has the latest drivers.
How do I fix the AtLibUsbDfu.dll error? All sources say to update the driver to fix this but I already have the latest driver and windows wont let me change it.

A quick google for AtLibUsbDfu.dll results in many "How to fix..." websites. And even some videos. I'm sure they can help you quicker and better than we can...

And you don't care about the Arduino Uno drivers. They are irrelevant. They are only for the CDC/ACM firmware, which you are replacing.


text:
Wemos D1 mini with relay shield (why does D1 not operate relay but D5 does)?
I connect gnd>gnd, 5v>5v and d1>d1 - nothing works with relay blink code
I change connection to d5 on wemos (still d1 on relay) and it works fine with code change to d5
Any ideas, as at present I can't stack the relay on the wemos? (because the d1 goes to d1)
According to pinout, D1 is "I/O, in the default mode, SCL of I2C" and GPIO5.
Thanks
Code:
/*
 * Relay Shield - Blink
 * Turns on the relay for two seconds, then off for two seconds, repeatedly.
 *
 * Relay Shield transistor closes relay when D1 is HIGH
 */

const int relayPin = D1;
const long interval = 2000;  // pause for two seconds

void setup() {
  pinMode(relayPin, OUTPUT);
}

void loop() {
  digitalWrite(relayPin, HIGH); // turn on relay with voltage HIGH
  delay(interval);              // pause
  digitalWrite(relayPin, LOW);  // turn off relay with voltage LOW
  delay(interval);              // pause
}

Also on GitHub.
Wemos D1 mini:
https://www.amazon.co.uk/gp/product/B071S8MWTY/ref=oh_aui_detailpage_o00_s01?ie=UTF8&psc=1
5V relay:
https://www.amazon.co.uk/gp/product/B07DK1FZF9/ref=od_aui_detailpages00?ie=UTF8&psc=1

post your code directly in the question.  It helps others search for your post on SE

D1 is io 5. the labels on the board have constants in code but the real io pin numers are different. if you use 5 it is D1. if you use D5 it is io 14. D1 is I2C only if you use the Wire library. the shield uses only one pin. you can't choose which one


text:
Testing a capacitor with a nodeMUC Lolin V3
Apparently it's possible to test the capacitance of a capacitor with an arduino. In this thread, someone tries to do the same on a NodeMCU but the conclusion is that it's enough to get the change in capacitantce, not the real value, and it's not "really stable" (reliable?).
I would like to get the real value of the capacitance (not just the change of the capacitance). Is there a way to do it with a NodeMCU Lolin v3?
If yes, how?
If no, will an arduino clone (like Elegoo or Geekcreit) be precise enough to give a real value of the capacitance?

An arduino uno has a high current output for a digital output pin and a high impedance analog input. The nodemcu has neither. An arduino uno clone is okay. Try a few examples that you can find. Some are accurate for small capacitance values, such as 100pF. You can start with this good example: https://www.gammon.com.au/forum/?id=12075 Please tell us what this is for. If you want to measure the soil moisture with a capacitance meter, then I think this is the wrong way.

Thanks for the link, this is a very good example. I just want to be able to test my capacitors, to see if they are working and to get their capacitance value.

And by the way, I have seen this 3€ arduino uno, do you think it will be precise enough for testing capacitors.

Yes, that will work. You need an extra driver for the ch340g usb serial chip.


text:
Relay module not working
I used 2 relay modules. One single channel 5 volt and  another 2 channel 5 volt. On connecting 5v of arduino uno the relay modules arent getting on(led on modules not on). 2 channel once worked with 9volt dc adapter supplying to arduino board.By work i mean the led on relay blinked as per code but no clicking sound.The next time i made the exact same connection and code it didn't work..Single channel arent working with 9v adapter also.Sometimes the led on single channel module is on but no switching and most of the times its not even getting on.i used 9 volt battery to supply vcc and ground to single channel module.This turned on the led on it but no switching.i don't understand how 9 volt powered 5 volt single channel relay without burning it.
Connection :: vcc to 5 v (arduino)   gnd to gnd on arduino
Digital pin 8 to in of module.
I used the blinking led type code and tried with and without serial.begin. Arduino is working as serial monitor was giving on /off output at every 2 second.
Load::200 watt bulb from 220 volts AC...under the limit of my modules i.e. 10A 230 volts
I tried 4 different single channel modules and 1 double channel.

And the Arduino is powered how? USB power is usually way too weak to switch the relay (poly fuse is fast and inrush peaks are higher than 500mA).

Provide a link for the actual modules used. Then maybe we can have an idea of how much current each relay requires to turn on.


text:
Arduino Modbus - Rtu slave with Raspberry pi using MAX-485
I am trying to use Arduino as Modbus- RTU slave and Raspberry Pi as a Modbus master
I have interfaced Max485 (RS485 to TTL converter) with Arduino and Rs485 to USB converter in Raspberry Pi, Initially, I was able to send data from Arduino to Raspberry Pi, but the data seems to inconsistent and fails to read most times
I am using https://github.com/smarmengol/Modbus-Master-Slave-for-Arduino for Arduino
Minimal Modbus for raspberry pi
Connections:
DI(max485)- TX ( Arduino),
DE(max485) -D4 ( Arduino),
RE(max485) - D4( Arduino),
Ro(max485) - RX( Arduino),
Vcc(max485) -5v( Arduino),
Gnd (max485)- GND( Arduino)
code for Arduino
#include <ModbusRtu.h>
uint16_t au16data[6] = {};
Modbus slave(5,0,4);
void setup() {
  slave.begin(19200,SERIAL_8N1 );
 }
void loop() {
  au16data[0]=100;
  au16data[1]=200;
  au16data[2]=300;
  au16data[3]=400;
  au16data[4]=500;
  au16data[5]=600;
  slave.poll( au16data, 6 );
  delay(3000);
}

python code
import minimalmodbus
from datetime import datetime
import time

instrument = minimalmodbus.Instrument('/dev/ttyUSB0', 5)
instrument.serial.baudrate = 19200
instrument.serial.bytesize = 8
instrument.serial.parity = minimalmodbus.serial.PARITY_NONE
instrument.serial.stopbits = 1
instrument.serial.timeout =5
instrument.mode = minimalmodbus.MODE_RTU

while(1):
    try:
        val = instrument.read_registers(0,6)
        # Registernumber, number of decimals
        print val
    except IOError:
        error_msg = "Failed to read from device"
        error_time = datetime.now()
        print "IO Error Time",error_time.isoformat(),error_msg

    except ValueError:
        error_msg = "Failed to read CRC"
        error_time = datetime.now()
        print "Value Error Time",error_time.isoformat(),error_msg
    time.sleep(2)

Sounds like a hardware problem. Show the schematic, and an oscilloscope trace.


text:
Doubt in choosing the right DC motor?
Take this motor as an example - https://www.robotshop.com/en/12v-100rpm-583-oz-in-brushed-dc-motor.html
it has torque of 42kg.cm
I know all the calculation to find the payload of dc motor from here - https://www.quora.com/How-do-I-calculate-how-much-weight-can-DC-motor-carry
My main concern is the output power. Power formula is:-
power = voltage x Stall Current
      = 12 x 2A = 24W
But the specification says that the power is 5W. Which value should I use in my calculation?

Do the same calculation with the rated values. What do you get?

then the value is too low, I want to make a mobile robot whose weight is 5kg. I want to use 2 dc motor for this project.

The stall current tells that the driver should be able to give that current or else the driver will get damaged. The 24W is only a calculation. I assume that the maximum mechanical power will be a few watts less. The 5W power is probably an average for normal operation. Perhaps the motor and gears are not designed to operate a long time near the stall current. Perhaps the motor gets too hot if used for a long time with more than 5W.

With a current rating of 0.68 A at 12 V you get the normal power requirement of 8.6 W for a 7Kg.cm torque.
If, for any reason, you stall the motor, your driver must be capable to output 2.2 A or 26.5 W to avoid a permanent damage.


text:
Unable to set LCD contrast using DAC pin on ESP32
I have followed the instructions at https://www.arduino.cc/en/Tutorial/HelloWorld and have my LCD displaying some text. I've also connected the LED back light (LCD pins 15&16).
I wanted to replace the potentiometer used to set the contrast, with a connection to the DAC pin. It needs to be about 0.8V.
When I connect the contrast pin from the LCD to my DAC pin on my ESP32 board, it doesn't work, the contrast is too high. Using a volt meter, it measures about 2.5V.
If I disconnect the LCD contrast pin from my DAC pin, the voltage measured is 0.8V.
Any ideas or examples on how to control the LCD contrast using a DAC pin?
I wondered if I need to add a resistor or something.

https://www.esp32.com/viewtopic.php?t=5098

The DAC in the ESP32 is ok for sourcing current but not so good at sinking current, and that is what you need.
A amplifier set up as a voltage follower would work.

Could a simple pull-down resistor work as well?

Sure. Much easier :) It would need to be a balance. Low enough to pull down but not too strong for the output.

Got more details please?

One Ohm would look like a short. 10K would look like it wasn't even there. I would try something like 150-330 Ohms. You could try a resistor by itself. Find one that gives you a reasonable contrast. Then go a little lower in resistance and add the D/A output. The resistance on its own does the pulling down, the D/A just is there to bring it back some.

Sorry, I meant where do I connect what? (iI'm a noob)

Connect one side of the resistor to the contrast pin, the other to ground. After you are happy with the resistor value then connect the D/A output to the contrast pin.


text:
Arduino Uno unable to detect serial port on MAC os Mojave 10.14.2
Ive upgraded to Mojave.  I've never used Arduino before.  I was given Arduino Uno.
Arduino Uno does not find any serial ports... can't load Blink example (the first step)
In blind frustration, I tried the three ports available... None of work.
I've loaded the
CH34x_Install_V1.4.pkg
to no avail.
How do I get a serial port package that will enable serial ports in general (and more importantly for arduino)
thx,
Bruce
On a related Note: the list of things that Mojave broke is long!  To solve many problems, re-install xcode FIRST!!! and read articles on apache, there is a "new and improve" apache server embedded in mojave.

you have it mixed up .... the Arduino Uno does not detect a serial port ..... the MAC detects the Arduino Uno as a USB serial port which can then be selected in the Arduino IDE

OK.  What can I do to get the serial port to show up in the IDE?  Currently the IDE sees /dev/cs.Bluetooth-Incoming-Port, /dev/cu.BrucesiPhone-WirelessiAP and /dev/cu.SSDC

I have this problem too ... plug the arduino into a USB port and nothing happens. (https://www.youtube.com/watch?v=mlejsgxOxrU)

If you are using a genuino or genuine Arduino, the most common cause of this is using a USB power only cable to connect rather than a data cable. (You only need the CH34x_Install_V1.4.pkg if you are running an Arduino clone based on that chipset)
If I ran the world, the USB standard would include some way to distinguish whether it's power only or power and data without having to test it with a multimeter. I know, I know, that's crazy talk.


text:
Sensors are not function with ESP8266 WeMos-D1R2
I attached all sensor into the Wemos-D1 for uploading the sensor data to the server. but when I upload the data to the server, it connects to the server but cannot save the data into the database and after that send the second data to the server, it shows connections failed... besides, the sensor such as ultrasonic sensor and IR sensor cannot function.
here is the source code for connecting the sensor to the wemos. Not sure the connecting those sensors are correct or not to the wemos.
#include <ESP8266WiFi.h>
#include <ESP.h>
#include <LiquidCrystal.h>
//LiquidCrystal LCD(12, 11, 5, 4, 3, 2);
LiquidCrystal LCD(D0,D1, D5, D4, D3, D2);
const char* ssid     = "wifi username";
const char* password = "wifi password";
const char* host = "192.168.1.10";

#define in  D7 //7
#define out D8 //8
#define trigPin D2 //10
#define echoPin D3 //13
#define relay D2 //2
#define led D6 //6            //red color
#define led2 D0           //yellow color
#define led3 D1 //9           //green color

int count = 0;

int distanceCm;
long duration;

void IN()
{
  count++;
  LCD.clear();
  LCD.print("Number of Item:");
  LCD.setCursor(0, 1);
  LCD.print(count);
  delay(10);
  LCD.setCursor(3, 1);
  LCD.print(distanceCm);
  delay(10);
  LCD.setCursor(6, 1);
  LCD.print(" cm");
  if (distanceCm <= 3) {
    delayMicroseconds(10);
    LCD.setCursor(10, 1);
    LCD.print("Full");
    digitalWrite(led, HIGH);
  } else {
    digitalWrite(led, LOW);
  }

  if (distanceCm > 3 && distanceCm <= 5) {
    delayMicroseconds(10);
    LCD.setCursor(10, 1);
    LCD.print("Enable");
    digitalWrite(led2, HIGH);
  } else {
    digitalWrite(led2, LOW);
  }

  if (distanceCm > 5) {
    delayMicroseconds(10);
    LCD.setCursor(10, 1);
    LCD.print("Empty");
//    digitalWrite(led3, HIGH);
  } else {
//    digitalWrite(led3, LOW);
  }
  delay(500);
}

void OUT()
{
  count--;
  LCD.clear();
  LCD.print("Number of Item:");
  LCD.setCursor(0, 1);
  LCD.print(count);
  delay(10);
  LCD.setCursor(3, 1);
  LCD.print(distanceCm);
  LCD.setCursor(6, 1);
  LCD.print(" cm");
  if (distanceCm <= 3) {
    delayMicroseconds(10);
    LCD.setCursor(10, 1);
    LCD.print("Full");
    digitalWrite(led, HIGH);
  } else {
    digitalWrite(led, LOW);
  }

  if (distanceCm > 3 && distanceCm <= 5) {
    delayMicroseconds(10);
    LCD.setCursor(10, 1);
    LCD.print("Enable");
    digitalWrite(led2, HIGH);
  } else {
    digitalWrite(led2, LOW);
  }

  if (distanceCm > 5) {
    delayMicroseconds(10);
    LCD.setCursor(10, 1);
    LCD.print("Empty");
    digitalWrite(led3, HIGH);
  } else {
    digitalWrite(led3, LOW);
  }
  delay(500);
}

void setup() {
  // put your setup code here, to run once:
  Serial.begin(115200);
  delay(10);

  pinMode(trigPin, OUTPUT);
  pinMode(echoPin, INPUT);

  pinMode(led, OUTPUT);
  pinMode(led2, OUTPUT);
  pinMode(led3, OUTPUT);

  LCD.begin(16, 2);
  LCD.print("Item Counter");
  delay(2000);

  pinMode(in, INPUT);
  pinMode(out, INPUT);
  pinMode(relay, OUTPUT);

  LCD.clear();
  LCD.print("Item In Box:");
  LCD.setCursor(0, 1);
  LCD.print(count);
  // ESP.restart();
  Serial.println();
  Serial.println();
  Serial.print("Connecting to ");
  Serial.println(ssid);

  WiFi.begin(ssid, password);

  while (WiFi.status() != WL_CONNECTED) {
    delay(500);
    Serial.print(".");
    // ESP.wdtFeed();
  }

  Serial.println("");
  Serial.println("WiFi connected");
  Serial.println("IP address: ");
  Serial.println(WiFi.localIP());
}

int value = 0;
void loop() {

  delay(0);
  delay(5000);
  ++value;

  digitalWrite(trigPin, LOW);
  delayMicroseconds(10);
  digitalWrite(trigPin, HIGH);
  delayMicroseconds(50);
  digitalWrite(trigPin, LOW);

  duration = pulseIn(echoPin, HIGH);
  distanceCm = duration * 0.034 / 2;

  //******************************************************//
  //IR Sensor Counting Object
  if (digitalRead(in) == HIGH && digitalRead(out) == LOW) {
    IN();
  }

  if (digitalRead(out) == HIGH && digitalRead(in) == LOW) {
    OUT();
  }

  if (count <= 0)
  {
    LCD.clear();
    digitalWrite(relay, LOW);
    LCD.clear();
    LCD.print("No Item in box");
    LCD.setCursor(0, 1);
    LCD.print("box is empty");
    delay(200);
  }
  else {
    digitalWrite(relay, HIGH);
  }

  Serial.print("connecting to ");
  Serial.println(host);

  // Use WiFiClient class to create TCP connections
  WiFiClient client;
  const int httpPort = 8095;
  if (!client.connect(host, httpPort)) {
    Serial.println("connection failed");
    return;
  }
  if (WiFi.status() != WL_CONNECTED) {
    WiFi.begin(ssid, password);
    while (WiFi.status() != WL_CONNECTED)
    {
      Serial.println("Waiting for connection");
      delay(0);
    }
  }

  String IRCount, myDistance;
  IRCount = String(count);
  myDistance = String(distanceCm);
  // We now create a URI for the request
  String url = "/Registration/write_data.php";
  url += "?item=";
  url += IRCount;
  url += "&distance=";
  url += myDistance;

  Serial.print("Requesting URL: ");
  Serial.println(url);

  // This will send the request to the server
  client.print(String("GET ") + url + " HTTP/1.1\r\n" +
               "Host: " + host + "\r\n" +
               "Connection: close\r\n\r\n");
  int timeout = millis() + 5000;
  while (client.available() == 0) {
    if (timeout - millis() < 0) {
      Serial.println(">>> Client Timeout !");
      client.stop();
      return;
    }
  }

  // Read all the lines of the reply from server and print them to Serial
  while (client.available()) {
    String line = client.readStringUntil('\r');
    Serial.print(line);
  }

  Serial.println();
  Serial.println("closing connection");
}

Anyone has the solutions please help me

is the LCD SPI? you use 4 pins D5/SCK, D6/MISO, D7/MOSI, D8/SS like it would be 10 different pins. how did you wire things?

LCD wire code is LCD(MISO, MOSI,D5, D4, D3, D2) which consists of 6pins for the LCD and then the IN and OUT pins are IR SENSOR PINS AND TRIG AND ECHO for the ultrasonic sensor pins but all of these sensors can’t work.

MISO is D6, MOSI id D7. why do you use SPI pin defines if it is not SPI?

MISO is the Wemos board pins... if I use the arduino board pins it wouldn’t work

Wemos has D0 to D8. MISO and MOSI are aliases to D6 and D7

But for what I attach  the MISO and MOSI pins are representing the D12 and D11

I have edited the pins based on just now u mention there are only D0 to D8 in wemos. So, I have edited the source code as above... but it shows this error: espcomm_upload_mem failed

but you how do you wire it if D2, D3 are for display and for ultrasonic sensor and relay at the same time? pins D3,  D4 and D8 are boot setup pins with pull-ups and pull-down (D8). this state must be preserved at boot. the wired devices must not pull-down D3 and D4 to LOW or set D8 HIGH before they are initialized in setup()

= = I have no idea already because I use the Arduino UNO board logic to wire it

Because i have 2 IR sensor, 1 ultrasonic sensor and LCD which must connect it to the Wemos board

use I2C LCD or don't use LCD but make a web page

make a web page?

you mean that if i dont use LCD then i have enough pins for me to connect ?

or display the data on the webpage that is what i want

I meant a local web page

Ya that what I going to do. Now For what I do is uploading this data into the php file and this php file will save it into the database. After that I use the webpage to read this data from the database and display it on the local webpage

Just for clarification, there are nine pins for me to attach the sensor (D0 -D8) in wemos. So if I attach the sensor to those pins (D0 -D8) so it can function and directly upload the data ?

yes. only test the sensors on different pins to find out what doesn't disturb D3, D4 and D8 at boot. and avoid D0 if you can. it is a little special too


text:
Low Level programming - MKR Fox1200
I'm working on a project using this board and wish to do so on a low level ,as in enabling certain registers to enable interrupts etc.
I can't seem to find the correct header files to support programming in this manner (Can't recognise the register names), I've tried using both Atmel Studio and the Arduino IDE but can't seem to get it to work.
Any help would be greatly appreciated

What kind of "low level" do you mean?  Why not look up the chip data sheet?  For example: https://www.mouser.com/ds/2/268/atmel-42181-sam-d21_datasheet-1065532.pdf

If you have installed the MKL Fox 1200 on your computer, then the needed header files are also installed.  They can be rather difficult to find, however the find command works well for this job

I programming from the datasheet, I have the header files imported manually but it doesn't seem to work correctly


text:
esp32 spi library, how read a mcp23s08 register
thanks for any help
I need to read a gpio expander mcp23s08 set as 8 bits input.
my code write correctly (I believe) the setup register using SPI library, with the enclosed example modified.
But I do not understand how read a gpio register (0x09)
code (with the read out routine wrong:
#define GPIO_SEL_pin 14                         // D14 = MCP23S08 GPIO SPI select pin
#define SCLK 18                                 // D18 SPI SCLK
#define MISO 19                                 // D19 SPI MISO
#define MOSI 23                                 // D23 SPI MOSI

#include <SPI.h>

uint8_t keyboard;

static const int spiClk = 1000000; // 1 MHz

//uninitalised pointers to SPI objects
SPIClass * mcp23s08 = NULL;

void setup() {
  Serial.begin(115200);
  pinMode(GPIO_SEL_pin, OUTPUT);                     //MCP23S08 SPI select pin
  digitalWrite(GPIO_SEL_pin, HIGH);                  //pull ss high to disable data transfer
  mcp23s08 = new SPIClass(VSPI);
  mcp23s08->begin(SCLK, MISO, MOSI, GPIO_SEL_pin);   //SCLK, MISO, MOSI, SS
  mcp23s08SetUp();
  delay(1);

}

void loop() {
  keyboard = mcp23s08Read();
  Serial.println (keyboard);
  delay(100);
}

// ================================== routines =================================
void mcp23s08SetUp( void ) {
  uint8_t dev_adr  = 0x40;                          // MCP23S08 address 0; R/W = write
  uint8_t reg_adr  = 0x00;                          // MCP23S08 IODIR register
  uint8_t reg_data = 0xFF;                          // pin configured as input

  digitalWrite(GPIO_SEL_pin, LOW);                 //pull SS slow to prep other end for transfer
// ============================= MCP3S08 pin as input ==============================
  mcp23s08->beginTransaction(SPISettings(spiClk, MSBFIRST, SPI_MODE0));
  mcp23s08->transfer(dev_adr);
  mcp23s08->transfer(reg_adr);
  mcp23s08->transfer(reg_data);
  mcp23s08->endTransaction();

  reg_adr  = 0x01;                                 // MCP23S08 IPOL register
  reg_data = 0xFF;                                 // invert input polarity
// ============================= MCP3S08 invert input ==============================
  mcp23s08->beginTransaction(SPISettings(spiClk, MSBFIRST, SPI_MODE0));
  mcp23s08->transfer(dev_adr);
  mcp23s08->transfer(reg_adr);
  mcp23s08->transfer(reg_data);
  mcp23s08->endTransaction();

  reg_adr  = 0x06;                                 // MCP23S08 GPPU pull-up register
  reg_data = 0xFF;                                 // set pull-up register
// ============================= MCP3S08 pullup resistor ==============================
  mcp23s08->beginTransaction(SPISettings(spiClk, MSBFIRST, SPI_MODE0));
  mcp23s08->transfer(dev_adr);
  mcp23s08->transfer(reg_adr);
  mcp23s08->transfer(reg_data);
  mcp23s08->endTransaction();

  digitalWrite(GPIO_SEL_pin, HIGH);                //pull ss high to signify end of data transfer
}

uint8_t mcp23s08Read ( void ) {
  uint8_t dev_adr  = 0x41;                          // MCP23S08 address 0; R/W = read
  uint8_t reg_adr  = 0x09;                          // MCP23S08 GPIO register
  uint8_t reg_data;                                 // GPIO register
  mcp23s08->beginTransaction(SPISettings(spiClk, MSBFIRST, SPI_MODE0));
  mcp23s08->transfer(dev_adr);
  mcp23s08->transfer(reg_adr);
  reg_data = mcp23s08->transfer(0x00);
  mcp23s08->endTransaction();
  return reg_data;
}

Why do you toggle SS inside mcp23s08SetUp() function and NOT inside mcp23s08Read()?
I don't remember if SS pin is managed by SPI Arduino library, but you can try it.

Yes, you are right. Just forgot to toggle the ss pin.

Hi @Angelo Gilin Maggiora if this answer has solved your question please consider accepting it by clicking the check-mark. This indicates to the wider community that you've found a solution and gives some reputation to both the answerer and yourself. There is no obligation to do this.

Thanks a lot for your help. @leoc7 could you tell me where is the check-mark button? I did not find in the page. Sorry, I am a newbe

Read answer of this question in order to know how to accept an answer. :) https://meta.stackexchange.com/questions/5234/how-does-accepting-an-answer-work

I, hopefully, did it. Isn't it

I would submint the full working example of setting up and readout of GPIO expander MCP23S08 using esp32 and SPI bus.

You forgot to toggle SS pin in mcp23s08Read() function.
 uint8_t mcp23s08Read ( void ) {
      ----> digitalWrite(GPIO_SEL_pin, LOW);                 //pull SS slow to prep other end for transfer
      uint8_t dev_adr  = 0x41;                          // MCP23S08 address 0; R/W = read
      uint8_t reg_adr  = 0x09;                          // MCP23S08 GPIO register
      uint8_t reg_data;                                 // GPIO register
      mcp23s08->beginTransaction(SPISettings(spiClk, MSBFIRST, SPI_MODE0));
      mcp23s08->transfer(dev_adr);
      mcp23s08->transfer(reg_adr);
      reg_data = mcp23s08->transfer(0x00);
      mcp23s08->endTransaction();
      ----> digitalWrite(GPIO_SEL_pin, HIGH);                //pull ss high to signify end of data transfer
      return reg_data;
    }


text:
Error with Sparkfun MP3 Shield and Arduino Due playing music files
The code worked on my Ardino Uno. I plugged it up the exact same way and am now getting an error.
Here is the error I get when I try to upload my code to the due:
Arduino: 1.8.5 (Windows 10), Board: "Arduino Due (Programming Port)"

C:\Program Files (x86)\Arduino\libraries\SFEMP3Shield\SFEMP3Shield.cpp: In static member function 'static void SFEMP3Shield::refill()':

C:\Program Files (x86)\Arduino\libraries\SFEMP3Shield\SFEMP3Shield.cpp:1984:7: error: 'sei' was not declared in this scope

   sei();

       ^

C:\Program Files (x86)\Arduino\libraries\SFEMP3Shield\SFEMP3Shield.cpp:2006:9: error: 'cli' was not declared in this scope

     cli(); // allow transfer to occur with out interruption.

         ^

C:\Program Files (x86)\Arduino\libraries\SFEMP3Shield\SFEMP3Shield.cpp: In member function 'void SFEMP3Shield::SendSingleMIDInote()':

C:\Program Files (x86)\Arduino\libraries\SFEMP3Shield\SFEMP3Shield.cpp:2053:7: error: 'cli' was not declared in this scope

   cli(); // allow transfer to occur with out interruption.

       ^

C:\Program Files (x86)\Arduino\libraries\SFEMP3Shield\SFEMP3Shield.cpp:2067:7: error: 'sei' was not declared in this scope

   sei();  // renable interrupts for other processes

       ^

exit status 1
Error compiling for board Arduino Due (Programming Port).

This report would have more information with
"Show verbose output during compilation"
option enabled in File -> Preferences.

Here is my code:
#include <SPI.h>
#include <SdFat.h>
#include <SdFatUtil.h>
#include <SFEMP3Shield.h>

SdFat sd;
SFEMP3Shield MP3player;

const uint8_t volume = 10; // MP3 Player volume 0=max, 255=lowest (off)
//10 for normal 50 for testing

const uint16_t monoMode = 1;

void setup() {
  initSD();
  initMP3Player();
}

void loop() {
  if(!MP3player.isPlaying()){
    MP3player.playTrack(1);
  }
}

void initSD() {
  if(!sd.begin(SD_SEL, SPI_HALF_SPEED))
    sd.initErrorHalt();
  if(!sd.chdir("/"))
    sd.errorHalt("sd.chdir");
}

void initMP3Player() {
  uint8_t result = MP3player.begin();
  MP3player.setVolume(volume, volume);
  MP3player.setMonoMode(monoMode);
}

The library is written for the Uno, not the Due. It relies on two instructions that are only available in the AVR compiler.
Newer versions of the core provide a pair of macros, interrupts() and noInterrupts() that should be used in place of sei() and cli() respectively, which should be provided by the Due's core as well to make it cross-platform. However that library has never been updated to work with those macros.
You could replace the sei() and cli() calls in the library with interrupts() and noInterrupts(), however that may not make it work, since it was written with the Uno and other AVR based chips in mind.

I don't have permission to change that library file. Do you know how I can get it?

You must have permission to edit it, otherwise you won't have been able to install it in the first place. Or are you on some strange system controlled by some overarching all knowing power?

I just changed the permissions in the properties. The code uploads, but the board does nothing. It doesn't even blink when I hit reset.

I feared as much. The library probably needs much work to run on a due.

do you have a suggestion on how i can play mp3 files on a due, maybe a different shield or something?

You just need either a library for that shield that works with the due, or you need to learn how the shield works and write a new library for it.

The mega uses the same libraries as the uno right?