Entendendo mais sobre VAR = 1 << 8

Ver o tópico anterior Ver o tópico seguinte Ir em baixo

Entendendo mais sobre VAR = 1 << 8

Mensagem por rogerin em Ter Ago 20, 2013 4:41 pm

Galera, estou fazendo um expansor de portas, tanto digital como analogico.. e o grande problema esta na programação..

Estou tentando criar uma função que eu vou dizer qual pino do expansor devo escrever HIGH para acionar apenas aquele pino especifico, sem afetar os outros que ja estejam high ou low.
Função Que estou usando.
Código:

void invertePino(int pinN, byte endereco){
  inicio = inicio ^ (1 << pinN);
  Wire.beginTransmission(endereco);
    Wire.write(inicio);
  Wire.endTransmission(endereco);
  delay(40);
}
Onde o endereço vai o byte do CI do expansor, no caso 0x20, ou 0x38, depende do expansor..
Alguem pode me ajudar nessa função para deixar um pino especifico HIGH ou LOW e os outros nao serem afetados??
Podem me ajudar tambem a criar uma função para leitura, retornando se o pino esta HIGH ou LOW?
O Expansor analogico deixo para depois, pois a logica teoricamente é a mesma.

rogerin

Mensagens : 6
Pontos : 10
Data de inscrição : 05/08/2013

Ver perfil do usuário

Voltar ao Topo Ir em baixo

Re: Entendendo mais sobre VAR = 1 << 8

Mensagem por Gregory em Qua Ago 21, 2013 2:40 pm

Bom cara! Quando o projeto estiver funcionando compartilha ele com a gente?

Fica a dica:

Para ativar apenas UM bit de um byte se usa a operação OU (or) com a máscara do bit. Vejamos:

(1 << bit) cria a máscara. Pois tu tem o valor 1 (00000001) deslocado de bit, ou seja, tu quer o bit 3 tu usa (1 << 3). Isso vai deslocar o um 3 vezes pra esquerda, ficando: (00001000).

Agora que temos a máscara do bit que queremos ligar, com a operação ou a gente modifica apenas quele bit do byte. Veja:

Código:

unsigned char a = 0b00110000; //valor aleatório pra mostrar o funcionamento
a = a | (1 << 3);                    //liga o bit 3 do byte sem mexer nos outros
Por que isso funciona? Faça a operação OU bit a bit com o byte e a máscara e perceba:

00110000
OU
00001000
=
00111000


Para desligar o bit tu faz a máscara contrária e usa a operação E (AND):

Código:

unsigned char a = 0b00111000; //valor para desmontração
a = a & ~(1 << 3);                 //desliga o bit 3 do byte
Faça a operação E bit a bit e veja como funciona:

00111000
E
11110111
=
00110111


Ficou claro? Acho que agora tu já sabe como fazer para ligar e para desligar. Uma função para ler o estado do pino pode ser:

Código:
unsigned char lePino(int pinN) {
     if (inicio & (1 << pinN)) return 1;
     return 0;
}
Se ficou alguma dúvida fala aí, abração!
avatar
Gregory
Admin

Mensagens : 59
Pontos : 88
Data de inscrição : 03/08/2013
Idade : 22

Ver perfil do usuário http://alleletronicsgr.forumeiros.com

Voltar ao Topo Ir em baixo

Re: Entendendo mais sobre VAR = 1 << 8

Mensagem por rogerin em Qua Ago 21, 2013 2:50 pm

Em outro forum um amigo ajudou a fazer uma função mais completa.. eu ainda não testei porque to ocupado fazendo o servidor websocket com ruby no raspberry pi, mas olha só como ficou, usando sua logica nele tb.

a função tem 3 parametros, (numero do pino, endereço do mux, status do high/low)

Código:
void I2C_IO_Write(int pinN, byte endereco,int status){
int aux = 0;
aux = 1 << pinN;
if(status == LOW){
inicio &= ~ aux;    //(LOW)
}
if (status == HIGH){
inicio |= aux;          //(HIGH)
}
  inicio = inicio ^ (1 pinN);
  Wire.beginTransmission(endereco);
    Wire.write(inicio);
  Wire.endTransmission(endereco);
  delay(40);
}

rogerin

Mensagens : 6
Pontos : 10
Data de inscrição : 05/08/2013

Ver perfil do usuário

Voltar ao Topo Ir em baixo

Re: Entendendo mais sobre VAR = 1 << 8

Mensagem por Gregory em Qua Ago 21, 2013 2:55 pm

Hmmm. Eu faria algo mais otimizado:

Código:
void I2C_IO_Write(int pinN, byte endereco,int status){
    inicio = inicio ^ (1 pinN);
    Wire.beginTransmission(endereco);
    Wire.write(inicio = (status == HIGH):(inicio | (1 << pinN)?(inicio & ~(1 << pinN));
    Wire.endTransmission(endereco);
    delay(40);
}
avatar
Gregory
Admin

Mensagens : 59
Pontos : 88
Data de inscrição : 03/08/2013
Idade : 22

Ver perfil do usuário http://alleletronicsgr.forumeiros.com

Voltar ao Topo Ir em baixo

Re: Entendendo mais sobre VAR = 1 << 8

Mensagem por rogerin em Qua Ago 21, 2013 2:59 pm

Vou testar depois, pois o objetivo é pegar esse codigo e fazer a mesma função na linguagem Ruby, pois todo o projeto vai rodar em ruby e o ruby que se comunica com outros CIs via I2C para expandir a sua capacidade, pois o Raspberry tem tem poucos pinos GPIO.

Ja criei uma player list no youtube para o curso de sobre Raspberry PI, baixei o programa camtasia para criar os videos, so não tenho um cronograma a seguir, preparar esse material requer tempo e conhecimento teorico nessas apresentações, ja dei aula, mas foi de forma bem tecnica nada de muita apresentação.

rogerin

Mensagens : 6
Pontos : 10
Data de inscrição : 05/08/2013

Ver perfil do usuário

Voltar ao Topo Ir em baixo

Re: Entendendo mais sobre VAR = 1 << 8

Mensagem por rogerin em Sab Ago 24, 2013 4:32 pm

Não compila..

Gregory escreveu:Hmmm. Eu faria algo mais otimizado:

Código:
void I2C_IO_Write(int pinN, byte endereco,int status){
    inicio = inicio ^ (1 pinN);
    Wire.beginTransmission(endereco);
    Wire.write(inicio = (status == HIGH):(inicio | (1 << pinN)?(inicio & ~(1 << pinN));
    Wire.endTransmission(endereco);
    delay(40);
}

rogerin

Mensagens : 6
Pontos : 10
Data de inscrição : 05/08/2013

Ver perfil do usuário

Voltar ao Topo Ir em baixo

Re: Entendendo mais sobre VAR = 1 << 8

Mensagem por Gregory em Sab Ago 24, 2013 5:17 pm

Opa. Tem um erro de sitaxe. Troca o ? Pelo : e vice-versa
avatar
Gregory
Admin

Mensagens : 59
Pontos : 88
Data de inscrição : 03/08/2013
Idade : 22

Ver perfil do usuário http://alleletronicsgr.forumeiros.com

Voltar ao Topo Ir em baixo

Re: Entendendo mais sobre VAR = 1 << 8

Mensagem por rogerin em Sab Ago 24, 2013 5:20 pm

Faltava outras coisas, mas olha ela ai corrigida.
Código:

void I2C_IO_Write(int pinN, byte endereco,int status){
    inicio = inicio ^ (1 << pinN);
    Wire.beginTransmission(endereco);
    Wire.write(inicio = (status == HIGH) ? (inicio | (1 << pinN)) :(inicio & ~(1 << pinN)));
    Wire.endTransmission(endereco);
    delay(40);
}

rogerin

Mensagens : 6
Pontos : 10
Data de inscrição : 05/08/2013

Ver perfil do usuário

Voltar ao Topo Ir em baixo

Re: Entendendo mais sobre VAR = 1 << 8

Mensagem por Conteúdo patrocinado


Conteúdo patrocinado


Voltar ao Topo Ir em baixo

Ver o tópico anterior Ver o tópico seguinte Voltar ao Topo

- Tópicos similares

 
Permissão deste fórum:
Você não pode responder aos tópicos neste fórum