Skocz do zawartości

display.display() blokuje działanie programu


Pomocna odpowiedź

Napisano

witam, pisze program do mini radia które ma działać na Attiny i ma wykorzystywać wyświetlacz OLED 64x32 oraz moduł radia TEA5767. problemem jest przedostatnia linijka programu a mianowicie display.display(); która powoduje że działa wyświetlacz ale przestaje działać radio jak ją usunę to sytuacja jest odwrotna więc proszę o pomoc by oba działały równocześnie bo nie mam pojęcia co jest nie tak

#include <Adafruit_GFX.h>
#include <Adafruit_SSD1306.h>
#define SCREEN_WIDTH 128 // OLED display width, in pixels
#define SCREEN_HEIGHT 64 // OLED display height, in pixels
Adafruit_SSD1306 display(SCREEN_WIDTH, SCREEN_HEIGHT, &Wire, -1);

#include <Wire.h>
#include <TEA5767Radio.h>

TEA5767Radio radio = TEA5767Radio();
float freq = 84 ;

void setup()
{
  Wire.begin();
  Serial.begin(115200);
  if (!display.begin(SSD1306_SWITCHCAPVCC, 0x3C)) { // Address 0x3D for 128x64
    Serial.println(F("SSD1306 allocation failed"));
    for (;;);
  }
  delay(2000);

  pinMode(3, INPUT_PULLUP);
  pinMode(4, INPUT_PULLUP);

}

void loop() {

  if (digitalRead(4) == LOW) {
    freq = freq + 0.01 ;
  }
  if (digitalRead(3) == LOW) {
    freq = freq - 0.01 ;
  }
  if (freq < 84) {
    freq = 113 ;
  }
  if (freq > 113) {
    freq = 84 ;
  }

  radio.setFrequency(freq);

  display.clearDisplay();
  display.setTextSize(2);
  display.setTextColor(WHITE);
  display.setCursor(0, 10);
  display.println(freq);
  display.setCursor(85, 10);
  display.println("MHz");
  display.display();
  Serial.println(freq);

}

 

(edytowany)

Możesz użyć multipleksera i2c bo chyba te dwa układy z jakiegoś powodu się "gryzą". Na marginesie czy na pewno w pętli loop zawsze musisz wysyłać częstotliwość radio.setFrequency(freq);? To ma sens po zmianie tej częstotliwości, a nie tysiące (miliony) razy na sekundę.

Jeśli chodzi o przyciski Arduino to czy aby na pewno program je właściwie obsługuje? Nie doskwiera ci drganie styków tych przełączników?

Edytowano przez Belferek
(edytowany)

Multiplekser rozumiem ze chodzi o osobna płytkę? Da sie to jakoś inaczej rozwiązać bo zależy mi na tym żeby całość była jak najmniejsza a z tego co widzę to multipleksery da sie kupić ośmio kanałowe co mnie średnio urządza ze względu na ich rozmiary (i cenę z reszta też).

Z kolei przyciski co ciekawe działają tak jak chce tez myślałem ze będą bardzo dużo dodawać/ odejmować z częstotliwości ale chodzi wszystko tak ze da się ustawić precyzyjnie częstotliwość.

zmienie tez to wysyłanie częstotliwości do radia.

Edytowano przez brunobu
2 godziny temu, brunobu napisał:

Z kolei przyciski co ciekawe działają tak jak chce tez myślałem ze będą bardzo dużo dodawać/ odejmować z częstotliwości ale chodzi wszystko tak ze da się ustawić precyzyjnie częstotliwość.

To znaczy że kod się dosyć mocno muli, bo powinno zasuwać..(biorę pod uwagę że libsy do lcd nie działają super szybko) 

A co do bibliotek to spróbuj jakiejś innej...akurat do ssd1306 jest ich dosyć sporo..

Przegapiłem informację, że piszesz pod ATtiny - jakie konkretnie? To dużo mniejsze układy. Niekoniecznie biblioteki dla ATmegi są dobre dla ATtiny. Swego czasu spotkałem się z biblioteką TinyWire. Na stronie arduino.cc można poczytać o SoftWire. Tego bym się czepiał - obsługi TWI przez to maleństwo. Pullupy na liniach sterujących oczywiście masz podpięte?

Stronka z wieloma projektami dla ATtiny - tutaj.

  • Lubię! 1

Posiadam Attiny85 i 84. Ze względu na to ze zależy mi na minimalnych rozmiarach celuje w Attiny85. Poczytam o TinyWire i SoftWire bo słyszę o tym pierwszy raz. Wstawienie rezystorów obok przycisków to dobry pomysł zapomniałem o tym.

9 godzin temu, brunobu napisał:

celuje w Attiny85

No to biblioteki Adafruit niespecjalnie się do tego nadają - przy displayu 64 x 32 połowa RAM-u idzie na bufor wyświetlacza i podejrzewam, że po prostu brakuje pamięci.

Oczywiście da się to zrobić - ja pisałem swój driver do wyświetlacza 128x64 właśnie dla ATtiny85, zerknij tutaj - może się do czegoś przyda. No i oczywiście zapomnij o istnieniu Serial.

  • Lubię! 1

Wstawiłem rezystory tam gdzie powinny być. Znalazłem kilka innych bibliotek ale nie potrafię z nich korzystać biorę przykładowe programy które z nimi się instaluje i zmieniam np. Tekst żeby wyświetlał coś innego ale zamiast wyświetlać to co powinno wyświetla jakieś dziwne krzaczki. Problemy występują również na płytkach arduino UNO i NANO z programem radia i przykładem z biblioteki

dobra doszedłem z programem do czegoś takiego zostałem przy pierwszej bibliotece której używałem ale nadal nie działa to perfekcyjnie bo radio działa co sekundę i przez kolejną sekuunde jest cisza ale wyswietlacz działa 🙂

 

 

#include <SPI.h>
#include <Wire.h>
#include <Adafruit_GFX.h>
#include <Adafruit_SSD1306.h>

#define SCREEN_WIDTH 128
#define SCREEN_HEIGHT 64

#define OLED_RESET     4
#define SCREEN_ADDRESS 0x3C
Adafruit_SSD1306 display(SCREEN_WIDTH, SCREEN_HEIGHT, &Wire, OLED_RESET);

#include <TEA5767Radio.h>
TEA5767Radio radio = TEA5767Radio();

float freq = 90.1 ;
void setup() {
  Serial.begin(9600);

  if (!display.begin(SSD1306_SWITCHCAPVCC, SCREEN_ADDRESS)) {
    Serial.println(F("SSD1306 allocation failed"));
    for (;;);
  }

  display.display();
  delay(2000);
  display.clearDisplay();

  wyswietlacz();

  display.invertDisplay(true);
  delay(1000);
  display.invertDisplay(false);
  delay(1000);
}
void loop() {
  if (digitalRead(4) == LOW) {
    freq = freq + 0.01 ;
  }
  if (digitalRead(3) == LOW) {
    freq = freq - 0.01 ;
  }
  if (freq < 84) {
    freq = 113 ;
  }
  if (freq > 113) {
    freq = 84 ;
  }
  radio.setFrequency(freq);
  
  wyswietlacz();
}

void wyswietlacz() {
  delay(1000);
  display.clearDisplay();
  display.setTextSize(1);      // Normal 1:1 pixel scale
  display.setTextColor(SSD1306_WHITE); // Draw white text
  display.setCursor(0, 0);
  display.print(freq);
  display.display();
}

 

stworzyłem coś takiego jako tako działa wyswitlacz sie odswieża tylko wtedy gdy zmienia się częstotliwość i radio działa po ustawieniu częstotliwości mam jednak wrażenie że nie zmienia częstotliwosci tak jak powinno więc proszę żeby ktoś to skontrolował z góry dziękuje

#include <SPI.h>
#include <Wire.h>
#include <Adafruit_GFX.h>
#include <Adafruit_SSD1306.h>

#define SCREEN_WIDTH 128
#define SCREEN_HEIGHT 64

#define OLED_RESET     4
#define SCREEN_ADDRESS 0x3C
Adafruit_SSD1306 display(SCREEN_WIDTH, SCREEN_HEIGHT, &Wire, OLED_RESET);

#include <TEA5767Radio.h>
TEA5767Radio radio = TEA5767Radio();

float freq ;
void setup() {
  Serial.begin(9600);

  if (!display.begin(SSD1306_SWITCHCAPVCC, SCREEN_ADDRESS)) {
    Serial.println(F("SSD1306 allocation failed"));
    for (;;);
  }

  display.display();
  delay(2000);
  display.clearDisplay();

  wyswietlacz();

  freq = 90.1 ;
  radio.setFrequency(freq);
}
void loop() {

  radio.setFrequency(freq);
  if (digitalRead(4) == LOW) {
    freq = freq + 0.01 ;
    wyswietlacz();

  }
  if (digitalRead(3) == LOW) {
    freq = freq - 0.01 ;
    wyswietlacz();

  }
  if (freq < 84) {
    freq = 113 ;
  }
  if (freq > 113) {
    freq = 84 ;
  }
}

void wyswietlacz() {
  radio.setFrequency(freq);
  display.clearDisplay();
  display.setTextSize(2);      // Normal 1:1 pixel scale
  display.setTextColor(WHITE); // Draw white text
  display.setCursor(0, 10);
  display.print(freq);
  display.setCursor(85, 10);
  display.println("MHz");
  display.display();
}
  • Lubię! 1

 

7 minut temu, brunobu napisał:

mam jednak wrażenie że nie zmienia częstotliwosci tak jak powinno

Masz uruchomiony w setup() port szeregowy możesz więc w loop() zobaczyć jak działa zmiana częstotliwości. Poza tym już pytałem o to czy w kółko musisz wysyłać radio.setFrequency(freq)? Ty wysyłasz tę częstotliwość podwójnie - w funkcji loop() i funkcji wyswietlacz(). 

Może wystarczy jedynie po jej zmianie? W swoim programie masz dwie bliźniacze konstrukcje (tu dla zmniejszenia częstotliwości):

if (digitalRead(3) == LOW) {
    freq = freq - 0.01 ;
    wyswietlacz();

  }
  if (freq < 84) {
    freq = 113 ;
  }
  

Czy nie lepiej (przy założeniu, że przyciski Ci działają właściwie) to napisać np. tak:

if (digitalRead(3) == LOW) 
{
  if( freq > 84.0 ) freq = freq - 0.01;
  else freq = 113.0;
  zmiana = 1;
}


// pozniej sprawdzasz czy doszlo do zmiany, a jesli tak to to wysylasz nowa f do radia
// i dla diagnostyki przez Serial

if(zmiana == 1)	
{
  radio.setFrequency(freq);
  Serial.println(freq);
  zmiana = 0;
}

Oczywiście zmienną zmiana należy sobie wcześniej zadeklarować

Bądź aktywny - zaloguj się lub utwórz konto!

Tylko zarejestrowani użytkownicy mogą komentować zawartość tej strony

Utwórz konto w ~20 sekund!

Zarejestruj nowe konto, to proste!

Zarejestruj się »

Zaloguj się

Posiadasz własne konto? Użyj go!

Zaloguj się »
×
×
  • Utwórz nowe...