TODOPIC
Microcontroladores PIC => Lenguaje Basic para microcontroladores PIC => Mensaje iniciado por: danelect23 en 05 de Septiembre de 2013, 23:44:44
-
Hola, Primero que nada me presento, soy Daniel, nuevo en el foro y estoy empezando con este tema de los pics.
Estoy trabajando con un pic16f84a, conecte un led en la pata RA0 y otro en RA1, un pulsador NA en RB0
Lo que quiero hacer es que RA0 destelle, pero al mantener activado el pulsador conectado en RB0 (configurado como entrada), que destelle el pulsador conectado en RA1. Logre hacer esto, pero quiero que al soltar el pulsador se apage RA1 y vuelva a destellar RA0. El que armé, al soltar el pulsador, sigue destellando RA1. Es decir no vuelve ala rutina inicial.
La idea ademas es aprender a usar un poco mas gosub y goto.
Uno de los programas que probe es el siguiente
pense que usando GOSUB O GOTO iba a lograr hacer lo que quiero, pero probe de varias formas y la verdad no se como se usan. Desde ya muchas gracias
TRISA=%00000
TRISB=%11111111
porta=0
portb=0
Led var porta.0
led2 var porta.1
Run1:
High led
Pause 1000
Low led
Pause 1000
if portb.0=0 then gosub run2
High led
Pause 1000
goto run1
run2:
high led2
pause 100
low led2
pause 100
high led2
pause 100
low led2
pause 100
goto run2
return `no me queda claro donde colocar return, y si goto run2 esta bien ahi o no.
End
-
Este código debería de hacer lo que quieres y es muy recomendable que evites usar los Gotos, a la larga es mejor.
El Goto solo se usa una sola vez para generar el bucle infinito en la subrutina principal main.
Es conveniente trabajar siempre desde una subrutina principal, a mi me gusta llamarla main.
TRISA = %00000
TRISB = %11111111
PORTA = 0
PORTB = 0
Symbol led = PORTA.0 'Asigna nombre al disositivo en Basic del PSI
Symbol led2 = PORTA.1
main: 'Subrutina principal
Gosub run1 'Salta a la subrutina run1 y vuelve
'Bucle tipo While/Wend
While PORTB.0 = 0 'Si RB0=0 ejecuta el código que hay entre While y Wend.
Gosub run2 'Salta a run2 y vuelve
Wend 'Mientras RB0=0 retorna al While inmediato superior.
Goto main 'Genera bucle infinito, solo para rutina principal.
End
'Subrutinas
run1: 'Nombre o etiqueta subrutina
High led 'Cambia el estado del pin configrado como digital
WaitMs 1000 'Hace una pausa de los mSeg. especificados en el Basic del PSI
Low led
WaitMs 1000
Return 'Fin subrutina run1, retorna a la línea siguiente despues del salto
run2: 'Nombre o etiqueta subrutina
High led2
WaitMs 100
Low led2
WaitMs 100
Return 'Fin subrutina run2, retorna a la línea siguiente despues del salto
-
Muchas gracias, compilado el error que me tiro fue en "WaitMs", los cambie todos por "pause", y no marco más error. lo cargué al pic y anda de diez.
una consulta..los gosub siempre deben ir asociados a un return?
en este caso "Gosub run1" va asociado al return de la subrutina run 1 y el "Gosub run2" al return de la subrutina run 2?
Habra forma que al pulsar el pulsador de RB0 la salida responda más rápidamente (vendria a ser la respuesta del pic, que sea mas rapida)? por que tarda un poco, en relación a lo que tarda el reset (si pongo la pata reset a masa, no tarda casi nada en reiniciarse)
Symbol led = PORTA.0 'Asigna nombre al disositivo en Basic del PSI
Symbol led2 = PORTA.1
main: 'Subrutina principal
'Salta a la subrutina run1 y vuelve
'Bucle tipo While/Wend
While PORTB.0 = 0 'Si RB0=0 ejecuta el código que hay entre While y Wend.
Gosub run2 'Salta a run2 y vuelve
Wend 'Mientras RB0=0 retorna al While inmediato superior.
Goto main 'Genera bucle infinito, solo para rutina principal.
End
'Subrutinas
run1: 'Nombre o etiqueta subrutina
High led 'Cambia el estado del pin configrado como digital
pause 1000 'Hace una pausa de los mSeg. especificados en el Basic del PSI
Low led
pause 1000
return 'Fin subrutina run1, retorna a la línea siguiente despues del salto
run2: 'Nombre o etiqueta subrutina
High led2
pause 100
Low led2
pause 100
return 'Fin subrutina run2, retorna a la línea siguiente despues del salto
-
hola, el tutorial que decis es en ensamblador no? Por ahora me voy a quedar con PBP, de a poco voy a aprender ensamblador, que me parece bastante mas complejo. Gracias
-
Cada Gosub tiene su Return; Return marca el final de la subrutina y Gosub si necesita un argumento que es un nombre o etiqueta donde debe saltar.
-
Para dar agilidad a los periféricos y al programa en general hay que dejar de utilizar los Pause, en mi caso Waitms. De echo pasa lo mismo que con el Goto, no se utilizan.
'Practicas para la introducción a las bases de tiempos (sin usar las interrupciones).
'Ejemplo para simulador
Define CLOCK_FREQUENCY = 4 'Se trabaja a 4Mhz
AllDigital 'Puerto A se utilizara como digital
TRISB.0 = 1 'Input
TRISA.0 = 0 'Output
TRISA.1 = 0 'Output
Symbol led = PORTA.0 'Asigna nombre al disositivo en Basic del PSI
Symbol led2 = PORTA.1
Call _btreset()
main: 'Subrutina principal
'Control tecla y parpadeo led2
If RB0 = 0 Then Gosub run2 'Salta a la subrutina
If RB0 = 1 Then led2 = 0 'Apaga led contrario
'Control tecla y parpadeo led
If RB0 = 1 Then Gosub run1 'Salta a la subrutina
If RB0 = 0 Then led = 0 'Apaga led contrario
Call _btcall() 'Actualiza las bases de tiempos
Goto main 'Genera bucle infinito, solo para rutina principal.
End
'Subrutinas
run1: 'Nombre o etiqueta subrutina
If _btimer.1 = 1 Then
Call _btsetup(1, 1000)
Toggle led 'Invierte el estado del pin configrado como digital
Endif
Return 'Fin subrutina run1, retorna a la línea siguiente despues del salto
run2: 'Nombre o etiqueta subrutina
If _btimer.0 = 1 Then
Call _btsetup(0, 100)
Toggle led2
Endif
Return 'Fin subrutina run2, retorna a la línea siguiente despues del salto
'**********************************************************
'Funciones para el control de hasta 8 bases de tiempos: _btimer.0 a _btimer.7
'**********************************************************
'Función principal las bases de tiempos:
'_bt = indica la base de tiempos para configurar
'_waitms = tiempo que contará la base de tiempos seleccionada con _bt
'_setup = operación a realizar con la base de tiempos indicada por _bt
Function _btimer(_bt As Byte, _waitms As Word, _setup As Byte) As Byte
Dim _cont(7) As Word 'Numero de contadores, tantos como bases de tiempos
If _setup = 1 Then _btimer = 255 'Configura las bases de tiempos como terminadas o desbordadas
''Recarga las bases de tiempos con el tiempo a contar y las activa
If _setup = 2 Then
If _bt = 0 Then
_cont(0) = _waitms
_btimer.0 = 0
Endif
If _bt = 1 Then
_cont(1) = _waitms
_btimer.1 = 0
Endif
If _bt = 2 Then
_cont(2) = _waitms
_btimer.2 = 0
Endif
If _bt = 3 Then
_cont(3) = _waitms
_btimer.3 = 0
Endif
Endif
If _setup = 0 Then
'Contadores de las bases de tiempos, descontando
If _cont(0) > 0 Then _cont(0) = _cont(0) - 1
If _cont(1) > 0 Then _cont(1) = _cont(1) - 1
If _cont(2) > 0 Then _cont(2) = _cont(2) - 1
If _cont(3) > 0 Then _cont(3) = _cont(3) - 1
'Estado de las bases de tiempos, terminaron de contar
If _cont(0) = 0 Then _btimer.0 = 1
If _cont(1) = 0 Then _btimer.1 = 1
If _cont(2) = 0 Then _btimer.2 = 1
If _cont(3) = 0 Then _btimer.3 = 1
WaitMs 1 'Tiempo patron
Endif
End Function
'Funciones auxiliares para el control de las bases de tiempos:
'********************************************************
'Actualiza las bases de tiempos.
Proc _btcall()
Call _btimer(0, 0, 0)
End Proc
'Recarga las bases de tiempos.
Proc _btsetup(_bt As Byte, _waitms As Word)
Call _btimer(_bt, _waitms, 2)
End Proc
'Inicializa las bases de tiempos, todas desbordadas.
Proc _btreset()
Call _btimer(0, 0, 1)
End Proc
-
bueno, voy a seguir investigando y armando circuitos. Un millón de gracias por la ayuda que me diste. ((:-))