text:
Connection ESP8266 to ESP8266 Client Server can't Connect, Help me?
I have a project to connecting dual esp8266 using client server method, my expectation the server can get command from user from web request, and the request will be forward to client from server to turn on led. But the connection from server always failed
I'm using ESP-12F and programming using Arduino IDE
the code of server :
//--------------------------------------------------------------------------
  #include <ESP8266WiFi.h>
//--------------------------------------------------------------------------
// Membuat Variabel Autentikasi
//--------------------------------------------------------------------------
  const char* ssid = "master-sport";
  const char* password = "1234567890";
//--------------------------------------------------------------------------
// Mengatur IP Address
//--------------------------------------------------------------------------
  IPAddress CLIENTA(192,168,4,100);
//--------------------------------------------------------------------------
// Create an instance of the server
// specify the port to listen on as an argument
//--------------------------------------------------------------------------
  WiFiServer server(80);
  WiFiClient client;
//===========================================================================
  void setup() {
   Serial.begin(115200);
   delay(10);

  // Mengatur WiFi ----------------------------------------------------------
   Serial.println();
   Serial.print("Configuring access point...");

   WiFi.mode(WIFI_AP);
   WiFi.softAP(ssid, password);

  // Start the server -------------------------------------------------------
   server.begin();
   Serial.println("Server dijalankan");

  // Print the IP address ---------------------------------------------------
   Serial.println(WiFi.localIP());
 }

//===========================================================================

  void loop() {
  // Check if a client has connected ----------------------------------------
    client = server.available();
    if (!client) {
    return;
  }

  // Wait until the client sends some data ----------------------------------
   Serial.println("new client");
   while(!client.available()){
     delay(1);
  }

  // Read the first line of the request -------------------------------------
   String req = client.readStringUntil('\r');
   Serial.println(req);
   client.flush();

  // Match the request ------------------------------------------------------
   const char* host;
   int val;
   if (req.indexOf("/sr/0") != -1){
      host = "sa";
      val = 0;
    }
   else if (req.indexOf("/sr/1") != -1){
      host = "sa";
      val = 1;
    }
   else {
     Serial.println("invalid request");
     client.stop();
     return;
    }

   client.flush();
   Serial.println("Client disonnected");

  // Pengiriman data ke client -----------------------------------------------
   int value  = 0;
   delay(5000);
   ++value;

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

  // Memebuat TCP Connection Menggunakan WiFiClient --------------------------
   const int httpPort = 80;
   if (!client.connect(CLIENTA, httpPort)) {
     Serial.println("connection failed");
     return;
   }

  // Membuat URL untuk dikirimkan -------------------------------------------
   String url = host;
   url += "/";
   url += val;

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

  // Mengirimkan Request ke Client ------------------------------------------
   client.print(String("GET ") + url + " HTTP/1.1\r\n" +
               "Host: " + CLIENTA + "\r\n" +
               "Connection: close\r\n\r\n");
   unsigned long timeout = millis();
   while (client.available() == 0) {
     if (millis() - timeout > 5000) {
       Serial.println(">>> Client Timeout !");
       client.stop();
       return;
    }
  }

  // Melihat semua line balasan dari server dan menampilkan di Serial -------
   while(client.available()){
     String line = client.readStringUntil('\r');
     Serial.print(line);
   }

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

Client code :
//--------------------------------------------------------------------------
  #include <ESP8266WiFi.h>
  #include <Adafruit_NeoPixel.h>
  #ifdef __AVR__
  #include <avr/power.h>
  #endif
  #define PIN 13
//--------------------------------------------------------------------------
// Membuat Variabel Autentikasi
//--------------------------------------------------------------------------
  const char* ssid = "master-sport";
  const char* password = "1234567890";
//--------------------------------------------------------------------------
// Mengatur IP Address
//--------------------------------------------------------------------------
  IPAddress IP(192,168,4,100);
  IPAddress NETMASK(255,255,255,0);
  IPAddress NETWORK(192,168,4,1);
//--------------------------------------------------------------------------
// Create an instance of the server
// specify the port to listen on as an argument
//--------------------------------------------------------------------------
  WiFiServer server(80);
//--------------------------------------------------------------------------
// Menasukan LED RGB
//--------------------------------------------------------------------------
  Adafruit_NeoPixel strip = Adafruit_NeoPixel(60, PIN, NEO_GRB + NEO_KHZ800);
//===========================================================================
  void setup() {
   Serial.begin(115200);
   delay(10);

  // Connect to WiFi network ------------------------------------------------
   Serial.println();
   Serial.println();
   Serial.print("Connecting to ");
   Serial.println(ssid);

  // Mengatur WiFi ----------------------------------------------------------
   WiFi.mode(WIFI_STA);
   WiFi.begin(ssid, password);
   WiFi.config(IP, NETMASK, NETWORK);

   while (WiFi.status() != WL_CONNECTED) {
     delay(500);
     Serial.print(".");
   }
   Serial.println("");
   Serial.println("WiFi connected");

  // Start the server -------------------------------------------------------
   server.begin();
   Serial.println("Server dijalankan");

  // Menjalankan LED RGB ----------------------------------------------------
   strip.begin();
   strip.show();

  // Print the IP address ---------------------------------------------------
   Serial.println(WiFi.localIP());
 }

//===========================================================================

  void loop() {
  // Check if a client has connected ----------------------------------------
    WiFiClient client = server.available();
    if (!client) {
    return;
  }

  // Wait until the client sends some data ----------------------------------
   Serial.println("new client");
   while(!client.available()){
     delay(1);
  }

  // Read the first line of the request -------------------------------------
   String req = client.readStringUntil('\r');
   Serial.println(req);
   client.flush();

  // Match the request ------------------------------------------------------
   int val;
   if (req.indexOf("/sa/0") != -1){
      strip.setPixelColor(4,0x000000); //LED menjadi mati -------------------
      strip.show();
    }
   else if (req.indexOf("/sa/1") != -1){
      strip.setPixelColor(4, 0xFF0000); //LED menjadi merah -----------------
      strip.show();
    }
   else {
     Serial.println("invalid request");
     client.stop();
     return;
    }

   client.flush();
   Serial.println("Client disonnected");
}

//============================================================================

whats wrong that code ?

Could you describe exactly how it fails, please? Does the client (station) connect to the server (access point)? Do you get the "new client" log? And so on...

the client connect to server but if my computer connect to and i try to scanning that network, client address can't detected.
i want to sending data to server from my computer, when data be received to server, data will be continued send to client. but communication failed when the server sending data to client

I don't understand, sorry, but here's my advice: solve one problem at a time. Write enough code to do the first little part of the problem. Test it. If that doesn't work, ask for help with a clear description of ONLY the problem, and only the code required to see the problem.

Your question is a bit difficult to understand but if I'm right, you want to connect an ESP to another ESP (which acts as a server) and then connect with your computer to get addresses? Well, the ESP is a very capable device, but not thát capable. I've worked with ESPs in a previous project and I decided to buy a portable wifi router (à €25) to which all the devices could connect. Furthermore, when you do get the ESPs to work as client and server, you can only connect 4 devices to an ESP. That's its limit.

Your server appears to be a client, sending a GET request.

You do not need 2 ESPs, one is enough. Here you are the code so you can turn on the NeoPixel using web interface:
#include <ESP8266WiFi.h>
#include <WiFiClient.h>
#include <ESP8266WebServer.h>

IPAddress ip(192,168,1,81);         // choose IP address
IPAddress subnet(255,255,255,0);

ESP8266WebServer server(80);

void handleRoot() {
  String page = "<!DOCTYPE html>\n";

  page += "\n\n
Some heading

Generated by ESP8266\n\n";
  server.send(200, "text/html", page);
}

// what to do when accessed through http://ip_address/something_undefined
void handleNotFound(){
  String message = "File not found\n\n";
  message += "URI: ";
  message += server.uri();
  message += "\nMethod: ";
  message += (server.method() == HTTP_GET)?"GET":"POST";
  message += "\nArguments: ";
  message += server.args();
  message += "\n";
  for (uint8_t i=0; i<server.args(); i++){
    message += " " + server.argName(i) + ": " + server.arg(i) + "\n";
  }
  server.send(404, "text/plain", message);
}

void setup(void){
  Serial.begin(74880);                      // so you can see debug messages automatically sent by ESP8266
  WiFi.mode(WIFI_AP);
  WiFi.softAPConfig(ip, ip, subnet);        // declared as: bool softAPConfig (IPAddress local_ip, IPAddress gateway, IPAddress subnet)
  WiFi.softAP("SOME_NAME", "password", 7);  // network name, network password, wifi channel

  IPAddress myIP = WiFi.softAPIP();
  Serial.println();
  Serial.print("AP IP address: ");
  Serial.println(myIP);

  server.on("/", handleRoot);               // what to do when accessed through browser using http://IP_address

  // what to do when accessed through http://ip_address/test
  server.on("/test", [](){
    server.send(200, "text/plain", "This is another page");
  });

  server.on("/sa/1", [](){
    // ... <-- put here the code for NeoPixel = on
    server.send(200, "text/html", "NeoPixel is now on");
  });

  server.on("/sa/0", [](){
    // ... <-- put here the code for NeoPixel = off
    server.send(200, "text/html", "NeoPixel is now off");
  });

  server.onNotFound(handleNotFound);

  server.begin();
  Serial.println("HTTP server started...");
}

void loop(void){
  server.handleClient();
}

Now you can use xx.xx.xx.xx/sa/1 and xx.xx.xx.xx/sa/0 (where xx.xx.xx.xx is an IP address you've chosen) to turn on/off the NeoPixel.
Just add the Adafruit library for controlling NeoPixel and copy the NeoPixel setup and the code to turn it on/off from your code #2 to the appropriate places (I marked the place where to put the code to turn the NeoPixel on/off with the comments).
If you really want to add another ESP8266 then you have to set it up as a server using the same code - just change the network name, password & IP address and add sending GET request from your first ESP to the second.


text:
`LOW` being defined as `0` and `HIGH` being defined as `1` - is this a part of external specification?
Arduino.h defines LOW as 0x0 and HIGH as 0x1. Does the Arduino API intend to expose that fact? Does it guarantee that this will always be that way?
In other words, what is the intended purpose of these manifest constants: LOW and HIGH?

Is this purely cosmetic mnemonics added as an alternative for 0/1 and false/true, for those who like LOW/HIGH better?
Or is this an attempt to abstract/isolate the user's source code from the actual representation of LOW and HIGH (e.g. in case the representation changes in the future)?

The underlying reason for this question is to figure out whether code like
digitalWrite(some_pin, true);
digitalWrite(some_other_pin, !digitalRead(some_other_pin));

is a good programming practice. (If LOW and HIGH are there to abstract the user's code form their actual values then code like that is definitely a bad programming practice.)

Couldn't it be both?

@jose can u c: It could. But the truly critical part here is whether the answer to the second point is "yes".

Looking at the precursor to Arduino framework, WConstants.h seems to have a commented out 0xFF as a potential definition of HIGH, so point 2 may be the case...

The underlying reason for this question is to figure out whether code like
digitalWrite(some_pin, true);
digitalWrite(some_other_pin, !digitalRead(some_other_pin));

is a good programming practice. (If LOW and HIGH are there to abstract the user's code form their actual values then code like that is definitely a bad programming practice.)

Strictly speaking, no, that is not good programming practice.
digitalRead() returns an int. digitalWrite() expects an int.  Using ! converts the int into a bool and then it's promoted back to an int again.
In fact, the "next gen" Arduino core API changes HIGH and LOW from a simple int to an enum - and that struggles with casting through bool like that:
typedef enum {
  LOW     = 0,
  HIGH    = 1,
  CHANGE  = 2,
  FALLING = 3,
  RISING  = 4,
} PinStatus;

You can see the problems that causes here.

source: Stack Exchange

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

sort: votes


text:
Time information from GPS receiver: how to tell whether it is fresh or stale?
I see that TinyGPS++ library extracts time information from GxRMC and GxGGA NMEA sentences streamed by GPS receiver. However, in my experiments I observed that both of my GPS receivers generate GxRMC sentences with time data in them at least once a second even when they have no access to satellites.
I presume that the time data comes from the internal clock of the receiver (and is maintained between warm startups). This is perfectly OK. However, I would like to know what measures are required by NMEA specification to ensure the reliability of this time data.
Am I correct in assuming that the device itself is supposed to understand that after certain period of time its internal clock will diverge? And that after that period the device will by itself stop pumping out these GxRMC sentences, until it gets a chance to see a satellite and re-sync its internal clock? Or should I expect to see the next field in GxRMC sentence to change from A to V?
If not, then what is the proper way to ensure that I receive "satellite time" (or close to that) or nothing at all?

Most of the GPS modules keep on sending the data in the NMEA format whether they have a GPS fix or not, however, you can parse the GPS data to find whether the data is the latest data received from the GPS or not. If you look at the definition of the NMEA data here, there are a few variables in the data that you can use to find whether the data is the latest data from the GPS or not.
You can use the "Fix Quality" in GPGGA as well as "Validity/Receiver warning" in GPRMC for your module. The tinyGPS indeed has both of these variables being parsed.
In the tinyGPS library, if _gps_data_good is true then the data coming from the GPS module is the latest data it received from the GPS satellites. The program uses either the fix or validity to determine this (Refer to the library here and here).
You should just keep checking this variable to find whether the current data is the latest from the GPS or is it being calculated internally.

Yes, thank you. Indeed, I just noticed that the warning field in GPRMC/GNRMC messages changes between A and V. When there's no fix, the time is reported with V (unreliable). Moreover, after a relatively long while without access to satellites, my receiver stops reporting time in GxRMC sentences entirely - the time field is left empty.

It is interesting that in this state, after partial exposure to open sky (e.g. just one or two satellites visible, no fix), the receiver again begins reporting time in GxRMC, but with V label (unreliable). At first sight, this is strange, since the time information in this case is apparently received from the satellites. V changes to A only when position fix is achieved, which is overkill in my case (I don't need position, just time).

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


text:
Arduino IDE doesn't release COM port after programming
I have an arduino mega 2560 and I'm trying to program it using Arduino IDE 1.8.1. The problem is that I also need to keep open another program that will communicate with the Arduino using the COM port. I usually have to make very small changes to the code with the IDE and then check the results in the program.
However, when the IDE has finished uploading the program it will not release the COM port, and the program I'm using will give me an error message saying "access denied". This is a problem because I want to keep both programs open at the same time.
In fact I could just: make my correction to the code, close the IDE when it has finished, open the program I need, check whether the correction I made was right, otherwise close it again and open the IDE again, but that would take an insane amount of time and it would be quite annoying.
Is there a way to force the Arduino IDE to release the COM port so that other programs could communicate with the Aduino?

To force the Arduino IDE to disconnect from the COM port, simply go into the Tools menu, go to Ports and select another COM port.
Alternatively, you can open and then close the serial port monitor (Ctrl+Shift+M then Alt+F4).

This type of problem happens many time with me. Try to disconnect your ARDUINO MEGA from your PC / LAPTOP and then connect it again. It must be solve your problem. If this will not work then restart your PC / LAPTOP and try it out again.

disconnecting the arduino right after the upload will cause the IDE to freeze.

So, first disconnect your arduino and then close IDE. And now open again IDE and connect your Arduino. Try it. Otherwise may be cable fault possible. Try it out with other cable.

I don't think you really understood my question, I've updated to make it more clear.

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


text:
Unable to read and write serial data between two arduino's (hc-05 paired) when using a sensor
What I did was that I wrote a piece of code that will-in-fact move a servo motor when a clap is detected using a sound impact sensor (fc-04).
The code for this is seen here and in fact does work:
#include "Arduino.h"
#include <Servo.h>
Servo myservo;//create servo object to control a servo
enum {
    SERIAL_BAUD        = 9600,
    SENSOR_DIGITAL_PIN =    2,
    SOUND_DELAY        =   1500, /* Delay to avoid duplicate detection */
};

void setup() {
    Serial.begin(SERIAL_BAUD);
    pinMode(SERIAL_BAUD, INPUT);
    myservo.attach(9);//attachs the servo on pin 9 to servo object
    myservo.write(0);//back to 0 degrees
    delay(1000);//wait for a second
}

void loop() {
    if (digitalRead(SENSOR_DIGITAL_PIN) == LOW) {
        static int count;

        Serial.print("Sound detected: ");
        Serial.println(++count);
        myservo.write(170);//goes to 15 degrees
        delay(3000);//wait for 3 seconds
        myservo.write(10);//back to 0 degrees
        delay(1000);//wait for a second

        // Wait a short bit to avoid multiple detection of the same sound.
        delay(SOUND_DELAY);
    }
}

On a seperate occasion I paired two arduinos together using two hc-05 bluetooth modeules making one a slave and another a master, the initial code I used for both of them are listed here:
//                 == SLAVE CODE ==

#include <Servo.h>
#define button 8

Servo myServo;
int state = 20;
int buttonState = 0;

void setup() {
  pinMode(button, INPUT);
  myServo.attach(9);
  Serial.begin(38400); // Default communication rate of the Bluetooth module
}

void loop() {
 if(Serial.available() > 0){ // Checks whether data is comming from the serial port
    state = Serial.read(); // Reads the data from the serial port
 }
 // Controlling the servo motor
 myServo.write(state);
 delay(10);

 // Reading the button
 buttonState = digitalRead(button);
 if (buttonState == HIGH) {
   Serial.write('1'); // Sends '1' to the master to turn on LED
 }
 else {
   Serial.write('0');
 }
}

and
//                == MASTER CODE ==

#define ledPin 9

int state = 0;
int potValue = 0;

void setup() {
  pinMode(ledPin, OUTPUT);
  digitalWrite(ledPin, LOW);
  Serial.begin(38400); // Default communication rate of the Bluetooth module
}

void loop() {
 if(Serial.available() > 0){ // Checks whether data is comming from the serial port
    state = Serial.read(); // Reads the data from the serial port
 }
 // Controlling the LED
 if (state == '1') {
  digitalWrite(ledPin, HIGH); // LED ON
  state = 0;
 }
 else if (state == '0') {
  digitalWrite(ledPin, LOW); // LED ON
  state = 0;
 }
 // Reading the potentiometer
 potValue = analogRead(A0);
 int potValueMapped = map(potValue, 0, 1023, 0, 255);
 Serial.write(potValueMapped); // Sends potValue to servo motor
 delay(10);
}

I attempted to use the master and slave code with the one with the servo and fc-04 so that the sound sensor will be on the master and the servo on the slave so that when ever I clap it will move the servo on the other arduino.
The new master and slave code that I used are :
//New slave
#include "Arduino.h"
#include <Servo.h>
int state = 0;
Servo myservo;

void setup() {
  Serial.begin(38400); // Default communication rate of the Bluetooth module
  myservo.attach(9);//attachs the servo on pin 9 to servo object
  myservo.write(0);//back to 0 degrees
  delay(1000);//wait for a second
  }

void loop() {
 if(Serial.available() > 0){ // Checks whether data is comming from the serial port
    state = Serial.read(); // Reads the data from the serial port
 }
// Controlling the servo
 if (state == '1') {
  myservo.write(170);//goes to 15 degrees
  delay(3000);//wait for 3 seconds
  myservo.write(10);//back to 0 degrees
  delay(1000);//wait for a second
  state = 0;
 }
 else if (state == '0') {
  state = 0;
  }
}

//new Master
#include "Arduino.h"
#include <SoftwareSerial.h>
int state = 0;
SoftwareSerial BTserial(1, 0); // RX | TX

void setup() {
    Serial.begin(9600);
    pinMode(9600, INPUT);
    BTserial.begin(38400);

}

void loop() {
    if (digitalRead(2) == LOW) {
        static int count;
        BTserial.write('1');
        delay(1500);
    }
    else {
      BTserial.write('0');
    }
}

However the slave and master code for the servo and fc-04 is not working at all despite knowing that all the conponents work individually. What I am aware of is that the fc-04 uses serial communication to transfer data and so does the hc-05 bluetooth modules. This causes an issue because I believe from experience is that you can not have two serial communications being transmitted from the arduino at the same time which I need.
I have been at this for days and It is driving me nuts.
If I could have some help at all I will be much appreciated.

SoftwareSerial BTserial(1, 0); // RX | TX

Well, there's your problem.  You are starting SoftwareSerial on the Serial pins.  Don't do that!
For best results, hook your BT to pins 8 & 9 and use AltSoftSerial.  It is much more efficient than SoftwareSerial, and it will not interfere with Serial reads and writes.
If you really can't use those pins, pick two other pins and use my NeoSWSerial.  It is almost as efficient, and it works on any PinChange interrupt pins at 9600, 19200 or 38400 baud rates.

Gotcha , so because of what I was doing it causes crosstalk then.
When I have the chance tomorrow I will make the required changes and report back on the results.
Thanks

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


text:
PWM water pump flow control - in percent
I want to control flow level on 12V water pump with PWM pin, I'm using IRF520N MOSFET for that (and dedicated 12V power supply).
I'm assuming, that setting PWM to full byte should give me about 100% or 12V. But how to set proper value on PWM pin so the flow equals to eg. 10%, 25% or 50%? Is it some logharitmic equation?

Unless the datasheet of the pump says something about it, you will have to experiment.

But is the voltage output on MOSFET linear? Like setting PWM to half gives me about 6V?

No. Setting the PWM to 50% is like having a switch ON half of the time (your motor gets nearly 12 V) and OFF (0 V) the other half. It is never at 6 V.

Expanding on dannyf's answer, if the pump datasheet does not feature a graph, then you will have to experiment. If a flowmeter is not readily available, an excellent approximation can be calculated by pumping water into a large, known receptacle (e.g. 10 litre bucket) and timing how long it takes. Do this for 20%, 40%, 60%, 80% and 100% Pulse Width Modulation modes, and you will have a plot of flow rate vs PWM that will help you interpolate the PWM required for a desired flow rate (e.g. 50% flow rate).
Below is an example of Rotations Per Minute of a 12V computer CPU cooler water pump for a given PWM input. It is assumed that this would be under load (of pumping water), but not stated explicitly.
Note that it may not be physically possible for the motor to operate with 10% or less PWM duty cycle. At this point I imagine that the internal friction of the motor and forces required to push the water along are greater than the force provided by a "10%" duty cycle.

Source: ekwb

But how to set proper value on PWM pin so the flow equals to eg. 10%, 25% or 50%?

look at the pump's datasheet; and
experiment.

You'll need to tun the pump at some number of intermediate PWM values and measure its output at each one. The more intermediate values you measure, the more precise your control can be. Then you build a table of flow-rates vs. PWM level in flow-rate order, something like:
struct {
  float flow;  // measured flow rate
  float pwm;   // pwm value that gave that rate
} FlowTable[FLOWTESTS] = {
 // flow  PWM
  {   0.,    0. },
  { 218.,  256. },
  { 480.,  512. },
  { 732.,  768. },
  { 885., 1023. }
}

For a particular flow-rate, step through the table until you find a flow in the table that is >= to the flow you want (if it's ==, just use that PWM and you're done.)
We'll interpolate between the two table values that span the desired flow-rate. The idea is, if your desired flow is say, 17% (0.17) of the way between those two flows, you want a PWM value that's about 17% of the way between the two PWM values.
Let's say you want a flow of 600 (in whatever units your measurements are in - cc/minute, for example. Index 3 in the table (remember, our arrays are 0-based) has the first measured flow greater than 600, the desired flow, so we know the required PWM will be between 512 and 768. To find it, find the desired flow as a fraction of the interval [480, 732]:
frac = (600-480)/(732-480) = 120 / 252 = 0.476,
or letting 'i' be the index of the first table entry whose flow exceeds the desired flow:
frac = (flow_des-FlowTable[i-1].flow) / (FlowTable[i].flow-FlowTable[i-1].flow);
. We need the PWM that is 47.6% of the interval [512, 768]:
pwm_req = 512 + ((768-512) * 0.476)) = 634or
' pwm_req = FlowTable[i-1].pwm + ((FlowTable[i].pwm-FlowTable[i-1].pwm) * frac);`


text:
What difference makes resistance of thermistors?
Following this thermistor tutorial i used 1k thermistors (and resistors) instead of 100k as in video.

What difference does it make?
What about 10k thermistors?
Is it good idea to use 1k/10k/100k potentiometer instead of resistors to tune up readings?

Maybe "thermistor" tag should be created here? 150 reputation required to do that.

A thermistor of 1k is less noise and more current. The 1k thermistor heats up with 6mW, I don't know if that will influence the themperature. To calculate the temperature you also need the specific numbers for that type of thermistor. When you would use the numbers of the 100k thermistor then the result of the formula could be less accurate. I prefer a "ntc" tag, or is "thermistor" more common ?

pots tend to have more thermal drift than carbon-film or wire-wound resistors. for basic hobby-level measurements, the specific resistance doesn't matter much. if you're integrating it with an LM334 for long-run sensing, one range might offer better integration than another.

Wish I knew which answer is proper to mark...

Skip to the end to get the easy answer!
Your choice of thermistor and bias resistor values depends on the following:
1.  How much current do you want to spend?
2.  How do you want the thermistor resistance to compare with the wiring resistance?
3.  How much filtering do you need?
4.  What kind of linearization do you want to apply?

A lower value thermistor will pull more current than a higher value one.  More current means less battery life but also affects (2) and (3) below.
For a given system wiring resistance, increasing the thermistor resistance reduces the measurement error due to the wiring. If your thermistor is 100 ohms (25C nominal) and your wiring is 1 ohm, then you would have a 1% error at 25C.  For an NTC (Negative Temperature Coefficient) thermistor, as it gets hotter and it resistance decreases, the wiring error  increases because the wiring represents a greater percentage of the total resistance.
Filtering a resistive sensor in front of an ADC can be done by simply putting a capacitor across the ADC input.  As your sensor resistance increases, the size of the capacitor required decreases for the same cutoff frequency.  Even if filtering is not needed, be sure to check the ADC input impedance requirement as sample and hold circuits need their minimum AC input impedances to be satisfied as well as the DC input currents:  Too much sensor impedance does not go well with too high ADC input current.
Unless you are using a platinum RTD with its linear response curve, your thermistor resistance vs temperature curve is going to be logarithmic where each end of the curve will be asymptotic.   This means you will get good resolution around the 25C reference temperature but at one end you'll get very little resistance change for a large change in temperature and at the other end you'll get a lot of resistance change for very little change in temperature.  By putting a resistor in parallel with the thermistor you can flatten out the curve to fit your measurement needs.

All this being said, your best bet is to put the thermistor curve into a spreadsheet and adjust the values until you get current consumption you can live with with a curve that gives you the information you need.  See this example for a 10K NTC sensor with linearization (Either the RT/R25 or RT-vs-Temp values are almost always listed in the data sheet for each thermistor):  Spreadsheet for this graph

I don't see the point of your linearization resistor: it can only lower your resolution and increase the current consumption. Per Thévenin's theorem, your circuit is equivalent to having the thermistor connected to a single pullup of resistance Rbias∥Rlinear pulling towards Vbias×Rlinear÷(Rbias+Rlinear). In other words you are only wasting part of your ADC range.

I see no pros to using a lower resistance thermistor in your answer; why might they even exist? Why ever use something like a 10 ohm (if it exists) vs. 100k or higher?

The spreadsheet link is not accessible anymore

The standard way to measure a resistive sensor is to make a voltage
divider with the sensor and a fixed resistance between Vcc and GND, like
this:
Vcc
 │
 Rb
 │
 ├─── analog input
 │
 Rx
 │
GND

where Rx is the resistance you want to measure and
Rb is a known bias resistance. The only unknown is the choice
of the bias resistance.
The simple rule of thumb is to choose a bias resistance close to the
typical values of the resistance you want to measure, as this will
optimize your measurement resolution. More specifically, the relative
measurement resolution, which could be stated as the number of ADC steps
you get per percent change in resistance, is maximal when Rx
= Rb, and decreases only slowly as Rx gets
further from Rb.
Now, one could argue that the relative resistance resolution is not
always the best performance metric. You may want to maximize the
absolute resistance resolution instead, or maybe the absolute
conductance resolution. Each of these choices would lead to a different
choice of bias resistor. For the case of a thermistor, however, the
choice is pretty clear: the resistance varies almost exponentially with
temperature, which means that the absolute temperature variations are
practically proportional to the relative resistance variations. If you
want to use temperature resolution as a metric, you could go through a
tedious calculation only to find out that the optimal Rb is
darn close to Rx.
In short, if your thermistor is 1 kΩ at 25 °C, and you will
use it near 25 °C, then a 1 kΩ pullup will give you the best
temperature resolution.
Now, measurement resolution may not be the only issue you care about,
and you may want to sacrifice some of it in order to improve something
else. For example:

Current consumption: a 1 kΩ thermistor in series with a 1 kΩ
pullup will draw 2.5 mA (assuming Vcc = 5 V), which
could rise to near 5 mA if it gets really hot. If you are running
off battery power this could be an issue.
Self heating: in that 1 kΩ + 1 kΩ configuration, the
thermistor will dissipate 6.25 mW. I've seen the datasheet of a
typical thermistor stating a thermal dissipation constant of
7 mW/K. This means the measurement current would heat the
thermistor to 0.9 °C above ambient temperature, which you would
need to take into account in your temperature calculations.

Both of these issues would be mitigated by using a larger value for
Rb, only at the cost of measurement resolution. Switching to
a 10 kΩ thermistor would mitigate these issues without sacrificing
resolution.

Related:

Selecting bias resistor for thermistor
Choosing the correct thermistor

I was trying to figure this out myself and was going to ask a question to verify my results. Since this question is so close, I'll just post my results as an answer and comments/votes can help me figure out if it's correct!
I've been going by this tutorial on Adafruit which, unfortunately, doesn't talk about why they use a 10k Ohm thermistor paired with a matching fixed/bias resistor.
So we're on the same page, here's the circuit used (voltage divider, pic taken from the second related answer above):

The formula used to get from resistance to temperature (taken from the Adafruit guide, which uses the Steinhart-Hart equation):

Here's the full code used to find the temperature based on the voltage divider created by the fixed/bias resistor and the thermistor:
int pin_therm = A0;    // analog read pin
float reading;         // hold thermistor resistance
float stein;           // hold calculated temp

int res_fixed = 10000; // 10k fixed resistor
int res_therm = 10000; // 10k thermistor
int therm_nom = 25;    // nominal thermistor temp
int therm_b = 3950;    // thermistor B coefficient

reading = analogRead(pin_therm);
reading = (1023 / reading) - 1;
reading = res_fixed / reading;

// apply the S-H equation
stein = reading / res_therm;    // (R/Ro)
stein = log(stein);             // ln(R/Ro)
stein /= therm_b;               // 1/B * ln(R/Ro)
stein += 1.0 / (25.0 + 273.15); // + (1/To)
stein = 1.0 / stein;            // Invert
stein -= 273.15;                // convert to C

My aim is to measure around 150-250C, and I was curious what my resolution was after seeing very specific, "steppy" values when watching serial output. For example, as temps rose I'd see values like 202, 211, 222 but nothing in between.
I used R to send all possible ADC values of 0-1023 through the equation to find the corresponding calculated temperature.
In my case, I modified the code above for the Honeywell 135-104LAG-J01 thermistor I was using (T = 25C, B = 3974). Using the rule of thumb to match the fixed resistor, here's what I get with 100k Ohms, showing ADC values for 150-250C. It revealed that this setup would only give me ~5 readings over 200-250C!

Going back to the math, it looked like I could drop the fixed resistance for better resolution. Here is the same 100k thermistor, but comparing the resolution obtained with 22k, 47k and 100k fixed resistors:

Using a lower fixed resistor, I have substantially more data points in my range of interest! We can simply compare the ADC ranges that make up this 150-250C span: ~20 for 100k and ~80 for 22k.
I'm not really worried about current consumption, but since it came up in the other answers, we can also increase the thermistor nominal resistance. Here's a plot breaking down by thermistor (100k - 1M) and matching fixed resistor (same 22k-100k values). I've removed the dots to make it less busy and the gray "mini-plot" titles are the thermistor values I looked at:

Lastly, to spare you from having to calculate the min vs. max ADC ranges covering the desired 150-250C range, here's a simple bar plot showing how many steps we get in this range.

So, with a 1M Ohm thermistor and 22k fixed resistor, we could have ~0.5C resolution in this high range (100C span divided by ~200 ADC steps).

I echo the suggestion of John Taylor to plot things out, but in my case, the datasheet didn't list the key values required for his spreadsheet. I think spelling out the Adafruit code and putting my R code at the end can help understand how to do this (approximated) in order to compare temperatures of interest vs. ADC steps which cover it.

As a last aside, I ran into the mention of "source impedance" on one of the related questions. I'm not an electrical engineer, but some answers suggest that there may be a time delay issue with reading ADC values when the circuit resistance is very high:

Required output impedance for ADC input?
Input impedance of Arduino Uno analog pins?

That said, since I'm measuring high on the temp scale, an NTC thermistor will have less than max resistance. We're also helped by the fact that the equivalent resistance is:
1/((1/R_fixed) + (1/R_therm))
So, even with a 1M thermistor an 100k fixed, our equivalent resistance at room temperature is:
1/((1/1000000) + (1/100000)) = ~91k
This will only reduce further at higher temps, but I thought I'd mention it for the sake of thoroughness!

Here's the R code used to generate the multi plot covering 100k-1M thermistors vs. 22k-100k fixed resistors:
## for plotting
library(ggplot2)

## R kept wanting scientific notation, e.g. 10e5
options(scipen=10)

## range for ADC reading
inputs <- 0:1023

## create all combos of fixed resistor, thermistor, and ADC values
combos <- expand.grid(res = c(22000, 47000, 100000),
                      therm = c(100000, 250000, 500000, 1000000),
                      adc = 0:1023)

## make sure it's sorted the right way
## also, give it a unique identifier per combo
combos <- combos[order(combos$therm, combos$res, combos$adc), ]
combos$grp <- paste0(combos$res, "_", combos$therm)

## calculate the temps for each thermistor/fixed res combo
dat_lst <- lapply(unique(combos$grp), function(grp) {

  temp <- combos[combos$grp == grp, ]
  res <- unique(temp$res) / ((1023 / inputs) - 1)
  stein <- res / unique(temp$therm);
  stein <- log(stein);
  stein <- stein / 3974.0;
  stein <- stein + (1.0 / (25.0 + 273.15));
  stein <- 1.0 / stein;
  stein <- stein - 273.15;

  temp$temp <- stein

  return(temp)

})

## combine results
data <- do.call(rbind, dat_lst)

## some factor re-labeling to make plots more readable
data$res <- factor(data$res,
                   levels = c(22000, 47000, 100000),
                   labels = c("22k", "47k", "100k"))
data$therm <- factor(data$therm,
                     levels = c(100000, 250000, 500000, 1000000),
                     labels = c("100k", "250k", "500k", "1M"))

## reduce to only values in our range of interest
data <- data[data$temp > 150 & data$temp < 250, ]

## the plot itself
p <- ggplot(data, aes(x = adc, y = temp, colour = as.factor(res),
            group = grp)) + geom_line()
p <- p + scale_x_continuous("adc value")
p <- p + scale_y_continuous("calculated temp, C")
p <- p + facet_grid(therm ~ .) + theme_bw()
p <- p + scale_colour_discrete("fixed resistor")
p

## to save it out
png("./therm-vs-fixed.png", res = 200, width = 1600, height = 900)
p
dev.off()

You would have reached the same conclusion much faster by applying the rule of thumb I posted in my answer: choose a fixed resistor close to the value of the resistance you want to measure. Example: Your 1 MΩ thermistor, in the middle of the relevant temperature range (200°C) has a resistance of 7.23 kΩ. You would then pair it with a fixed 6.8 kΩ resistor (the closest E6 series). Likewise, the 500 kΩ thermistor would be paired with 3.3 kΩ. All the fixed resistors you choose for your plots are way too high. You did exactly the kind of mistake that rule of thumb helps to avoid.

@EdgarBonet this answer was as much for me to process though why that rule of thumb makes sense as to add to this discussion. Maybe it will help someone to see the data vs. just taking it on faith. People think in different ways, and different answers can help things "click." Your answer is right on; I hope this supplements it as folks wander through.

Your idea of illustrating the concepts graphically is great. It does help many people, including myself, get the things. The problem is with your poor choice of data. Since all your fixed resistances are too high, your curves show a consistent trend: the lower the fixed resistance, the better. And that would be a very wrong conclusion to draw. Had you better chosen your fixed resistors, not only would you have revealed the optimum, but you could also asses how well the rule of thumb performs at getting you close to that optimum. Then you would have posted a great answer.

@EdgarBonet Gotcha. So if my example range of 150-250C is some range R1-R2, show what the curves look like for Rb < R1 and Rb > R2? Keep in mind I did most of this before finding this answer. Honestly, most people will google "how to read a thermistor," find people throwing out a 10k thermistor and 10k fixed resistor (or just saying "match them") and never find their way here. My plots look like they do because I was starting with what exists in tutorials and I slowly started testing the waters from there...

authors: Иван Янушкевич


text:
Is it wrong power supply?
I used this cheap impulse power supply, and it worked on Arduino with prototype board for some short time, but then it stopped while I felt a burning smell. Is "impulse" a wrong type of power supply for Arduino board?

On that board I had 0,96" OLED display (0,08W) connected, 3 LED's, 2 thermistors, 1 buzzer. All is working fine while powered by USB cable from laptop.

that PSU should be fine, you might have mis-wired something.

A DC power supply with the right voltage is okay, also that one. You did connect it to the barrel jack ?
The most likely reason is that your Arduino board draws too much current for the voltage regulator on the Arduino board. Suppose you have an Arduino Uno with a servo motor or a lot of leds and they require 500mA. The voltage regulator would heat up with (9V-5V)*500mA = 2 Watt.
Can you find the voltage regulator on the Arduino board ? You can check if it is getting to hot by holding your finger on the voltage regulator. If you can keep your finger on it, then it is okay.
The voltage regulator should reduce the current too prevent that it gets too hot, but it is not hard to blow the voltage regulator despite that.
The DC power supply could be bad quality and could have an output voltage that is too high or has voltage peaks, or there is a leakage current from the mains. Do you have another power supply ?
I use a good quality and certified DC power supply of 7.5V. In the photo I see all the right certification labels, but I don't know if they are real.
What was connected to your Arduino board ? If nothing was connected, then you are in trouble, and it could be faulty DC power supply or a bad Arduino board.

Voltage regulator got hot indeed at that moment. It is Arduino Uno (non-genuine), and its working until now on USB power supply.

authors: Артур Таказов


text:
Is setting clock divider worth changing on delay() to save power?
Along all the "advanced" methods described in this article, does simple method as downscaling processor while delay makes a difference on power consumption? How much time does the clock alternation takes itself?
Is below example valid?
#include <avr/power.h>

void setup() {}

void loop {

    /*
       here some jobs to do...
    */

    clock_prescale_set(clock_div_256); // downscale clock
    delay(200); // wait
    clock_prescale_set(clock_div_1); // restore clock
}

i don't think that will accomplish anything; it's not like there are background threads...

It's not running background threads, no, but the delay function doesn't just 'pause'. It runs a loop waiting for the time to pass. If you scale down the clock the cpu will process slower and use less power. I'm not super familiar with the clock prescaler, so perhaps someone could verify, but a delay(200) with a div 265 prescale would actually take just over 51 seconds, i think. ?

@Mazaryk: if that's the case, power-saving mode would be better right? I just don't see shaving empty cycles as a big savings, but i could be wrong; most of my experience is with ESP8266s...

@dandavis: I'm not sure, but I would think sleeping would yield better power savings but that's just a guess. Best way to know for sure would be to test and measure it.

@dandavis setting the clock divider is major power-saver, see the article i linked (esp. reply #7 http://www.gammon.com.au/forum/?id=11497&reply=7#reply7)

@madneon: interesting. i think sleeping still shaves more, but that's nice and simple whilst still pretty good for not screwing around with watchdogs and brownouts or suspending IOs like spi and serial. With the right setup, you can get a 3.3v one all the way down to ~5µA. but not as easily for sure. thanks for sharing!

Reducing the CPU frequency should work, but I would expect better
savings by sleeping during the busy loop:
#include <avr/sleep.h>

void sleepy_delay(uint32_t duration)
{
    uint32_t start = millis();
    while (millis() - start < duration) {
        sleep_mode();
    }
}

Note that the sleep will be interrupted at least on every Timer 0
overflow interrupt, which happens every 1024 µs (that's what
increments the value returned by millis()), so there is no risk of
oversleeping. You could add some power_*_disable() calls for better
savings.

1024 µs "wakeup" thats 1 ms, so your loop will execute every milisecond assuming that it takes less then 1 ms to execute millis() with 2 operations (substract, compare+jump), right? So does this method actually saves power, aka is Arduino that fast? ;)

@madneon: millis() is fast, and subtract+compare+jump is only a few CPU cycles. With this loop the Arduino will be awake only a tiny fraction of the time, mostly executing the Timer 0 overflow ISR.


text:
Cutting off OneWire/SDA line with transistors
I am developing a pcb for a design I am working on and I need to share a pin to be used by a ds18b20 (onewire) and some possible I2C sensors. There would be just one of each at a time.
I was thinking about using a couple of transistors. One would cut or enable ds18b20 data line and the other one, the same for SDA line. So I would enable the first one and disable the second one or viceversa.
Do you think this is possible? I don't have transistors right now to test it. I have to order some of them. I was thinking about a bd228. Would this add some errors/delays/whatever in signal information? A kind of distorsion I mean. Or should it work?
EDIT: I will try to explain a bit my project.
My idea is to have a box with 5 sockets. Each one of them will be a different data input. They should be able to use a wide variety of sensors, ds18b20, dht22, open/close door (1 or 0 signal)... Also I would want to include some I2C sensors.
I was thinking about BME280 for example.
My idea is that the user could set which sensor is connected each time so the arduino can switch transistor behaviour to allow the connectivity to the digital pin or the I2C SDA (or SCL) pin.
I was thinking about using an I2C multiplexer to allow multiple BME280 to be at the same time so the first line would go to the socket1, second line socket 2...

You could use a I2C-to-1-Wire bridge. The DS2483 solves the problem; https://datasheets.maximintegrated.com/en/ds/DS2482-100.pdf. An example driver may be found in Cosa; https://github.com/mikaelpatel/Cosa/blob/master/libraries/DS2482/DS2482.hh. The example sketch shows how to talk to a DS18B20; https://github.com/mikaelpatel/Cosa/blob/master/libraries/DS2482/examples/CosaDS2482/CosaDS2482.ino

Thank you. At the end I removed that part from my pcb but I will keep in favorites your links, they could be useful in future when we have to do some rework on the pcb.

For multiple I2C busses, it is allowed to share a single SCL and have a separate SDA line for each I2C bus. That means that as long as the SDA is inactive (high), you can do with the SCL whatever you want.
It might even be possible to share the SCL signal for I2C and 1-Wire, and use both. The SCL signal would then also be the 1-Wire signal. The I2C pulses are probably shorter than the start pulse of the 1-Wire. You would also have to do it right in the software to switch the function of the pins. As far as I know that has never been done, so you might get into a lot of trouble.
Transistors are not the right choice to multiplex signals, and the BD228 is definitely not okay. The I2C bus is a open-collector or open-drain bus with a current of maximum 3mA. The 1-Wire bus is roughly the same. It is possible with mosfets or with multiplexers (see: Nick Gammon about multiplexers). However, if you are going to add extra hardware there are probably better solution than combining I2C with 1-Wire.
Have you thought about the voltage levels ? Are you using a 5V Arduino board ? Most sensors are 3.3V. The DS18B20 will work with voltages as low as 3.0V, so 3.3V is no problem for the DS18B20.
Tell us what else is connected to your Arduino board. I'm sure there are better solutions.
Could you better specifiy what it is that you want to achieve ? When there is only I2C sensors or only 1-Wire sensors connected, you could run a i2c-scanner to check for I2C sensors. If nothing is found, do a Wire.end() and start the OneWire using the SCL pin. That could be done during startup and then you don't need extra hardware.
How long are the wires ? The 1-Wire bus can have long wires, but the I2C bus can only have short wires.

I added an explanation about what I want to get

The Arduino is for fast prototyping. With an Arduino board and a small breadboard, all the sensors that you mentioned can be used. However, 5 universal ports that can do everything might be too much. I'm not sure if you can make that work. With Software I2C it is possible to create multiple I2C busses, and the same two pins can also be set as 1-Wire bus or for the DHT22 signal. It might be possible if you are a software wizard.
The most practical solution is to use only a BME280.
There is still the problem with voltage levels, and I don't know if you want to change sensors runtime.


text:
Can't move servo with my Nano
I'm new to this kind of thing. My code works on my Uno without problem with two separate servos. I've ensured that it's not any faulty leads, having tried a few other circuits with LEDs, buttons and potentiometers as well, simply switching between my Uno (which works fine) and the Nano.
I've chosen the correct port, chipset and board each time and the code uploads fine to the Nano. The Nano simply refuses to do anything I tell it.

Digital PIN of servo goes to designated D5 pin.
Ground goes to the GND near the Analog pins (shouldn't matter which I imagine).
Power goes to 5V.

The code above simply tells the servo to go to a certain degree when uploaded. Could anybody tell me why the servo will not move at all with the Nano? I just bought it and I haven't hooked up any power to it other than the USB, surely it isn't fried. It lights up and flashes as well.
#include <Servo.h>
Servo my_servo;

void setup() {
  my_servo.attach(5);
  // Pin definition
}

void loop() {
  my_servo.write(60);
  // No. of degrees
}

does the servo get enough power?

I know that the servo works fine through only the USB using the same schematic with the Uno. Do you think maybe the Nano could be providing less power through the USB to the 5V pin?

@ratchetfreak I checked the voltage (using a multimeter) going from the GND and 5V to the servo and I got 4.58V for the Nano and 5.06V for the Uno. Could that make that difference? The servos I'm using are rated at 4.8V +

If you're starving the servo of power then the internal controller may not function.

@Majenko perhaps I should figure out how to drop a 9V battery to 5v and power the Nano?

Or power the servo separately from the Nano.

@Majenko From the Uno, I've tried running 5V from a switchable (5V) power supply straight to the servo GND/Power and it doesn't move. If I take the GND/Power back to the Uno it works fine. What could I be doing wrong?

I bet you removed the ground from the Arduino when you added the external power supply, didn't you?

https://hackingmajenkoblog.wordpress.com/2016/12/06/the-importance-of-sharing-grounds/

@Majenko That was an error I made. However.. this is what I did now and the Nano still doesn't work. GND/Power from Servo to the supply GND/Power - then from the GND of those I took one lead to the Uno's GND and it worked fine. But if I switch it over to the Nano it doesn't move. Odd.

Connect a multi meter in series with the servo connection from the uno to the servo and see how much current it draws when working (probably less than 20ma, definitely less than 40ma). Then connect it in series with the nano and see what happens. If you get no current then you're activating the wrong pin.
If you see a current draw but the servo doesn't move then you need to use some sort of switch (transistor, FET, relay) to switch the servo. You could also compare the voltage and current read off the nano to the requirement in the datasheet for the servo. Again, this may lead you to needing a switch.
Edit based on comments above... Also try your 5v directly to the servo, then add a forward biased diode in series which should simulate the voltage drop to the level of your nano (0.4-0.6v). If the servo doesn't work with the diode and does without then you can be pretty sure the issue is insufficient volts (which is likely given the rating of 4.8v you mentioned in comments).

i will try this when I'm home. You also may be right, what if I'm activating the wrong pin...Could it be that the PWM of the Uno (I've used D9/10) are different to the Nano?

Your code says d5. Regardless it's possible and I'd check that it flips from 0 to 5v and that current is drawn by solenoid.

I has the same problem. Example: With Arduino Uno only conected to 5V from PC, the servos run perfectly, but with Nano no, maybe the servos try to move, but not. I charged the skecth on the arduino Nano and deesconect form pc, and then i supply Arduino Nano with baterry Li-ion 2s. In another words, for servos you must to supply over 6 volts. Be careful because the max voltage of servos,can be 6 volts, you can use the regulator of Arduino, severals servos produce overheating in this regulator. Yes my english is noob.


text:
Passing serial data to Processing using something other than ln to trigger Processing
I have a Uno program and I can transfer data to Processing using println. In Processing bufferUntil('\n') interprets the ln  as \n, stops buffering, and reads the string until the next '\n'. I would like to use something other than ln to trigger Processing. That way I can use Serial Monitor in the Uno to see serial data when Processing is not running at the same time.
I have searched the net but have not found the technique to use something other than ln. Thanks.

ln? You mean \n aka new line character?

Sounds like you want 2 programs monitoring the same serial port on the PC. What OS are you using? The question is not very clear.

If I understand your question (which is not certain):

Pick a different "trigger" byte that you won't be sending in your messages.  Maybe TAB?
In your "Processing" program, use: port.bufferUntil(TRIGGER);
In your Arduino sketch, rather than println, use print to send both your data and the trigger byte:  Serial.print(your_message); Serial.print(TRIGGER);

Note that sending binary data will cause this to fail when the data uses the trigger byte.
From: https://www.arduino.cc/en/Serial/Println The println()
   method sends your output then a CR and NL.  And it seems bufferUntil() takes a character on which to trigger:
https://processing.org/reference/libraries/serial/Serial_bufferUntil_.html


text:
Making a 7-hour timer-based relay
I want to make a very small 7-hour timer circuit that can turn on a relay after 7 hours. I am trying to make the first prototype with an Arduino Nano but I can't understand how to program it for such purpose. So please help me out.
Once I make a prototype in Arduino then I was thinking to make a small one  using an ATtiny13. Can I use an ATtiny13 for such purpose?

Never seen an Arduino core for the tiny13. You may have to program it at the avr-libc level.

You could try a timer with millis. 7 hours is (7L * 60L * 60L * 1000L) milliseconds. The ATtiny13 has an internal oscillator for the CPU clock, the 7 hours will not be accurate. I have ATtiny13 chips and I have seen the Arduino core for it, but I never tried it: https://github.com/MCUdude/MicroCore

I have investigated the MicroCore code and compared it with my project for ATtiny13 (I did not actually compile a similar project). The overhead is not too bad, and it makes fast prototyping possible because it is pretty Arduino compatible. The millis function is very inaccurate though, because that uses the watchdog timer. For normal basic use of the ATtiny13 I would recommend the MicroCore. I think the MicroCore is well made, I like it a lot (@EdgarBonet).

Could you please tell in your question: 1) what event will start the timer? 2) will the tiny13 have something to do during these 7 days other than count time? 3) what accuracy do you need (7 days ± how much)? 4) what clock source do you plan to use on the tiny13?

The question is whether its a one shot triggering ON the relay after 7 hours and thereafter you always leave it ON or its some periodic process where every 7 hours, you want the relay to trigger ON and OFF alternatively. Presuming the latter, this can be done in 2 ways:
1) Configure a hardware timer interrupt to call a small function every second and increment a variable within that function. So after 1 hour your variables value must be 3600, therefore after 7 hours it will be 25,200. Once the variable is equal to 25200, you can ON the relay and reset the variable to 0. Factors such as the number of hardware timers and its resolution differs from one MCU to another.
2) Use a Real Time Clock like the DS1307 for this purpose and save you hardware timers for performing some other time critical operations.
Hope this helps!.

You wrote: “Configure a hardware timer(32 or 16 bit)”: there is no such thing in the ATtiny13.

@EdgarBonet, I am not aware if ATiny13 has any inbuilt hardware timers as I haven't used it. However, until today whichever MCU's I have used had at least one hardware timer. For example, the esp8266ex has one 32 bit hardware timer, similarly the TICC3200 has four 32 bit hardware timers.

Just did a Google search and found a few examples as well where they are flashing an LED using the timer interrupts. And between, just got to know its an 8 bit controller, hence edited my answer.

cant understand how to program it for such purpose so please help me out

it is fairly easy to approach such questions:
1) you can program any?
2) can you program this mcu to blink an led?
3) can you program this mcu to do short time counting?
4) can you program this mcu to do long time counting?
what you help helps you the most depends on your  answers to those questions.


text:
Upload original firmware to HID Arduino
I recently was playing around with Arduino and using dfu-programmer reflashed ATMega16u2 to make the computer think it was a keyboard device.
Well, I wish to put the original Arduino firmware back on, but now dfu-programmer says the device is not present.
The Arduino is listed under /dev/hidraw5 on Ubuntu. Typing lsusb gives the following output for Arduino keyboard:
Bus 004 Device 008: ID 03eb:2042 Atmel Corp. LUFA Keyboard Demo Application

I tried erasing with the command:
sudo dfu-programmer atmega16u2:4,8 erase

and got
dfu-programmer: no device present.

Is there a way to target /dev/hidraw5 using dfu-programmer? Many thanks.

Very sorry!  But I actually figured this out on my own.  I needed to reset by briefly bridging the reset pin with ground near the USB connector.  Then typed
sudo dfu-programmer atmega16u2 erase

and I'm happy again.


text:
Creating a file in an SD card
I have an Arduino Mega connected to an SD card reader (Catalex branded), that at least detects the card as it displays the info of the card. But when I try to create a file, it does not create it. I am using the following code:
if (SD.exists("data.txt")) {
  Serial.println("data.txt exists.");
} else {
  Serial.println("data.txt doesn't exist.");
}
File root=SD.open("data.txt", FILE_WRITE); //open of the File for writting
if (SD.exists("data.txt")) {
  Serial.println("data.txt exists.");
} else {
  Serial.println("data.txt doesn't exist.");
}

I also tried with this code:
File root2 = SD.open("file.txt", O_RDWR | O_APPEND);
    if (!root2) {
       // It failed, so try and make a new file.
        root2 = SD.open("file.txt", O_RDWR | O_CREAT);
        if (!root2) {
          // It failed too, so give up.
        Serial.println("Failed to open file.txt");
         }
    }

[Update]
I also tried with this easier code and it does not work either:
#include <SD.h>

const int chipSelect = 10;
Sd2Card card;

void setup() {
  Serial.begin(115200);
  while (!Serial) {
    ; // wait for serial port to connect. Needed for native USB port only
  }
  Serial.print("Initializing SD card...");
  // see if the card is present and can be initialized:
  if (!SD.begin(chipSelect)) {
    Serial.println("Card failed, or not present");
    // don't do anything more:
    return;
  }
  Serial.println("card initialized.");
}

void loop() {
  File myFile = SD.open("Data.txt", FILE_WRITE);
  if (myFile) {
    for (int i = 0; i < 101; i++) {
      myFile.print(i);
      myFile.print(" multiplied by two is ");
      myFile.println(i * 2, DEC);
    }
    Serial.println("Finished");
    myFile.close();
  } else {
    Serial.println("Error opening Data.txt");
  }
  //do nothing else
  do { } while(1);
}

I don't think it should matter, but can you try to close the file after opening and before the exists call?

@MichelKeijzers Yes i tried it and it neither work

You can try to format the card in a different format (I don't know which formats are supported by the library), also you can check if the file really is created (on a PC) or that the exists fails.

@MichelKeijzers i do not why i open a new code file and copy the code and it worked. thanks for the help

Glad you can continue now

// open a new file and immediately close it:

Serial.println("Creating example.txt...");
myFile = SD.open("example.txt", FILE_WRITE);
myFile.close();

This is what you missed (I guess..).
Please see the link and check the steps followed:
https://www.arduino.cc/en/Tutorial/Files

If you want to make it sure it will not have problem with SD card format then format it to FAT it's most compatible format type.


text:
error: invalid use of non-static member function attachInterrupt(0,count,RISING);
XRPM_COUNTERS.h:15:5: error: expected unqualified-id before string constant

     ISR(PCINT0_vect) {

     ^

In file included from C:\Documents and Settings\SAM\Desktop\automation_1_A_NEW_AAA\automation_1_A_NEW_AAA.ino:10:0:

XRPM_COUNTERS.h:72:1: error: expected ';' after class definition

 }

 ^

sketch\XRPM_COUNTERS.h: In function 'void XRPMLoop()':

XRPM_COUNTERS.h:77:19: error: 't' was not declared in this scope

   if ((millis() - t) > 300) rpm = 0;

                   ^

XRPM_COUNTERS.h:77:29: error: 'rpm' was not declared in this scope

   if ((millis() - t) > 300) rpm = 0;

                             ^

XRPM_COUNTERS.h:79:17: error: 'ot' was not declared in this scope

   else if (t != ot) {

                 ^

XRPM_COUNTERS.h:81:5: error: 'rpm' was not declared in this scope

     rpm = 60000.0 / (float)(t - ot);

     ^

XRPM_COUNTERS.h:87:13: error: 'rpm' was not declared in this scope

   lcd.print(rpm);

             ^

XRPM_COUNTERS.h:93:14: error: 'printVu' was not declared in this scope

   printVu(rpm);

              ^

sketch\XRPM_COUNTERS.h: At global scope:

XRPM_COUNTERS.h:97:1: error: expected declaration before '}' token

 };

 ^

exit status 1
expected unqualified-id before string constant

My source code
class XRPM_COUNTERS {

  private:
#include <Wire.h>  // Comes with Arduino IDE
#define interrupt_pin2 A8 //Define Analog Pin (analog pins are 16-21)

    volatile unsigned long t = 0;

    volatile unsigned long ot = 0;

    ISR(PCINT0_vect) {

      if (PINB & 1) {

        ot = t;

        t = millis();

      }

    }

    //actualizar o visor (aqui calibrado para um maximo de 3000 rpm, basta mudar o valor)

#define max_rpm 3000

    void printVu(int r) {

      int i = map(r, 0, max_rpm, 0, 20);

      for (int n = 0; n < 20; n++) {

        lcd.print((char)(n < i ? 255 : ' '));

      }

    }

  public:

    void XRPMSetup() {
      lcd.begin(16, 2);  // initialize the lcd for 20 chars 4 lines, turn on backlight

      lcd.print("RPM with PCINT");

      MCUCR = (1 << ISC01) | (1 << ISC00);

      PCICR |= (1 << PCIE0);

      PCMSK0 |= (1 << PCINT0);

      pinMode(interrupt_pin2, INPUT); //Make pin an input

      digitalWrite(interrupt_pin2, HIGH); //Enable pullup resistor on Analog Pin

      interrupts();

    }

    unsigned int rpm = 0;

}
void XRPMLoop() {

  //lcd.setCursor(0,3);lcd.print(millis()-t);lcd.print("     ");

  if ((millis() - t) > 300) rpm = 0;

  else if (t != ot) {

    rpm = 60000.0 / (float)(t - ot);

  }

  lcd.setCursor(0, 1);

  lcd.print(rpm);

  lcd.print(" rpms    ");

  lcd.setCursor(0, 2);

  printVu(rpm);

}

};
XRPM_COUNTERS XRPM;

Format your question so that people can see where error messages end and code begins.

Possible duplicate of expected unqualified-id before string constant

You placed an #include directive inside a class definition. Don't place #include directives inside class definitions. (Unless you are including a file specifically designed for that purpose.)
#include directives for regular header files should normally reside somewhere at the top of your file, separately from any other declarations.


text:
"variable does not name a type
Hey guys I'm getting an error that is im pretty sure to do with how i am initializing my variables. It is:
exit status 1
'threshold' does not name a type
Here's my code:
//Global Variables for moving max:

int analogValues[100];
int ir=0;
int maxA0=0;
int threshold = 0;
//Global variables for moving max ^^

//Global Variables for moving average ECG:
const int no_averages = 2;

unsigned long time = 0, peak1 = 0, peak2 = 0;
int binaryrange, bpm, i=0; //not sure what i does tbh
int readings[no_averages]; // the readings from the analog input
int readIndex = 0; // the index of the current reading
int total = 0; // the running total
int average = 0; // the average which we will display as ECG

void setup() {
// initialize serial communication with computer:
Serial.begin(115200);
// initialize all the readings to 0:
for (int thisReading = 0; thisReading < no_averages; thisReading++) {
readings[thisReading] = 0;
}

//set moving max shit to zero
  for (int is = 0; is < 100; is++) {
analogValues[is]=0;
  }
}

void loop() {
  //int maxA0=0; //Whether I intitate the variables here or globally, same error
  //int threshold = 0;
time = millis();

average=0;
readings[readIndex] = analogRead(A0);
readIndex++;
for (int ir=0; ir < no_averages; ir++) {
  average = average + readings[ir];
}
if (readIndex >= no_averages) {    // ...wrap around to the beginning of array if it has hit the end:
readIndex = 0;
}
average = average/no_averages;
if (average>1000) {
  average = 600;
}
Serial.print(average);

analogValues[ir]=average;
ir++;
if (ir>=100) {
  ir=0; } //This is to roll back to the start of the array if it surpasses the 100th array spot
for (int is = 0; is < 100; is++) {
 if (analogValues[is]>analogValues[is-1])
 analogValues[is]=maxA0;
  }
}

//**************************

//This line with error:

threshold=maxA0-40;

//**************************

if (average<threshold){
  binaryrange=0; }
if (average>threshold && binaryrange==0){
  peak1=peak2;
  peak2=time;
  bpm=60000/(peak2-peak1);
  binaryrange=1;
  }
   Serial.print(" ");
  Serial.println(bpm);
//BPM code ^^

delay(8); // delay in between reads for stability
i++;
}

THANKS!

"The line with the error" falls outside of any functions. In C and C++ we write executable code inside functions. You placed your
threshold=maxA0-40;

(and everything that follows) outside of any functions. Hence the error.
Errors like this are typically cased by improper placement of { and } braces. But this is something you have learn to check for yourself. Most C or C++ oriented code editors can usually help you with this. And proper code formatting can help you with this too. What you have now is such a mess, that a simple error is virtually impossible to see.

Ah man that is embarrasing, just had a rogue "}" in there that ruined my code. Thanks!

@glebecreator That's why is coding style and indentation so important. And even if you can't follow it, you can use Ctrl+T keystroke in Arduino IDE to reformat your code. If you try it, you'll spot part of code somehow misaligned.


text:
Hex to binary, LED blinking
I need to write a program that takes a user inputted HEX value and converts it to binary, then an LED blinks according to the number of 1's in the binary. For instance, if the value is 0xABC then there are number of 1's are 7 so LED will blink 7 times.
I only just started Arduino so not sure how to let user input a value nor do I know how to convert HEX to BIN but I'm assuming that once I convert the HEX to BIN I can just use a loop to count the number of 1's yet I'm unsure as to actually how to do that. This is what I've written so far.
  byte val=0xABC;
int ledPin=13;

int countSetBits(unsigned int n)
{
    unsigned int c;
    for (c=0;n>0;n=n&(n-1))
        c++;
    return c;
}

void blink(int n)
{
    for (int i = 0; i < n; i++)
    {
        digitalWrite(ledPin,HIGH);
        delay(500);
        digitalWrite(ledPin, LOW);
        delay(500);
    }
}

void setup()
{
    Serial.begin(9600);
    pinMode(ledPin,OUTPUT);
    blink(countSetBits(val));
}

void loop()
{   }

Any help would be appreciated.
EDIT: If I want to take a number from a user and then make the LED blink according to the number of 1's in its binary form, how would I implement that?

byte val=0xABC; that's not going to fit in a byte. Use an int instead (int val=0xABC;)

You are almost there. Now you just have to read and parse the hex
numbers supplied by the user.
The simplest way to accept numeric user input is with
Serial.parseInt(). This is not always ideal since it involves blocking
the program until it either receives an invalid character or the reading
times out. It is also not applicable to your situation because it only
works with decimal numbers.
The better standard way to get the input is to put the incoming bytes
into a buffer until you catch a specific character designated as an end
of message marker. This is typically a CR ('\r' in C++) or an LF
('\n'). This technique is more involved than just calling parseInt()
but it is often preferred because it can be done in a non-blocking way.
See for example this simple command line interpreter.
In your case, however, you do not need to buffer the incoming bytes. You
can instead parse the hex number while you read it, like this:
void loop()
{
    if (Serial.available()) {
        static unsigned int val;
        int c = Serial.read();
        if (c >= '0' && c <= '9') {
            val = 16 * val + (c - '0');
        } else if (c >= 'a' && c <= 'f') {
            val = 16 * val + (c - 'a' + 10);
        } else if (c >= 'A' && c <= 'F') {
            val = 16 * val + (c - 'A' + 10);
        } else {  // End of number.
            blink(countSetBits(val));
            val = 0;  // reset for next round
        }
    }
}

If I add this to the loop section of my program will it work? I don't have a board to test on right now

I tested it on an Uno using Serial.println(val, 16); instead of blink(countSetBits(val));, and it did correctly echo the values I entered with screen.

You could use BIT SHIFTING looks flash, but is actually really useful.
const unsigned char value = 0x55;  // Input
int blinks = 0;                    // Times to blink.

for (int i = 0; i < 8; ++i)
{
    blinks += ((value >> i) & 0x01); // Could just blink the light if its true.
}

(value >> i) takes value and moves the number right i places.  So if value is Hex 55 (0x55) that is 01010101 in binary.  On the first time around the loop when i is 0 (value >> 0) will be 0x55 (unchanged).   0x55 & 0x01 is a logical and between the two numbers, so any bits that are set in both will be set in the result.  Since 0x01 only has the least significant bit set (LSB) then we only need to look at the LSB of 0x55, which we know is set.  therefore blinks is incremented by one.
On the second time around the loop value >> i is 0x2A (00101010) because value has been shifted right one place.  So 0x2A & 0x01 = 0, so blink isn't altered.
etc.
The answer at the end of the loop is blinks == 4.

The OP already solved the problem of counting the bits set, and his solution looks more efficient than yours.

I just timed both solutions, both inside a function taking a uint8_t argument and returning an int. The OP's function takes from 14 to 86 cycles, depending on the number of set bits found. Yours takes 281 CPU cycles irrespective of its input.

You might do it much simpler... Create a fixed array that for each hex character possible (0..F) has the number of 1's counted.
Than iterate through the string, sum up the values of 1's from the array and make a LED blink that many times.
Something in pseudo code:
// Number of 1's: 0  1  2  3  4  5  6  7  8  9  A  B  C  D  E  F
boolean ones[] = {0, 1, 1, 2, 1, 2, 2, 3, 1, ...                };
string str = "ABC";
int total = 0;
for (index = 0; index < str.length; index++)
{
   if string[index] <= '9'
       total += ones[string[index] - '0'];
   else
       total += ones[string[index] - 'A' + 10];
}

Any help would be appreciated.

your code is in pretty good shape - there are some minor issues that need to be taken care of. the countSetBits() is a fairly standard implementation and in this case returns the right value:

I sped up the blinky rate for convenience.
a good starting out place.


text:
Warning when verifying sketch with VS code
I use Visual Studio Code to develop for arduino which uses Arduino Studio installed files and needs the installation to work. This works very well.
Annoying is that when verifying a sketch it takes longer than in the Arduino IDE. I suspect the following warning to cause it:

[Warning] Output path is not specified. Unable to reuse previously
  compiled files. Verify could be slow. See README.

I would like to get rid of the warning and I searched through all README files in the arduino installation folder and I also searched google but haven't found out what its supposed to mean and how to fix it. No readme file mentions that or I overlooked it.
Is there a documentation on how to fix this anywhere?

Is there a README with whatever you installed into VS?

@Majenko Thanks. After reading through 30-40 readme files in all sorts of folders and libraries I didn't think of that anymore :-).

I installed Arduino from App Store, to fix the issue i uninstalled Arduino and reinstalled by downloading windows installer, after installation and basic configuration in VS Code, like path to Arduino exe error was gone and i was able to compile and Upload.

Thanks to @Majenko I looked some place new:
documented in the arduino plugin of VS Code Arduino Extension there is an option to set an output directory.
Note though that according to this it should not be in the workspace or subfolders.
So in arduino.json settings file add:
"output": "../ArduinoOutput"

To clarify the answer, for those new in arduino world +StudioCode (source: https://marketplace.visualstudio.com/items?itemName=vsciot-vscode.vscode-arduino )
The following settings are as per sketch settings of the Arduino extension. You can find them in .vscode/arduino.json under the workspace.
{
    "sketch": "example.ino",
    "port": "COM5",
    "board": "adafruit:samd:adafruit_feather_m0",
    "output": "../build",
    "debugger": "jlink",
    "prebuild": "bash prebuild.sh"
}

sketch - The main sketch file name of Arduino.
port - Name of the serial port connected to the device. Can be set by the Arduino: Select Serial Port command.
board - Currently selected Arduino board alias. Can be set by the Arduino: Change Board Type command. Also, you can find the board list there.
output - Arduino build output path. If not set, Arduino will create a new temporary output folder each time, which means it cannot reuse the intermediate result of the previous build leading to long verify/upload time, so it is recommended to set the field. Arduino requires that the output path should not be the workspace itself or in a subfolder of the workspace, otherwise, it may not work correctly. By default, this option is not set.
debugger - The short name of the debugger that will be used when the board itself does not have a debugger and there is more than one debugger available. You can find the list of debuggers here. By default, this option is not set.
prebuild - External command before building the sketch file. You should only set one prebuild command. command1 && command2 does not work. If you need to run multiple commands before the build, then create a script.
When You add folder with sketch, you are creating "so called" project.
VS code puts there some hidden folders with the project configuration files.
To see them from windows file explorer you may enable show hidden files. than in your project folder You may find .vscode , and there is the arduino.json file.
More simple way is just click on the project navigation bar on the left, and open there the .vscode folder and using vscode as editor just add
"output": "../ArduinoOutput" or "output": "../build" or whatever you want to name that folder.
".." tells that it is one level above the "project folder" so it is "outside" as VScode wants.
And as far as i know this is not global setting, so You need to set it for every project if you want it.
Check the proper formatting in order to save file, use code hints to add options in file.
Hope that this is as clear as possible and help others to find that magic arduino.json file and understand where what and why.
Cheers.

Or, use the Visual Micro plug-in from https://www.visualmicro.com/  I have been using this for many years now and love it.  It is extremely well supported (see https://www.visualmicro.com/forums/)


text:
"No Socket available" for WiFiClient
I have an LDR/Photocell which sends a value 1 or 0 (depending on the value) to a text file on my web address. The code works for a few seconds then prints out No Socket available.
Any help will be appreciated; code below.
#include <SPI.h>
#include <WiFi.h>

int LDR = A0;
int LED = 11;
char ssid[] = "SSID";
char password[] = "password";
int status = WL_IDLE_STATUS;

char server[] = "www.example.com";
int value;

void setup() {
  Serial.begin(9600);
  pinMode(LDR, INPUT);
  pinMode(LED, OUTPUT);
  connectWifi();
  printWifiStatus();
  // postData();
}

void loop() {
  value = analogRead(LDR);
  postData();

  delay(10000);
}

void connectWifi() {
  while (status != WL_CONNECTED) {
    Serial.print("Attempting to connect to ");
    Serial.println(ssid);
    status = WiFi.begin(ssid, password);
    delay(500);
  }
}

void printWifiStatus() {
  // Print the SSID of the network you're attached to
  Serial.print("SSID: ");
  Serial.println(WiFi.SSID());

  // Print your WiFi shield's IP address
  IPAddress ip = WiFi.localIP();
  Serial.print("IP Address: ");
  Serial.println(ip);

  // Print the received signal strength
  long rssi = WiFi.RSSI();
  Serial.print("signal strength (RSSI):");
  Serial.print(rssi);
  Serial.println(" dBm");
}

void postData() {
  WiFiClient client;
  if (client.connect(server, 80)) {
    Serial.println("Connecting...");
    if (value > 350) {
      Serial.println("0");
      digitalWrite(LED, LOW);
      String data = "value=0";
      client.print("GET /example/client.php?");
      client.print(data);
      client.println(" HTTP/1.1");
      client.println("Host: www.example.com");
      client.println("Connection: close");
      client.println(); client.println();
      //client.stop();
    } else {
      Serial.println("1");
      digitalWrite(LED, HIGH);
      String data = "value=1";
      client.print("GET /example/client.php?");
      client.print(data);
      client.println(" HTTP/1.1");
      client.println("Host: www.example.com");
      client.println("Connection: close");
      client.println(); client.println();
      //client.stop();
    }
  } else {
    Serial.println("Connection failed");
    client.stop();
  }

}

Output:
Attempting to connect to SSID
SSID: SSID
IP Address: 255.255.255.255
signal strength (RSSI):-47 dBm
Connecting...
1
Connecting...
0
Connecting...
0
Connecting...
0
No Socket available
Connection failed
No Socket available
Connection failed
No Socket available
Connection failed
No Socket available

Actual web address omitted.

The text  “No Socket available” isn't in any of the Serial writes shown.  What program produces it, and where does it appear?  Also, perhaps edit question with cut and paste of serial monitor output (as text, not as picture)

@jwpat7 Thanks for that, updated the question.

Do any of the suggestions in Arduino wifi shield - “No Socket available” help?

I assume you actually have a server listening to port 80.  Also are you sure you should be using the WifiClient and not a HttpClient object?

I guess you have commented the command:
 //client.stop();
If you allow it, I guess you will have your code running


text:
Press on pressure sensor, then wait 5 seconds, turn on LED
I'm having some trouble wrapping my head around timers in Arduino. I've got a FSR Pressure Sensor and I want it to turn on my NeoPixel LED after pressing on it for 5 seconds. Any help is much appreciated!
My goal:
FSRReading > 1022 then wait 5 seconds, turn on NeoPixel
FSRReading < 1022, then reset timer, turn off NeoPixel
This is what I currently have for my code, I can detect and act on sensor readings, but no timer:
#include <Adafruit_NeoPixel.h>
#define PIN 6
#define NUMPIXELS 16
#include "Timer.h"

Adafruit_NeoPixel pixels = Adafruit_NeoPixel(NUMPIXELS, PIN, NEO_GRB + NEO_KHZ800);

int fsrPin = 9; // FSR is connected to analog 0
int fsrReading; // the analog reading from the FSR resistor divider int LEDbrightness;
int LEDbrightness;
Timer t;

void setup(void) {
 Serial.begin(9600);
 pixels.begin();
}

void loop(void) {
fsrReading = analogRead(fsrPin);
Serial.println(fsrReading);
Serial.print("Analog reading = ");

// we'll need to change the range from the analog reading (0-1023) down to the range // used by analogWrite (0-255) with map!
LEDbrightness = map(fsrReading, 0, 1023, 0, 255);

if (fsrReading < 10) {
Serial.println(" - No pressure"); } else if (fsrReading < 200) {
Serial.println(" - Light touch"); } else if (fsrReading < 500) {
Serial.println(" - Light squeeze"); } else if (fsrReading < 800) {
Serial.println(" - Medium squeeze"); } else {
Serial.println(" - Big squeeze"); }
delay(50);

for(int i=0;i<NUMPIXELS;i++){

  // pixels.Color takes RGB values, from 0,0,0 up to 255,255,255
  if (fsrReading>1022){
  pixels.setPixelColor(i, pixels.Color(0,255,0));
  } else if (fsrReading<1022) {
  pixels.setPixelColor(i, pixels.Color(0,0,0));
  }

  pixels.show(); // This sends the updated pixel color to the hardware.
 }
 }

The basic concept for tracking timing in the loop() is as follows:
1) when your event occurs, you store the current time in a variable:
unsigned long lastReading = 0;
uint8_t waiting = false;

if ( !waiting && fsrReading > 1022 ) {
  lastReading = millis();
  waiting = true;
}

2) you compare the lastReading variable against the current time and when enough time has passed, you can perform you timed action. ie:
int timeToWait = 5000; // 5 seconds

// are we waiting? and has enough time passed?
if ( waiting && millis() - lastReading > timeToWait ) {
   waiting = false; // reset

   // Light up lights
   ...
}

Note: this specific implementation only requires the sensor to rise above 1022 once, then wait 5 seconds before executing the timed action. If you want the sensor reading to be maintained above 1022 for the entire duration then you would add a check for a release with something like:
if ( fsrReading < 1022 ) {
  waiting = false; // reset because reading fell below 1022
}

hey thanks for your answer! could you explain a bit more about the purpose of the lastReading boolean? In what case would it become true? or is it suppose to stay false?

Error in the above:  long lastReading should be  unsigned long lastReading.  Also, 0 is an ok value for millis() so lastReading should not be used as a flag as well as a value.

@jwpat7. Right updated. And yes, 0 is a valid value for millis(), so if this sketch is expected to run ~50 days or more then a separate flag would be a good idea.

@jmswng lastReading is used to store the time of the last sensor reading. It is set to false to indicate we are not counting. When we are counting, it's value is the time when counting started. This 'trick' takes advantage of the fact that any non-zero number evaluates to true. However, jwpat7 pointed out that doing it this way could introduce unintended side effects. I'll update the code to use a dedicated flag. That should make it more clear.

@Mazaryk, ok, +1

My goal: FSRReading > 1022 then wait 5 seconds, turn on NeoPixel FSRReading < 1022, then reset timer, turn off NeoPixel

something like this will do.
  static uint32_t pressed_time; //last time the pressure sensor is pressed
  static uint8_t pressed_state=0; //the previous state. '1'->pressed, '0'->not pressed

  if (pressed()) {
    if (!pressed_state)) { //first time the pressure sensor is pressed
      pressed_state = 1;  //pressure sensor has been pressed
      pressed_time = millis(); //take time now
    }
  } else {                //no longer pressed
    pressed_state = 0;  //reset pressed state
    turnOffled();       //turn the led off
  }

  if ((millis() > pressed_time + LED_DLY) && pressed_state) turnOnled();

untested code, use at your own risk
edit:
the above code in action, with a minor modification to return the desired led state (active high):
    //turn on / off the led pins
    if (led_ctrl()) digitalWrite(LED_PIN, HIGH);    //turn on the led, active high
    else digitalWrite(LED_PIN, LOW);        //turn off the led
}

Note:
1. pressed() is active low;
2. the led is programmed to turn on 100ms after the button goes low.
hope it helps.

You should edit this to clarify relation of fsrReading to pressed()

Thanks for the answer, but what's 'LED_DLY'?

authors: Юрий Говорухин


text:
Navigating menus using buttons on Arduino
I have made a very short version of my code. It has the basic problem I am facing. I explain my code and problem below.
#include <Adafruit_RGBLCDShield.h>
#include <utility/Adafruit_MCP23017.h>
Adafruit_RGBLCDShield lcd = Adafruit_RGBLCDShield();

void setup() {
  lcd.begin(16, 2); //format of display
}

int menu = 0;
int subMenu = 99;
void loop() {

  uint8_t buttons = lcd.readButtons();

  lcd.setCursor(0,0);

  if (menu == 0) {
  lcd.print("Select menu option");
    if (buttons & BUTTON_SELECT) {
      lcd.clear();
      menu = 99;
      subMenu = 1;
    }
  }

  if (subMenu == 1) {
    lcd.print("in sub menu 1");
    if (buttons & BUTTON_SELECT) {
       lcd.clear();
       lcd.setCursor(0,1);
       lcd.print("shouldnt happen");
    }
  }
}

I am setting a variable menu, which will keep track of what main menu I am on, and a subMenu, which keeps track of what sub-menu I am on.
The default value of menu (0) prints on the LCD "Select Menu Option".
When pressing SELECT, the LCD is cleared. The menu is being set to an unknown number, so that it doesn't print anything, and subMenu is set to 1.
If subMenu is equal to 1 (which it will be if the user chooses presses SELECT), the LCD prints "in sub menu 1".
Inside this, if the button SELECT is clicked, it should print "shouldnt happen".
The issue I am facing is that when clicking SELECT for entering the menu 1, the SELECT is also carried out to the sub-menu, so instead of waiting for a second key press to confirm going into the sub menu, it goes straight into it.
This makes sense because it is check that SELECT has been pressed, prints a new page, with the button SELECT still having been pressed, so it validated the condition for key press in the sub menu as well.
The user input to LCD display response should be the following:
Select menu option -> presses SELECT -> in sub menu 1 -> presses SELECT -> shouldnt happen
Currently however, it is like this:
Select menu option -> presses SELECT -> in sub menu 1 shouldnt happen
How can I make it so that these key presses only act on the menu on which they are?
Thanks, let me know if something confuses you, I can explain in more details

Would still love to read any tips or help regarding these multi-level buttons. Thanks!

In your posted code I don't see you changing menu anywhere, except for setting it to 99 if it is zero.


text:
Which platform is better to debug Arduino memory problems? Linux or Windows?
I am developing a product. I developed every module in the firmware individually. Now I am integrating them but getting memory issues. I am not able to see how the memory is allocated inside the MCU during the runtime.
Can Linux help me debug issues better, using its command than Windows platform?
Thanks in advance.

As I remember the Arduino IDE is the same at Linux or Windows. Doesn't the IDE show you, how much memory is used, at compile time? Or are you using dynamic allocation? (You should ditch those anyway if possible, due to heap fragmentation)

Ide is showing me 54% dynamic allocation leaving 46% for stack I have no track for the stack that where it collapses. I ditched calloc, malloc because of fragmentation in heap. My programme runs nice for some loops but after some time it stucks. I want to track every byte of memory in every function & pin point where memory is getting leaked & program gets stucked.

#include <MemoryFree.h> Serial.println(freeMemory());

Why do you think that you have memory issues? It could be a number of things. The most likely problem is writing beyond a buffer on the stack or a function that returns a pointer to a buffer that was declared in that function on the stack.

46% of RAM for the stack is plenty, unless you are doing recursion or loads of stack allocation.

@jot for some loops My device works fine when I see it in the Serial Monitor but
when I make it a standalone device it stops pinging or device hangs after some time.  what may be the other causes of getting program stucked other than memory issue..? one you told that writing beyond a buffer but I checked I have not any issue like this in the code but please tell other causes of programme crash.

@EdgarBonet I am actually doing a lot of stack allocation in my final firmware structure. Actually its irreplaceable :(  .

@juraj thanks for your kind reply. I tried MemoryFree.h but the problem is this library is a little buggy for ex. while(1){Char c=0;Serial.println(freeMemory());} declares variable c again & again into a function which should decrease stack memory present but it shows the same value.

Your “proof” that MemoryFree is bugged is flawed. Declaring a variable again and again does not increase memory usage: the compiler is not as dumb as you seem to believe.

@bandejiya, by the language definition the variable exists until end of the block. so at } it is removed from stack. in reality the compiler optimizes it and puts it on the stack of the parent block

@Juraj: The compiler doesn't put it anywhere: as it is an unused variable, it gets optimized away.

@EdgarBonet, true. what I wrote would be true if it was used :-)

Hmm..! point noted, Thank you all so much..! :)

I simply burned the code written below but it is showing me free memory as 2267 bytes please somebody clarify that how in a Atmega328pu can have 2267 bytes free with overall capacity of 2048 bytes, The code is :----#include <MemoryFree.h>
void setup()
{Serial.begin(9600); Serial.println(freeMemory(), DEC);}
void loop()
{}

The operating system is irrelevant. If you want to debug the target you need a debugger and a debugging environment. That means a proper hardware debugger interface, not an Arduino's USB serial port, and a proper IDE like Atmel Studio not the Arduino IDE.  All are available for both Linux and Windows.

I have developed firmware on arduino IDE..! will'nt  it will take a lot more efforts to change the IDE..? please suggest any other way if possible to achieve MVP.

The Arduino IDE is very easy to program in but almost impossible to debug in. The best you can do is use Serial.print to display information. You cannot do real debugging in the Arduino environment. It's not a professional tool.


text:
MPU6050 accelerometer giving output as -1 -1. Can anyone tell the issue in the code?
// MPU-6050 Short Example Sketch
// By Arduino User JohnChi
// August 17, 2014
// Public Domain
#include<Wire.h>
const int MPU_addr=0x68;  // I2C address of the MPU-6050
int16_t AcX,AcY,AcZ,Tmp,GyX,GyY,GyZ;

void setup() {
  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);
  Serial.begin(9600);
}

void loop() {
  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)
  GyZ=Wire.read()<<8|Wire.read();  // 0x47 (GYRO_ZOUT_H) & 0x48 (GYRO_ZOUT_L)
  Serial.print("AcX = "); Serial.print(AcX);
  Serial.print(" | AcY = "); Serial.print(AcY);
  Serial.print(" | AcZ = "); Serial.print(AcZ);
  Serial.print(" | Tmp = "); Serial.print(Tmp/340.00+36.53);  //equation for temperature in degrees C from datasheet
  Serial.print(" | GyX = "); Serial.print(GyX);
  Serial.print(" | GyY = "); Serial.print(GyY);
  Serial.print(" | GyZ = "); Serial.println(GyZ);
  delay(333);
}

Serial Monitor output:
AcX = -1 | AcY = -1 | AcZ = -1 | Tmp = 36.53 | GyX = -1 | GyY = -1 | GyZ = -1
AcX = -1 | AcY = -1 | AcZ = -1 | Tmp = 36.53 | GyX = -1 | GyY = -1 | GyZ = -1
[…]

You need to initialize the device and take it out of sleep mode first.

A return value of -1 means that the Wire.read is reading an empty buffer. In other words: you are not connected to the mpu6050. Try a i2c scanner first: https://playground.arduino.cc/Main/I2cScanner

Thanks Jot..! you point out the problem. My MPU was not connected to the arduino. Actually in arduino's MCU i2c module was not working well.

I found that there was a communication problem between MPU and Arduino which I found using code given in this link http://playground.arduino.cc/Main/I2cScanner .
Then I found thought problem Must be in MPU or arduino and problem was in Arduino MCU.
So after changing the Arduino MCU it worked


text:
Cannot mount NodeMCU with MicroPython on Mac OS X
I've recently bought a NodeMCU board and flashed MicroPython in it. I've read about the boot.py and main.py scripts, but I can't understand how to access them...
I have succesfully connected to the Python REPL with the screen command and everything works fine. Is there a way to mount it as an external drive on Mac OS X? Because I haven't found a way till now.
Thanks in advance!

this is not an arduino question, it's a micropython question.

The typical NodeMCU board uses a fixed function CP-210x USB-Serial chip.  This cannot appear to a host operating system as any ordinary sort of storage device, so it is not "mountable" via conventional storage drivers.
Access would need to be through some client program - or else, at a bit of a stretch, some highly specialized driver that created something fitting the host operating system's idea of filesystem, but proxying the actions through operatings the CP-210x and software running in the ESP8266 can support.