I'm using dtostrf() to transcribe a float into a string for my touchscreen. I'd leave it as a float, but my screen orientation library function only works with a string.
So I have a char array, then a float value. then dtostrf().
char buffer[6]
float X; //changes each loop with incoming sensor data from pixy camera
float thingposition = X * .0064 //float calculations are performed.
void loop(){
Camera.Get_X(); //retrieves X from the camera. waits until X has been recieved via UART serial
dtostrf(buffer, 5, 2, thingposition) // writes float to string with a controled decimal place and all that - dtostrf(floatVar, minStringWidthIncDecimalPoint, numVarsAfterDecimal, charBuf);
Tft.drawString(buffer, 70, 215, 5, WHITE); //print output to screen
}
Note that this is a simplified version. In my code I also have methods for overwriting my last string value on the LCD when the new one has changed. I also have several "if" conditionals that control whether I write the buffer value to the screen or instead send an error message. Those things do not seem to be causing me problems though, except to say that my buffer overflows only occur when I cause the sensors to flip the conditionals at just the right interval.
For example, when I place my hand in front of the camera, that triggers the error message. Take my hand away, and then the number "thingposition" is printed to the screen. But if I time my hand just right, the buffer overflows and numbers loop across the screen. Usually this freezes the whole sketch. The best I can figure is that since dtostrf() does not check bounds, and since the calculated float values can be longer than the buffer has room for, that sometimes dtostrf() tries to write too many digits to the buffer. Something timing-related seems to trigger the problem, but what I need is some way to prevent the overflow in the first place.
I've tried rounding "thingposition" to a certain number of sigfigs, but I can't seem to truncate it at the desired decimal point. That shouldn't matter though, since dtostrf has controls for the minimum total length including the decimal point, as well the number of digits after the decimal. I also tried making sure that the last byte in my char array is null by adding this right after dtostrf():
stringval[5] = NULL; //make sure buffer is null-terminated to prevent buffer overflow
I've tried doubles, different ways of rounding, and anything I could find, but the problem has persisted for several weeks and a few steady days worth of searching for a solution. I'll be glad to provide further information if anyone has any ideas on what to try. Thanks everyone.
thingposition
is100000
or more, thendtostrf()
will use more than 5 characters to represent the number. It will use no more than 2 decimal digits (less if they won't fit in 5 characters), but it won't compromise the main number to fit it inside your buffer. If you don't want that, clip the number to less than100000