# Contador 0-9 en CCS compiler



## DanNeil (Dic 20, 2010)

Buenas tardes amigos.
He recibido ayuda de ustedes muchas veces, y ahora a pesar de que no es gran cosa, y ya que hasta ahora estoy aprendiendo, les adjunto este programa de un contador 0-9 con el PIC16F84A.
Saludos a todos.

```
#include <16f84a.h>  // pic escogido
#use delay(clock=4000000) //cristal de 4Mhz
#fuses xt,nowdt,noprotect,noput // sin esto no arranca:trabajar con cristal, no protegido con clave..etc
#use standard_io(b)           //puerto b como entrda o salida estándar


int conteo=0;// el conteo inicia en 0
byte display[10]={0x3f,0x06,0x5b,0x4f,0x66,0x6d,0x7d,0xa7,0x7f,0x6f};/* saca por el puerto
                                                                      e ilumina los segmentos para ver 0-9     
                                                                     ya saben, RB0a A,...RB6a G y el punto no se conecta.*/
           
                        

void main(void){ 
do{
if(input(pin_a0)){         // si el pin RA0 está en alto
while(input(pin_a0));     //se queda en esta línea mientras RA0 esté en alto
delay_ms(20);       //luego al soltar el pulsador (RA0 ya no está en alto, pero ya entró a la rutina)hace un antirebote
if(conteo>9)          //Este es el reinicio, si llega a 9 y quiere subir, pasa a 0 de nuevo
conteo=0;             
output_b(display[conteo]);    /*como conteo cuenta 0-9, cada vez que cuenta, 
                             se escoge un valor del corchete [10] que es una matriz que arroja
                             valores según la vaiable que cuenta (conteo 0-9 10 valores) y se saca por el puerto B */
                             
conteo++;                    //y por cada pulso hay un incremento
}


}
while(1);         //esto hace un bucle sin fin, o sea que se repite siempre.
} 

/* en el simulador proteus verás que hasta no soltar el pulsador, no hay incremento
 por la condición while de la línea 17*/
```


----------



## KarlosDC23 (Mar 6, 2015)

Hace poco empece a estudiar los PIC's y quería hacer un Contador que me  contara de 0 a 9 en un display-catodo común. Sé que en varias partes hay  ejemplos de como hacer uno (incluso los hay en este foro) pero quiero  hacer uno a mi manera, aunque el código que he hecho es demasiado básico  
	

	
	
		
		

		
			





  . Lo que hice fue crear una variable 'carga' que aumenta su valor en 1  cada vez que se active el puerto A0 (pulsador), y mediante un _switch _arrojar las salidas (los puertos B0 a B6) al display las cuales dependen del valor de 'carga'.

Cuando  hago correr el código en Proteus, las salidas de todos los puertos B  arrojan cualquier valor...Alguien podría decirme cual es el problema?  creo que tiene que ver con el comando Switch :/
(Adjunto código y circuito en proteus):







```
#include <16F84A.h>
#use delay (clock=4000000)
#fuses XT,NOWDT,NOPUT,NOPROTECT
#use fast_io(B)

void main(){

set_tris_a (0x1F); //se definen todos los puertos 'a' como entradas
set_tris_b (0x00); //se definen todos los puertos 'b' como salidas

while(true){

int carga=0;

if (input (pin_A0)){ // si el pin A0 esta en 1 lógico.
carga++; //aumenta el contador de la variable 'carga' en 1
delay_ms(100); //retardo de 100 milisegundos
}

while ((carga>=0)&&(carga<=9)){

switch (carga){

case 0:
output_high(pin_b0);
output_high(pin_b1);
output_high(pin_b2);
output_high(pin_b3);
output_high(pin_b4);
output_high(pin_b5);
output_low(pin_b6);
case 1:
output_low(pin_b0);
output_high(pin_b1);
output_high(pin_b2);
output_low(pin_b3);
output_low(pin_b4);
output_low(pin_b5);
output_low(pin_b6);
case 2:
output_high(pin_b0);
output_high(pin_b1);
output_low(pin_b2);
output_high(pin_b3);
output_high(pin_b4);
output_low(pin_b5);
output_high(pin_b6);
case 3:
output_high(pin_b0);
output_high(pin_b1);
output_high(pin_b2);
output_high(pin_b3);
output_low(pin_b4);
output_low(pin_b5);
output_high(pin_b6);
case 4:
output_low(pin_b0);
output_high(pin_b1);
output_high(pin_b2);
output_low(pin_b3);
output_low(pin_b4);
output_high(pin_b5);
output_high(pin_b6);
case 5:
output_high(pin_b0);
output_low(pin_b1);
output_high(pin_b2);
output_high(pin_b3);
output_low(pin_b4);
output_high(pin_b5);
output_high(pin_b6);
case 6:
output_high(pin_b0);
output_low(pin_b1);
output_high(pin_b2);
output_high(pin_b3);
output_high(pin_b4);
output_high(pin_b5);
output_high(pin_b6);
case 7:
output_high(pin_b0);
output_high(pin_b1);
output_high(pin_b2);
output_low(pin_b3);
output_low(pin_b4);
output_low(pin_b5);
output_low(pin_b6);
case 8:
output_high(pin_b0);
output_high(pin_b1);
output_high(pin_b2);
output_high(pin_b3);
output_high(pin_b4);
output_high(pin_b5);
output_high(pin_b6);
case 9:
output_high(pin_b0);
output_high(pin_b1);
output_high(pin_b2);
output_low(pin_b3);
output_low(pin_b4);
output_high(pin_b5);
output_high(pin_b6);
}
}
}
}
```


----------



## MrAlphonse (Mar 7, 2015)

No manejo ese lenguaje para Pic, pero no hacen falta breaks al final de cada case? Y cuando saldra del ultimo ciclo while si "carga" nunca rompera ese while? Creo que esos son tus dos principales problemas.


----------



## miglo (Mar 7, 2015)

Prueba limpiando el puerto B con output_b(0x00);


----------



## ferfila20 (Mar 7, 2015)

Hola que tal amigo, cheque tu codigo y realice los siguientes cambios. 

Saludos!


```
#include <16F84A.h>
#use delay (clock=4000000)
#fuses XT,NOWDT,NOPUT,NOPROTECT
#use fast_io(B)
int carga=0;
void main(){

set_tris_a (0x1F); //se definen todos los puertos 'a' como entradas
set_tris_b (0x00); //se definen todos los puertos 'b' como salidas

for(;;){
if (input (pin_A0)==1){ // si el pin A0 esta en 1 lógico.
delay_ms(150);
carga++; 
}
   if(carga>9){
   carga=0;
   
}

if(carga==0){
output_high(pin_b0);
output_high(pin_b1);
output_high(pin_b2);
output_high(pin_b3);
output_high(pin_b4);
output_high(pin_b5);
output_low(pin_b6);}
if(carga==1){
output_low(pin_b0);
output_high(pin_b1);
output_high(pin_b2);
output_low(pin_b3);
output_low(pin_b4);
output_low(pin_b5);
output_low(pin_b6);}

if(carga==2){
output_high(pin_b0);
output_high(pin_b1);
output_low(pin_b2);
output_high(pin_b3);
output_high(pin_b4);
output_low(pin_b5);
output_high(pin_b6);
}
if(carga==3){
output_high(pin_b0);
output_high(pin_b1);
output_high(pin_b2);
output_high(pin_b3);
output_low(pin_b4);
output_low(pin_b5);
output_high(pin_b6);
}
if(carga==4){
output_low(pin_b0);
output_high(pin_b1);
output_high(pin_b2);
output_low(pin_b3);
output_low(pin_b4);
output_high(pin_b5);
output_high(pin_b6);
}
if(carga==5){
output_high(pin_b0);
output_low(pin_b1);
output_high(pin_b2);
output_high(pin_b3);
output_low(pin_b4);
output_high(pin_b5);
output_high(pin_b6);
}
if(carga==6){
output_high(pin_b0);
output_low(pin_b1);
output_high(pin_b2);
output_high(pin_b3);
output_high(pin_b4);
output_high(pin_b5);
output_high(pin_b6);
}
if(carga==7){
output_high(pin_b0);
output_high(pin_b1);
output_high(pin_b2);
output_low(pin_b3);
output_low(pin_b4);
output_low(pin_b5);
output_low(pin_b6);
}
if(carga==8){
output_high(pin_b0);
output_high(pin_b1);
output_high(pin_b2);
output_high(pin_b3);
output_high(pin_b4);
output_high(pin_b5);
output_high(pin_b6);
}
if(carga==9){
output_high(pin_b0);
output_high(pin_b1);
output_high(pin_b2);
output_low(pin_b3);
output_low(pin_b4);
output_high(pin_b5);
output_high(pin_b6);
}
}
}
```


----------



## KarlosDC23 (Mar 7, 2015)

Gracias @ferfila20 !

Así funciona perfectamente, gracias!


----------



## ruben90 (Mar 10, 2015)

no es necesario tanto if o incluso el for en el codigo, solo configurar las salidas del pic segun el display y con un if y un contador es mas que suficiente.

*codigo*

unsigned short contador; // variable de 0-255, solo usa 1 bit, el int usa 2 bit
const unsigned short display7seg[]=
{
0X3F,0X06,0X5B,0X4F,0X66,0X6D,0X7D,0X07,0X7F,0X6F
};
void main(){
TRISA = 1; //puerto A como entrada
TRISB = 0; //puerto B como salida
while(1){
if(PORTA.F0 == 1){ //push-button en RA0
contador++;
delay_ms(100);
if(contador >= 10)contador = 0; //reinicio contador
}
PORTB = display7seg[contador]; //salida en el puerto B
delay_ms(100); //tiempo a convenir
}
}


----------



## ferfila20 (Mar 12, 2015)

Hola que tal ruben90, obviamente si es mejor el codigo que propones, pero en si me base en el codigo que el habia presentado con anterioridad.
El ciclo for esta haciendo la misma funcion que el while que esta en tu codigo. 
y bueno viendo tu codigo en esta parte


```
if(contador >= 10)contador = 0; //reinicio contador
}
```
para mi seria mejor ponerlo asi


```
if(contador >9)contador = 0; //reinicio contador
}
```
Creo que se ve mejor. 
oye una pregunta, en esta parte del codigo que presentas 
	
	



```
if(PORTA.F0 == 1){ //push-button en RA0
contador++;
delay_ms(100);
```
que significa el "F0" despues de "PORTA"

Saludos!


----------



## KarlosDC23 (Mar 12, 2015)

@ruben90
Se sabe que el código puede ser mas diminuto, pero cuando coloqué el código dije que estaba empezando con esto de los PIC's y que quería hacer un contador primitivo.
Saludos.


----------



## crazysound (Abr 16, 2017)

ferfila20 dijo:


> Hola que tal amigo, cheque tu codigo y realice los siguientes cambios.
> 
> Saludos!
> 
> ...



Hola ferfila20, necesito ayuda. He estado trabajando con este código que propusiste y ahora quiero hacer el puerto b con 2 salidas BCD para alimentar dos 4511 (BCD a 7SEG) y utilizarlos por separado, o sea, que cuenten uno por un pulso en a0 y el otro en b0, por ejemplo... Se podrá....

Adjunto el rar con los archivos Pic C Compiler y Proteus 8.1.

Muchas gracias a todos los que respondan con sugerencias.....

Saludos...


----------



## Saint_ (Abr 16, 2017)

crazysound aquí un ejemplo.

```
#include <16F84A.h>
#use delay (clock=4000000)
#fuses XT,NOWDT,NOPUT,NOPROTECT
#use fast_io(B)
#use fast_io(A)
void main()
{
   unsigned int8 digito1=0;
   unsigned int8 digito2=0;
   unsigned int8 puerto;
   unsigned int8 p1_anterior=1;
   unsigned int8 p2_anterior=1;
   output_b(0);
   set_tris_a (0x1F);//se definen todos los puertos 'a' como entradas
   set_tris_b (0x00);//se definen todos los puertos 'b' como salidas
   while(true)
   {
      puerto=input_a();    //lee el estado de puerto a
      if(!bit_test(puerto,0)&&(p1_anterior))//si cambìo de 1 a 0
      {
         if(++digito1==10)
         {
            digito1=0;
         }
      }
      if(!bit_test(puerto,1)&&(p2_anterior))//si cambìo de 1 a 0
      {
         if(++digito2==10)
         {
            digito2=0;
         }
      }
      p1_anterior=bit_test(puerto,0);
      p2_anterior=bit_test(puerto,1);
      output_b(digito2<<4|digito1);
      delay_ms(100);
   }
}
```


----------



## crazysound (Abr 17, 2017)

Hola Saint_, gracias!! 
Funciona sólo que los display arrancan en 1. No soy un experto en programación... 

Cómo hace para escribir los puertos? 

Saludos..


----------



## Saint_ (Abr 17, 2017)

Hola, debería iniciar en cero, fíjate que los pines A0 y A1 estén como en el esquema (con los pull-up) 
La clave de esto es que los valores de las cuentas están guardadas en variables diferentes _digito1_ y _digito2_ y al momento de escribir estos valores en el puerto solo se usa una rotación de bits y un enmascaramiento
_output_b(digito2<<4|digito1);_


----------

