Medidor de Nivel utilizano Potenciometro e led's

Versão de Software Utilizado: Arduino 1.0.3 [Vesão mais recente]

Ola todos sou novo na area de arduino e hoje queria mostrar um simples projeto de um "Medidor de Nivel" utilizando led's e potenciômetro.

O funcionamento dele é o seguinte : Tenho três led's vermelho,verde,amarelo ligados nos pinos digitais 2,3,4 e um potenciometro ligado ao pino A1 (Analogico 1).

Conforme eu vou girando o potenciometro aumentando o valor dele vai acendendo os led's

Quando o potenciometro marca 40 acende apenas o led vermelho e resto fica apagado, quando chega em 80 ocorre a mesma coisa de todos o led's fica aceso apenas o led verde e quando chega aos 120 fica aceso apenas o led amarelo.

..... bem voce pode fazer isso tambem com o LED RGB que tem exatamente a mesma estrutura que foi citado acima mas so muda as cores vermelho,verde e azul.

ou ver o video do projeto em funcionamento: - YouTube

download do codigo fonte+fz(arquivo do Fritzing) -->Medidor_de_Nivel

ATENÇÃO: ao abrir o arquivo o Fritzing se aparecer alguma mensagem durante seu carregamento click em READ-ONLY

Bom entao agora um desafio facil.
No teu código tens de andar a fazer mira para apanhar o potenciómetro no valor correcto para assim satisfazeres o case:

  switch (x)
  {
    case 40:// Quando aumentar o potenciometro para 40 
    // dos tres leds acenderá apenas o led vermelho
    digitalWrite(led_vermelho,HIGH);
    digitalWrite(led_verde,LOW);
    digitalWrite(led_amarelo,LOW);
    break;
    case 80:// Quando aumentar o potenciometro para 80 
    // dos tres leds acenderá apenas o led verde
    digitalWrite(led_vermelho,LOW);
    digitalWrite(led_verde,HIGH);
    digitalWrite(led_amarelo,LOW);
    break;
    case 120:// Quando aumentar o potenciometro para 120 
    // dos tres leds acenderá apenas o led amarelo
    digitalWrite(led_vermelho,LOW);
    digitalWrite(led_verde,LOW);
    digitalWrite(led_amarelo,HIGH);
    break;
    default://Se caso o potenciometro não chegar em nenhum dos 
    //valores abaixo (40,80,120) todos os três led's 
   // permanecerão apagados
   digitalWrite(led_vermelho,LOW);
    digitalWrite(led_verde,LOW);
    digitalWrite(led_amarelo,LOW); 
    break;

Assim nao é medidor de Nivel :grin: Porque não adicionares mais leds para teres melhor resultados e melhorar os leds que acendem ao longo da escala?
Tipo 10 Leds(O teu arduino tem saidas suficientes XD) e teres uma escala de 0 a 100% onde nos 100 % acendem todos e nos 50% apenas metade e por ai adiante.
È fácil de fazer e vai te fazer pensar talvez e reaprender...

Se ligares 10 LEDs tem cuidado com o máximo da corrente por porto do Arduino...

Já agora, um medidor de nível não será algo assim:

#define VERMELHO   0
#define AMARELO     1
#define VERDE         2

const int LEDs[] = {4,6,8}; // imagina os LEDs ligados nos pinos 4, 6 e 8

void liga_led(unsigned char led) {

for (char i = 0; i <3; i ++ {
   if (i == led) {
      digitalWrite(i, HIGH); //liga LED
   } else {
      digitalWrite(i, LOW); //desliga LED
   }
}

loop () {

unsigned int nivel = analogRead(A1); 

if (nivel <= 40) {
    liga_led(VERMELHO);
}
if (nivel > 40 && nivel <= 80) {
    liga_led(AMARELO);
}
if(nivel > 80) {
    liga_led(VERDE);
}
}

Ola HugoPT e bubulindo ... eu sou iniciante na area de arduino , porem e vi que os dois que escreveram , e vou pensar em melhora-lo e autalizar o arquivo e o video.

obrigado pelas opiniões XD

ps: Eu tenho muito que aprender pela frente.

So uma pequena correçao na funçao liga_led penso que te enganaste e deverá ter de ficar asssim

void liga_led(unsigned char led) {

for (char i = 0; i <3; i ++ {
   if (i == led) {
      digitalWrite(LEDs[i], HIGH); //liga LED
   } else {
      digitalWrite(LEDs[i], LOW); //desliga LED
   }
}
}

Bruno claro que tambem teras de usar o Setup para configurar os pinos como saida e bla bla bla....
Mas a idea é esta que o Bubulindo te apresentou, o codigo está mais limpo e reutilizavel

HugoPT uma curiosidade que eu achei no codigo que vc escreveu anteriomente..

qual é a função do "unsigned"?

joguei no tradutor mas não é "não assinado" :~

que eu utilizei ele poucas vezes

o quer dizer exatamente isso na liguagem do arduino (C/C++)

O prefixo unsigned quer dizer sem sinal ou seja serve para delimitar o valor minimo e maximo de uma variavel.
Por defeito um int se nao indicares prefixo ele é signed (com sinal ), como um Int sao 16 Bits na arquitectura do arduino ele pode conter no maximo 65535 valores( que é 2 ^16)
Sendo ela unsigned começa de 0 a 65535
Se for signed é dividida ao meio contendo valores negativos(65535/2 ) que dá ?32,768 to 32,767
Se na programaçao do arduino declareces uma variavel assim e a colocasses na loop() imprimindo o valor actual para a Porta Serie

int numero = 0;

loop()
{
Serial.print(numero);
numero ++;
}

Ele iria contar ate 32767 e depois pulava para o valor negativo dando a volta.

HugoPT:
So uma pequena correçao na funçao liga_led penso que te enganaste e deverá ter de ficar asssim

void liga_led(unsigned char led) {

for (char i = 0; i <3; i ++ {
  if (i == led) {
      digitalWrite(LEDs[i], HIGH); //liga LED
  } else {
      digitalWrite(LEDs[i], LOW); //desliga LED
  }
}
}

Muito bem visto... correr o que eu deixei com a porta série havia de ser engraçado... LOL

HugoPT:
O prefixo unsigned quer dizer sem sinal ou seja serve para delimitar o valor minimo e maximo de uma variavel.
Por defeito um int se nao indicares prefixo ele é signed (com sinal ), como um Int sao 16 Bits na arquitectura do arduino ele pode conter no maximo 65535 valores( que é 2 ^16)
Sendo ela unsigned começa de 0 a 65535
Se for signed é dividida ao meio contendo valores negativos(65535/2 ) que dá ?32,768 to 32,767
Se na programaçao do arduino declareces uma variavel assim e a colocasses na loop() imprimindo o valor actual para a Porta Serie

int numero = 0;

loop()
{
Serial.print(numero);
numero ++;
}



Ele iria contar ate 32767 e depois pulava para o valor negativo dando a volta.

Se calhar é melhor experimentares com uma variável char (que contém valores de -126 a 127) em vez do int. Apenas porque demora menos tempo para mostrar o mesmo conceito.

Eu tenho por norma usar o unsigned sempre e se uma variável tiver a possibilidade de conter valores negativos, então usar o signed ou deixar em branco essa opção. O motivo pelo qual tenho esta norma vem do facto que eu iniciei a programação de microcontroladores em Assembly com PICs. Ora, as PIC que usava tinham pouca memória, apenas 31 instruções de assembly e era uma máquina de 8 bits. Então, tinha de "espremer" ao máximo os valores que podia conter dentro das variáveis e mais tarde passei essa preocupação ou método para o meu C. Daí tentar sempre garantir que tenho o maior espaço disponível na variável (0 a X em vez de -X/2 a X/2)

Não fiques preocupado, no exemplo em questão ser unsigned não implica em nada para o funcionamento do exemplo, é apenas a minha maneira de escrever código (como podes confirmar nos restantes posts que tenho aqui no fórum).

Nota também, apenas como curiosidade, que podes activar uma flag que trata todas as variáveis como unsigned. Ou seja... normalmente defines uma variável assim:

int my_var = 0;

No entanto, se reparares bem, em lado nenhum dizes ao compilador que a variável é signed ou unsigned. O compilador é que, por defeito, assume que é signed. No entanto, a forma completa de escrever a definição da variável seria

signed int my_var = 0; 
//ou 
unsigned int my_var = 0;

Num programa pequeno, dentro do mesmo ficheiro e que seja de muito baixo nível (implementações que mexem directamente com registos do micro processador, por exemplo), este cuidado é irrelevante ou até muito pouco problemático uma vez que é simples de ajustar o tipo de variável consoante o compilador.

No entanto, em projectos grandes onde o código vai estar distribuído por várias equipas ou pessoas e que seja um código de alto nível, ou seja, suposto correr em plataformas diferentes (tipo em PIC, ARM e AVR), ter este cuidado de definir exactamente o tipo de variável ajuda a evitar problemas com a compilação.

Isto é algo que testado é melhor... vê o exemplo do Hugo.

Algo que é complementar a isto são os casts. Já falaste ou leste sobre isso? Se não sabes o que é, apita que metemos aqui um exemplo para perceberes. :slight_smile:

Ola HugoPT e bubulindo , eu consegui melhora-lo , mas com 10 leds , mas eu consegui fazer em escala

20 40 60 80 100

ou seja utilizei 5 (1 para a acionar 2 led's) pinos do meu arduino se fosse em 10 em 10 acho que iria sobre carregar um pouco o meu arduino.

mas o desafio de colocar 10 led's e de o arduino aguentar sucegadamente consegui e tambem consegui fazer ele acencer gradativamente sem ocorre do led anterior se apagar como estava no video antes

#define VERDE 0
#define GREEN 1
#define AMARELO 2
#define YELLOW   3
#define VERMELHO  4
#define  RED 5

const int LED[] = {4,7,11,12,13};
int potenciometro = A1;
int potencia = 0;

void setup()
{
  pinMode(4,OUTPUT);
  pinMode(7,OUTPUT);
  pinMode(11,OUTPUT);
  pinMode(12,OUTPUT);
  pinMode(13,OUTPUT);
  Serial.begin(9600);
}

void loop()
{ 
  unsigned int nivel = analogRead(potenciometro);

  nivel = map(nivel,0,1023,0,100);

Serial.println(nivel);

if (nivel > 20 )// 20% {
    led_on(VERDE);
}

if (nivel > 40)// 40%
{
  led_on(GREEN);

if (nivel > 60)//60% {
    led_on(AMARELO);
}

if (nivel > 80)//80%
{
  led_on(YELLOW);
}

if(nivel > 80) {
    led_on(VERMELHO);

}

if(nivel > 100)//100%
{
  led_on(RED);
}

}
}

void led_on(unsigned char led)
{
  for (char i = 0; i <5; i++){
    if (i == led){
     digitalWrite(LED[i],HIGH);
    }
   }
    }
   }
}