Autor Tema: Ayuda con modulo CCP y ccs  (Leído 6854 veces)

0 Usuarios y 1 Visitante están viendo este tema.

Desconectado RALF2

  • Moderadores
  • PIC24H
  • *****
  • Mensajes: 2060
Ayuda con modulo CCP y ccs
« en: 29 de Diciembre de 2010, 22:20:59 »
Que tal amigos!
Tengo un problemita a ver si me pueden ayudar  :mrgreen:
Estoy utilizando un pic18f252 @ 10MHZ y el ccs, el proyecto consiste en hacer un programa para manejar un servo motor por medio de un potenciometro conectado al adc del pic.
El programa consiste en utilizar el timer1 con interrupcion cada 20ms, este marca el periodo.
Y el modulo CCP1 para controlar el tiempo en que la señal esta en ON.
En principio todo funciona bien, en cuanto a la interrupcion y el modulo ccp, pero el valor que se carga en la variable ccp1, la cual controla el tiempo en que la señal esta en on, la quiero variar con el adc del pic  :?
Los valores calculados para el servo que usare son: 64035 para que el servo se vaya a cero grados y 59535 para que el servo se vaya a 180 grados, estos valores deben cargarse en la variable ccp1.
El adc a utilizar varia de 0 a 1023 (10bits).
Alguna idea de como puedo hacer esto?


Saludos

Desconectado MLO__

  • Colaborador
  • DsPIC33
  • *****
  • Mensajes: 4581
Re: Ayuda con modulo CCP y ccs
« Respuesta #1 en: 29 de Diciembre de 2010, 22:39:43 »
Hola.

Para ello creo que hay una función (set_pwm_duty()), pero no se si sea eso lo que buscas ...  :?

No se puede asignar directamente en CCP_1?

Saludos
El papel lo aguanta todo

Desconectado jhozate

  • Colaborador
  • PIC24H
  • *****
  • Mensajes: 1698
Re: Ayuda con modulo CCP y ccs
« Respuesta #2 en: 29 de Diciembre de 2010, 23:13:11 »
el pwm en ese pic no es de 16bit?
Ser Colombiano es un Premio, Saludos desde CALI-COLOMBIA

Desconectado RALF2

  • Moderadores
  • PIC24H
  • *****
  • Mensajes: 2060
Re: Ayuda con modulo CCP y ccs
« Respuesta #3 en: 29 de Diciembre de 2010, 23:57:56 »
Que tal amigos!
bueno lo que quiero es que cuando el adc me cargue 0, en la variable ccp_1 sea igual a por ejemplo 59535 y cuando el adc tenga 1023 la variable ccp_1 tenga ahora 64035.
No le paren al resto  :D

jhozate el pwm es de 10bits
« Última modificación: 29 de Diciembre de 2010, 23:59:57 por RALF2 »

Desconectado AngelGris

  • Colaborador
  • PIC24H
  • *****
  • Mensajes: 2480
Re: Ayuda con modulo CCP y ccs
« Respuesta #4 en: 30 de Diciembre de 2010, 00:47:45 »
  Yo creo que se debería emplear la ecuación de una recta que pasa por dos puntos. Y = aX + b
Tomamos como "X" el valor leído del ADC. "Y" serían los valores que querés que tome el módulo CCP.

  Para el caso que "X" valga 0, la fórmula queda "Y" = (a * 0) + b --> 59535 = (a * 0) + b --> b = 59535. Ya tenemos despejado el valor de b.
  Ahora nos ocupamos del otro caso ("X" valiendo 1023) Y = aX + b --> Y = (a * 1023) + 59535 --> 64035 = (a * 1023) + 59535 --> 64035 - 59535 = (a * 1023) --> 4500 = (a * 1023) --> 4500/1023 = a --> a es aproximadamente 4.3988.

  Para corroborar el resultado podemos suponer un punto intermedio del pote... y = aX + b --> Y = (4.3988 * 511) + 59535 -->
Y = 2247.7868 + 59535 --> Y = 61782.7868. Y corroboramos el valor haciendo el promedio de los dos valores que vos querías
Y = (64035 + 59535) / 2 --> Y = 123570 / 2 --> Y = 61785
Valor entero calculado de punto medio      61785
Valor entero con el ADC entregando 511   61782
De vez en cuando la vida
nos besa en la boca
y a colores se despliega
como un atlas

Desconectado RALF2

  • Moderadores
  • PIC24H
  • *****
  • Mensajes: 2060
Re: Ayuda con modulo CCP y ccs
« Respuesta #5 en: 30 de Diciembre de 2010, 01:21:41 »
Correcto angelgris le diste cerquitica  :mrgreen:
Solo falta implementar eso en el pic con ccs como lo harias? alli estas utilizando punto flotante y los registros del pic operan con numeros enteros en este caso el ccp_1 opera a 16bits  :shock:

Como seria la formula que deberia colocar en ccs para implementar lo que brillantemente deducistes  :mrgreen:

Saludos

Desconectado AngelGris

  • Colaborador
  • PIC24H
  • *****
  • Mensajes: 2480
Re: Ayuda con modulo CCP y ccs
« Respuesta #6 en: 30 de Diciembre de 2010, 09:48:11 »
  No sé como sería en CCS, pero en ANSI C hay que hacer casting. Básicamente sería algo así...

 
Código: C
  1. void main(void)
  2. {
  3.   int valor_adc;
  4.   int valor_ccp;
  5.  
  6.   while (1)
  7.   {
  8.     valor_adc = readadc();
  9.     valor_ccp = (int)((4.3988 * valor_adc) + 59535);
  10.   }
  11. }

  Fijate que pongo int entre paréntesis antes de la cuenta. Eso indica que se trate el resultado como un valor entero, y luego se almacena en la variable "valor_ccp"
De vez en cuando la vida
nos besa en la boca
y a colores se despliega
como un atlas

Desconectado MLO__

  • Colaborador
  • DsPIC33
  • *****
  • Mensajes: 4581
Re: Ayuda con modulo CCP y ccs
« Respuesta #7 en: 30 de Diciembre de 2010, 11:55:07 »
No tocaría hacer el casting con float? y de ahí cargarlo a CCP_1.

Saludos
El papel lo aguanta todo

Desconectado AngelGris

  • Colaborador
  • PIC24H
  • *****
  • Mensajes: 2480
Re: Ayuda con modulo CCP y ccs
« Respuesta #8 en: 30 de Diciembre de 2010, 11:59:26 »
No tocaría hacer el casting con float? y de ahí cargarlo a CCP_1.

Saludos

  Ah, que duda que me generaste.... Creo que no, porque si yo trato a la cuenta como FLOAT y lo intento guardar en una variable INT debería generar un error porque son distintos tipos de datos.

  Voy a probar....
De vez en cuando la vida
nos besa en la boca
y a colores se despliega
como un atlas

Desconectado MLO__

  • Colaborador
  • DsPIC33
  • *****
  • Mensajes: 4581
Re: Ayuda con modulo CCP y ccs
« Respuesta #9 en: 30 de Diciembre de 2010, 12:01:38 »
Hola.

Es que las variables son int (que deberían ser long) pero la operación es la que se hace como si fueran float (para no perder exactitud), si haces las operaciones haciendo el casting como int o long, te va a dar cero .... porque estas usando punto flotante no?

Saludos
El papel lo aguanta todo

Desconectado AngelGris

  • Colaborador
  • PIC24H
  • *****
  • Mensajes: 2480
Re: Ayuda con modulo CCP y ccs
« Respuesta #10 en: 30 de Diciembre de 2010, 12:16:01 »
  Yo creo que la operación se hace como float (porque hay involucrado un operando de ese tipo).

  Esto es lo que encontré en internet al respecto "En programación, un casting (o cast) sirve para cambiar el tipo de dato del valor resultante de una expresión."

  Yo entiendo que si una expresión da un float, pero le hago el cast como int voy a tener el resultado entero de dicha operación... A ver si con un ejemplo me explico mejor.... A = 11/2 --> A = 5.5 al hacerlo con cast sería A = (int) (11/2) --> A = 5. O sea que en A tengo la parte entera del resultado.

  Lo tengo así en un frecuencímetro y me funcionaba bien... "Frecuencia = (int) (2.5e6/Periodo);"
De vez en cuando la vida
nos besa en la boca
y a colores se despliega
como un atlas

Desconectado RALF2

  • Moderadores
  • PIC24H
  • *****
  • Mensajes: 2060
Re: Ayuda con modulo CCP y ccs
« Respuesta #11 en: 30 de Diciembre de 2010, 12:45:45 »
Ok amigos excelente analisis algelgris!
Solo unos detallitos que hay que afinar  :mrgreen:

La formula seria:  ccp_1= (long)(read_adc()*4.3988) + 59535;
Claro el unico problema esta en que al pasar de float a long se perderian unos decimales que alterarian un poco los resultados  :shock:

Pero bueno es lo mas cercano que podemos hacer con el metodo empleado  :mrgreen:
Mlo__ la variable tipo ccp_1 es de tipo long como dices, por lo que si le  cargas un float este te truncara los decimales y el error que obtendrias seria mayor.
Es mejor utilizar float para hacer los calculos y luego pasar ese valor a long como lo coloco en la formula.  :mrgreen:


Desconectado AngelGris

  • Colaborador
  • PIC24H
  • *****
  • Mensajes: 2480
Re: Ayuda con modulo CCP y ccs
« Respuesta #12 en: 30 de Diciembre de 2010, 12:59:59 »
  Y si.... siempre se va a perder algo de precisión al perder los decimales. También he de notar entrar en la rutina de interrupción lleva más tiempo en C que en ASM, así que ahí también se está introduciendo un error (el cual se puede compensar alterando levemente el valor que se almacene en CCP).

  Yo traté la variable como INT porque para HiTech, una variable de 16 bits es int. No sé para CCS. En HiTech el tipo long es de 32 bits
De vez en cuando la vida
nos besa en la boca
y a colores se despliega
como un atlas

Desconectado MLO__

  • Colaborador
  • DsPIC33
  • *****
  • Mensajes: 4581
Re: Ayuda con modulo CCP y ccs
« Respuesta #13 en: 30 de Diciembre de 2010, 13:07:44 »

Estoy utilizando un pic18f252 @ 10MHZ y el ccs, el proyecto consiste en hacer un programa para manejar un servo motor por medio de un potenciometro conectado al adc del pic.


Raro, yo he hecho lo que digo para el velocímetro:

Código: [Seleccionar]
Variable.Velocidad= ((float)(Variable.Metros*FactorVelocidad)/(float)(Variable.SetPointPulsos))/((float)(CCP_1*0.0000016)+Timer.Desbordes);


Variable.Velocidad es del tipo char y todas las otras variables son diferentes a float. Si usaba el casting (long) ... me daba cero ....

Ya probaras y nos diras tus resultados RALF.

Un saludo
El papel lo aguanta todo

Desconectado AngelGris

  • Colaborador
  • PIC24H
  • *****
  • Mensajes: 2480
Re: Ayuda con modulo CCP y ccs
« Respuesta #14 en: 30 de Diciembre de 2010, 13:49:14 »
  Sí MLO__, así como lo ponés vos lo que hacés es que se trate como FLOAT a cada argumento. Y tal vez el resultado es "casteado" implícitamente a char por el compilador.

  Hice la prueba de poner -tomo como ejemplo la línea que puse de mi frecuencímetro- "Frecuencia = (float) (2.5e6/Periodo);" y el compilador arrojo un "warning" diciendo que había una conversión implícita de float a int. Tal vez -siguiendo con la línea de mi ejemplo- debería poner algo así "Frecuencia = (int) (2.5e6/(float)Periodo)". Así la división se hace entre dos tipos float y luego todo el resultado es "casteado" a int.
De vez en cuando la vida
nos besa en la boca
y a colores se despliega
como un atlas