@something_go_wrong

Как нарисовать график используя стандартные средства ssd1306?

Хочу понять, как можно нарисовать любой график, например параболу на дисплее ssd1306.
  • Вопрос задан
  • 817 просмотров
Пригласить эксперта
Ответы на вопрос 3
hint000
@hint000
у админа три руки
Первый же ответ в Гугле: https://habr.com/ru/post/313490/
Ответ написан
Комментировать
Делюсь своим кодом для ардуины с графиком влажности. Код даю как есть, со всеми его недостатками. График автоматически масштабируется, есть подписанные оси. Писался давно, библиотеки для датчика DHT22 с тех пор обновились и код не компилируется, но рисовка должна работать.
Осторожно, сырой код!
//Подключаем библиотеки
#include <Wire.h>
#include <OLED_I2C.h>
#include "DHT.h"
#include <BH1750.h>
//Создаем объекты
OLED  myOLED(SDA, SCL, 8);
DHT dht;
BH1750 lightMeter;
//Подключаем шрифты
extern uint8_t SmallFont[];
extern uint8_t MediumNumbers[];
//Объявляем переменные
float humidity[100];
int count = 0;

void setup()
{
  myOLED.begin();
  myOLED.setFont(SmallFont);
  dht.setup(4);
  lightMeter.begin();
}

void loop()
{
  for (int i = 99; i > 0; i--)//Циклом сдвигаем массив на единицу
  { //делать кольцевой массив лень
    humidity[i] = humidity[i - 1];
  }
  humidity[0] = dht.getHumidity();//Меряем влажность
  if (count < 100) count++;       //Сколько атуальных значений в массиве
  //для исключения нулей при включении

  myOLED.clrScr();//Очистили буфер дисплея
  myOLED.setFont(MediumNumbers);//Выбради шрифт
  myOLED.printNumF(humidity[0], 1, RIGHT, 0, '.', 4);//Написали сверху справа влажность
  myOLED.printNumF(dht.getTemperature(), 1, LEFT,  0, '.', 4);//А слева температуру
  //Нарисовали рамочку графика
  myOLED.drawLine(0, 18, 127, 18);
  myOLED.drawLine(0, 18, 0, 63);
  myOLED.drawLine(127, 18, 127, 63);
  myOLED.drawLine(0, 63, 127, 63);
  //Нашли минимум и максимум на графике
  int minHum = humidity[0];
  int maxHum = humidity[0] + 1;
  for (int i = 1; i < count; i++)
  {
    minHum = min(minHum, humidity[i]);
    maxHum = max(maxHum, humidity[i] + 1);
  }
  //Написали их на шкале справа
  myOLED.setFont(SmallFont);
  myOLED.printNumI(lightMeter.readLightLevel(), CENTER, 0);
  myOLED.printNumI(maxHum, 107, 20, 3);
  myOLED.printNumI(minHum, 107, 55, 3);
  //Нарисовали саму шкалу
  myOLED.drawLine(103, 62, 103, 20);
  myOLED.drawLine(103, 61, 108, 61);
  myOLED.drawLine(103, 20, 108, 20);
  //И деления на ней
  int j = 10; //шаг делений 10%
  if (maxHum - minHum < 50) j = 5; //или 5% если размах графика меньше
  if (maxHum - minHum < 11) j = 1; //или 1% если совсем маленький
  for (int i = 0; i <= 100; i += j) //перебираем все возможные значения процентов
  {
    if (i > minHum && i < maxHum)   //но рисуем только если они в диапазоне графика
    {
      int y = map(i, minHum, maxHum, 61, 20); //определяем положение штриха по вертикали
      if (i % 10 == 0) myOLED.drawLine(103, y, 107, y); //если это штрих для десяткков, то длинный
      else myOLED.drawLine(103, y, 105, y);//иначе короткий
    }
  }
  //Нарисовали график
  for (int i = 0; i < count; i++)
  {
    int y = map(humidity[i] * 10, minHum * 10, maxHum * 10, 61, 20);
    myOLED.drawLine(101 - i, 62, 101 - i, y);
  }
  //Вывели данные из буфера на дисплей
  myOLED.update();
  //Ждем следующего измерения
  delay(dht.getMinimumSamplingPeriod());
  //delay(60000);
}
Ответ написан
Комментировать
@lonelymyp
Хочу вылезти из минуса по карме.
У ssd1306 нет стандартных средств для рисования графиков.
Но всегда можно воспользоваться одной из множества графических библиотек, либо нарисовать самому, попиксельно.
В любом случае интернет завален примерами и уроками под это супер популярный контроллер
Ответ написан
Комментировать
Ваш ответ на вопрос

Войдите, чтобы написать ответ

Похожие вопросы