70 lines
2.4 KiB
C++
70 lines
2.4 KiB
C++
#ifndef MAIN_H_DEF
|
|
#define MAIN_H_DEF
|
|
#include "system.h"
|
|
#include "gpio.h"
|
|
#include "usart.h"
|
|
#include "adc.h"
|
|
#include "spline.h"
|
|
static constexpr unsigned FIFOLEN = 8u;
|
|
class Average : public OneWay<uint16_t> {
|
|
FIFO<uint32_t, FIFOLEN> & ring;
|
|
uint32_t y, w;
|
|
public:
|
|
explicit Average (FIFO<uint32_t, FIFOLEN> & r) : OneWay(), ring(r), y(0u), w(0u) {}
|
|
unsigned int Send(uint16_t * const ptr, const unsigned int len) override {
|
|
unsigned suma = 0u;
|
|
for (unsigned n=0u; n<len; n++) {
|
|
suma += ptr [n];
|
|
}
|
|
y += suma - w; // ustálení teploty trvá dost dlouho, takže lze posílat klouzavý
|
|
w = y >> 4; // průměr s postupným zapomínáním. Hodnota je násobena délkou
|
|
// bufferu, t.j. 128 (posun doleva o 7)
|
|
if (w < (134 * 128)) return len; // skip limits - nezobrazuj mimo rozsah -40 až 120
|
|
if (w > (3976 * 128)) return len;
|
|
ring.Write (w);
|
|
return len;
|
|
}
|
|
};
|
|
class RealOut : public BaseLayer { // Zjednodušené výpisy teploty
|
|
static constexpr unsigned BUFLEN = 64u;
|
|
static constexpr char const * decstr = "0123456789";
|
|
unsigned dec_points;
|
|
char buf[BUFLEN]; //!< Buffer pro výstup čísla.
|
|
public:
|
|
explicit RealOut (const unsigned dp = 2) noexcept : dec_points(dp) {}
|
|
RealOut & operator << (const char * str) {
|
|
uint32_t i = 0;
|
|
while (str[i++]); // strlen
|
|
BlockDown (str, --i);
|
|
return * this;
|
|
}
|
|
RealOut & operator << (const real num) {
|
|
int mf = 1;
|
|
for (unsigned n=0u; n<dec_points; n++) mf *= 10;
|
|
int p = (mf * num.x) >> 16; bool s = false;
|
|
if (p < 0) { p = -p; s = true; }
|
|
int i = BUFLEN, j = 0; buf [--i] = '\0';
|
|
for (;;) {
|
|
const int q = p % 10; p = p / 10; j++;
|
|
buf [--i] = decstr [q];
|
|
if (j == dec_points) { buf [--i] = '.'; j++; }
|
|
if (!p and j > (dec_points + 1u)) { break; }
|
|
}
|
|
if (s) { buf [--i] = '-'; j++; }
|
|
BlockDown(buf + i, j);
|
|
return * this;
|
|
}
|
|
protected:
|
|
uint32_t BlockDown (const char * buf, uint32_t len) {
|
|
uint32_t n, ofs = 0, req = len;
|
|
for (;;) {
|
|
// spodní vrstva může vrátit i nulu, pokud je FIFO plné
|
|
n = BaseLayer::Down (buf + ofs, req);
|
|
ofs += n; // Posuneme ukazatel
|
|
req -= n; // Zmenšíme další požadavek
|
|
if (!req) break;
|
|
}
|
|
return ofs;
|
|
}
|
|
};
|
|
#endif // MAIN_H_DEF
|