Autor Tema: calcular pwm  (Leído 31644 veces)

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

Desconectado septiembre_negro

  • PIC18
  • ****
  • Mensajes: 310
calcular pwm
« en: 21 de Mayo de 2010, 14:29:15 »
Hola  
 Pues resulta que ya me líe al grado de no entender ni m%&%$%&.
Más que nada por que no e encontrado dos ejemplos que resuelvan el cálculo del pmw de la misma forma.
El ejemplo que mejor e entendido es que les pongo a continuación en cual tiene dos defectos el primero que al camarada que puso el ejemplo no le contestaron si su procedimiento  es correcto.
Segundo que en su ejerció sustituyo las literales por los valores por lo cual no termino de entender.
Así que si alguien puede decirme si el ejerció es correcto y cuales serian las formulas que utilizo. Se lo agradezco de antemano



aquí el ejemplo:
Citar
cristal del pic 4MHz, Preescaler 1:1, ciclo de trabajo del PWM 50% y frecuancia del PWM igual a 20KHz

Periodo PWM= 1/20KHz = 50us

Tosc= 1/ 4MHz =250ns

PR2= (50us/(4*250ns*1))-1 = 49

CTPWM 50%= Periodo PWM / 2 = 25us

CCPR1L:CCP1CON = 25us/(250ns*1) = 100

por lo tanto la configuración de esto es:

setup_ccp1(ccp_PWM);
setup_timer_2(t2_div_By_1,49,1);
set_pwm_duty(100);



Ahora suponiendo que el ejercicio es correcto y quisiera cambiar el siclo de trabajo del 50% al 75 por ciento que tendría  que hacer  en esta parte.
Citar

CTPWM 50%= Periodo PWM / 2 = 25us

De verdad que ya le busque y solo me enredo mas



Desconectado Mando31

  • PIC10
  • *
  • Mensajes: 32
Re: calcular pwm
« Respuesta #1 en: 23 de Mayo de 2010, 23:09:28 »
Te recomiendo ver el libro Compilador C CCS y Simulador Proteus Para Microcontroladores PIC, te dejo un MP, suerte.

Desconectado Mario

  • Colaborador
  • PIC24F
  • *****
  • Mensajes: 873
Re: calcular pwm
« Respuesta #2 en: 26 de Mayo de 2010, 12:06:39 »
Hola septiembre negro,

¿solucionaste tu problema?

No es muy complicado entender el funcionamiento, pero si debes especificar si utilizarás la resolución completa de 10 bits u ocho, el compilador de CCS no distingue, debes forzar a la variable o número para que lo tome de una u otra manera.
La buena administración es utilizar el sentido común y la regla de oro; aunque el sentido común no es tan común como quisiéramos que fuera y, quien tiene el oro, hace las reglas.
George Terry

"A loser will defeat a genius with hard work"
Rock Lee

Desconectado septiembre_negro

  • PIC18
  • ****
  • Mensajes: 310
Re: calcular pwm
« Respuesta #3 en: 26 de Mayo de 2010, 17:43:21 »
Hola septiembre negro,

¿solucionaste tu problema?

No es muy complicado entender el funcionamiento, pero si debes especificar si utilizarás la resolución completa de 10 bits u ocho, el compilador de CCS no distingue, debes forzar a la variable o número para que lo tome de una u otra manera.


Hola
Pues  ya me alcance el libro compilador ccs y simulación en proteus , pero sigo empelotado se tiran unas formulas que me marean  :shock: :shock:  agradecería si alguien puede explicarme el ejercicio que colgué.
Básicamente lo que intento es variar la velocidad de un motor   cambiando  el ciclo de trabajo al 20% ,50% ,75%.
Pero ahora si que no doy pie con bola  :? :?mientras unos ejercicios hablan de variar el ciclo de trabajo otros hablan de variar la frecuencia

Desconectado Mario

  • Colaborador
  • PIC24F
  • *****
  • Mensajes: 873
Re: calcular pwm
« Respuesta #4 en: 27 de Mayo de 2010, 07:12:46 »
Pues vamos viendo......



Supongamos que se desea una frecuencia de 1KHz a un ciclo de trabajo de 50% con una frecuencia del oscilador de 4MHz.


Lo primero es revisar la hoja de datos (en mi caso el 16F887 o cualquiera que tenga CCP).

Establece una fórmula
PWM Period = [(PR2)+ 1]•4•TOSC •(TMR2 Prescale Value)

Pero es menos complicado si se contempla en función de la frecuencia (recordar que f=1/t):
Fpwm=  [(Fosc)/(PR2+1)*(TMR2 Prescale Value)*(4)]

Lo que interesa es el PR2 ya que es el registro del periodo para la frecuencia (revisar fórmula de hoja de datos):
PR2= [(Fosc)/(Fpwm)*(TMR2 Prescale Value)*(4)]-1

PR2 debemos recordar que es de 8 bits, por lo que el valor máximo no debe exceder 255 (muy importante).


Si se desea 1KHz tenemos básicamente dos opciones:
  • 1.- Se cambia de frecuencia de oscilación (no recomendable, ya que todo el programa se altera)
  • 2.- Se cambia de preescalador para el Timer2


Si tomamos la segunda entonces tenemos tres opciones: 1, 4 y 16.

Con 1:
PR2= [(4MHz)/(1KHz)*(1)*(4)]-1
PR2=1000-1  <---bien importante no olvidarse del -1

PR2=999

Con 1 no sirve, ya que se pasa de los 8 bits.



Con 4:
PR2= [(4MHz)/(1KHz)*(4)*(4)]-1

PR2=249

Con 4 sirve.



Con 16:
PR2= [(4MHz)/(1KHz)*(16)*(4)]-1

PR2=62.5

Con 16 podría servir pero..... el registro no almacena decimales, solo enteros; lo anterior nos proporciona dos posibles caminos:
  • PR2=62
  • PR2=63

Si PR2=62, entonces la Fpwm será:
Fpwm=  [(Fosc)/(PR2+1)*(TMR2 Prescale Value)*(4)]
Fpwm=  [(4MHz)/(62+1)*(16)*(4)]
Fpwm=  992.0634 Hz

Lo anterior entrega un error de 0.8% aproximadamente.



Si PR2=63, entonces la Fpwm será:
Fpwm=  [(Fosc)/(PR2+1)*(TMR2 Prescale Value)*(4)]
Fpwm=  [(4MHz)/(63+1)*(16)*(4)]
Fpwm=  976.5625 Hz

Lo anterior entrega un error de 2.4% aproximadamente.



La ideal es PR2=249 con preescalador a 4; cabe señalar que solo estamos en la frecuencia.



Para el PWM es algo similar pero, el CCS utiliza funciones donde el comportamiento no es tan transparente como se desearía.


Recordar que
Pulse Width =(CCPRxL:CCPxCON<5:4>) •TOSC • (TMR2 Prescale Value)



y que

Duty Cycle Ratio= (CCPRxL:CCPxCON<5:4>)
                           --------------------------------
                                       4(PR2 + 1)


El ciclo de trabajo ya se conoce (es el deseado), por lo que interesa es el valor de CCPRxL:CCPxCON<5:4>. En C o en BASIC es relativamente sencillo colocar ese valor, en ensamblador no tanto. Lo anterior debido a que los bits 5 y 4 de CCPxCON son los de menor peso y se debe realizar un corrimiento con todo CCPRxL.


Aquí es donde se torna algo confuso (para la mayoría):

suponiendo un ciclo de trabajo de 50%, significa que el valor donde se repite el periodo (PR2+1) es 250, el valor medio sería 125, por lo que CCPRxL deberá tomar ese valor.
CCPRxL toma el valor ya que es el registro de mayor peso para el ciclo de trabajo, los otros dos bits no afectan.

Lo anterior es si deseas utilizar el PWM en "modo de 8 bits"  (no existe tal modo, pero trabaja asi). Si deseas utilizar los 10 bits de resolución, deberás utilizar esos dos bits de menor peso.

Esos dos bits de menor peso siempre producirán 4 combinaciones adicionales (00,01,10,11) a las 256 del CCPRxL y, como sabemos 10bits=1024. El máximo valor que tendrás será 1023.

Si PR2 es 249, y PR2+1 =250, entonces el valor para el ciclo de trabajo crece de 250 a 1000, dando 4 veces el original (debido a esos dos bits).

Aqui está la situación:
para utilizar los 10 bits de resolución el CCS debe saber que el parámetro de set_pwm_duty() es un entero de 16 bits (INT16 o LONG), de otra manera lo tomará como 8 bits (solo tomará el CCPRxL).

Coloca esto:
setup_ccp1(ccp_PWM);
setup_timer_2(t2_div_By_4,249,1);
set_pwm_duty(125);

Coloca esto:
setup_ccp1(ccp_PWM);
setup_timer_2(t2_div_By_4,249,1);
set_pwm_duty(500L);

Verás que no hay cambio.

Si tu micro cuenta con dos CCP, coloca uno con 125 y otro con 500.

Te mandaría la simulación en registros del MPLAB pero me son las 3:10 AM aquí y ya casi entro a trabajar.


Cualquier cosa estamos siguiendo el hilo.
La buena administración es utilizar el sentido común y la regla de oro; aunque el sentido común no es tan común como quisiéramos que fuera y, quien tiene el oro, hace las reglas.
George Terry

"A loser will defeat a genius with hard work"
Rock Lee

Desconectado septiembre_negro

  • PIC18
  • ****
  • Mensajes: 310
Re: calcular pwm
« Respuesta #5 en: 28 de Mayo de 2010, 11:30:43 »
Mas claro imposible   :-/ :-/ :-/ ;  de verdad te agradezco mucho, sobre todo por el tiempo que te as tomado en dar una explicación tan completa de seguro a alguien mas le servirá  ;-)

Desconectado septiembre_negro

  • PIC18
  • ****
  • Mensajes: 310
Re: calcular pwm
« Respuesta #6 en: 30 de Mayo de 2010, 18:03:18 »
Hola
Después de haber solucionado el problema de configurar el pwm, pues resulta que el motor pierde torque al conectar el motor directamente a vcc opera  de  forma correcta al aplicar el pwm la perdida de torque es tal que incluso el motor se puede detener con la mano .
No entiendo  cual pudiera ser el problema se entiende que a un pwm del 100% el motor debería estar a su máximo.
Un amigo me dice que a menor pwm mayor torque pero esto tampoco se cumple,
Estoy seguro que esta configurado correctamente ya que en el osciloscopio la señal que se observa  corresponde al duty_cicle que configuro 25% ,50%,100%.
Así que  lo único que se me ocurre es que estoy aplicando  mal el pwm al cto.
Estoy utilizando un l2724 como puente h y  para inyectar el pwm lo que ago es  aplicar el pwm a  la base de un  transistor de potencia que conecta y desconecta   12vcc que llegan  al l2724.
Cualquier sugerencia es bienvenida
 
« Última modificación: 30 de Mayo de 2010, 18:05:22 por septiembre_negro »

Desconectado japifer_22

  • PIC18
  • ****
  • Mensajes: 405
Re: calcular pwm
« Respuesta #7 en: 30 de Mayo de 2010, 19:17:45 »
hola septiembre_negro, bueno te comento, lo que puede pasarte son varias cosas;

primero alomejor tu motor no es del voltaje del cual le estas aplicando, en ocaciones suele suseder esto, por ejemplo si tienes un motor de 9V y le inyectas 12V en este caso te aumenta las RPM pero no el torque, por que este te desminuira.

segundo alomejor tu driver no tiene la corriente que requiere el motor.

alomejor estas aplicando un driver dañado.

lo otro que puede ser, es que la frecuencia del PWM no es la correcta para tu motor, y como saver cual es la mas indicada para esto??, bueno lo que yo hice en un momento dado y por la sujerencia de varios en este foro fue que a mas bajo empiesa a funcionar el motor del PWM va a ser mejor el decempeño del motor. por ejemplo le aplico 5 PWM de distintas frec, por ejemplo de 8KHz, 13KHz, 15KHz, 18KHz o 20KHz y los pruebo de a 1 con un duty cicle del 10% por ejmplo y veo si el motor me parte con alguna de estas frecuencias al 10% del duty y si es así, es la recomendada para tu motor.

de todas formas, te dejo una simulacion y el codigo, el cual hice para probar los PWM para unos motores que estoy usando. el programa que hice le puse 9 PWM diferentes con un rango de trabajo del 0 a 100%.
en la simulacion tambien te dejo un driver que uso yo para la parte de potencia del pic, en donde se conecta directo el motor.

bueno espero que te sirva de algo.

el codigo es este:

Código: [Seleccionar]
#include <16F873a.h>
#device adc=10
#FUSES NOWDT, HS, NOPUT, NOPROTECT, BROWNOUT, NOLVP, NOCPD, NOWRT
#use delay (clock=4000000) //Fosc=20Mhz
#define use_portb_lcd TRUE //definir portb lcd
#include<lcd420.c> //libreria manejo lcd de 20x4 modificada por suky para el puerto D
#use standard_io(A)
#use standard_io(C)

void frecuencia_20KHz(void);

void frecuencia_18KHz(void);

void frecuencia_16KHz(void);

void frecuencia_14KHz(void);

void frecuencia_12KHz(void);

void frecuencia_10KHz(void);

void frecuencia_8KHz(void);

void frecuencia_6KHz(void);

void frecuencia_5KHz(void);


int16 a;//variables para el PWM
int frecuencia,frec,b=20;
float c,e;


void main(){//programa principal
lcd_init();         //inicializa lcd

  while(true){
      if(!input(PIN_A0)){                  //¿se ha pulsado el boton?
         do{                           //SI -> eliminar...           
         }while(!input(PIN_A0));            //...rebotes del boton
     if(frecuencia<=9){
     frecuencia++;
     }}
      if(!input(PIN_A1)){                  //¿se ha pulsado el boton?
         do{                           //SI -> eliminar...           
         }while(!input(PIN_A1));            //...rebotes del boton
     if(frecuencia>=2){
     frecuencia--;
     }}
     lcd_gotoxy(1,1);
     printf(lcd_putc,"Escoja una frec ");
     lcd_gotoxy(1,2);
     printf(lcd_putc,"de PWM. opt 1-10");
     lcd_gotoxy(1,3);
     printf(lcd_putc,"Frec %i ",frecuencia);
     lcd_gotoxy(1,4);
     printf(lcd_putc,"                ");     
      if(!input(PIN_A2)){                  //¿se ha pulsado el boton?
         do{                           //SI -> eliminar...           
         }while(!input(PIN_A2));            //...rebotes del boton     
   frec=frecuencia;
      }
      else{
      frec=0;
      }
     
switch( frec )
   {
   case 1:
         lcd_gotoxy(1,1);
         printf(lcd_putc,"Frec de 20KHz");
         frecuencia_20KHz();
           break;
   case 2:
         lcd_gotoxy(1,1);
         printf(lcd_putc,"Frec de 18KHz");   
         frecuencia_18KHz();
           break;
   case 3:
         lcd_gotoxy(1,1);
         printf(lcd_putc,"Frec de 16KHz");   
         frecuencia_16KHz();
           break;
   case 4:
         lcd_gotoxy(1,1);
         printf(lcd_putc,"Frec de 14KHz");   
         frecuencia_14KHz();
           break;
   case 5:
         lcd_gotoxy(1,1);
         printf(lcd_putc,"Frec de 12KHz");   
         frecuencia_12KHz();
           break;
   case 7:
         lcd_gotoxy(1,1);
         printf(lcd_putc,"Frec de 10KHz");   
         frecuencia_10KHz();
           break;

   case 8:
         lcd_gotoxy(1,1);
         printf(lcd_putc,"Frec de 8KHz ");   
         frecuencia_8KHz();
           break;
   case 9:
         lcd_gotoxy(1,1);
         printf(lcd_putc,"Frec de 6KHz ");   
         frecuencia_6KHz();
           break;
   case 10:
         lcd_gotoxy(1,1);
         printf(lcd_putc,"Frec de 5KHz ");   
         frecuencia_5KHz();
           break;           

   } }
}

void frecuencia_20KHz(void){

   setup_ccp1(CCP_PWM); //ccp1 modo PWM
   setup_timer_2(T2_DIV_BY_1, 49, 1);
   
   a=20;   // punto medio del duty de 10 bits
   set_pwm1_duty(a);//duty cycle con una variable para variar el PWM
   
   while(TRUE){
   
      set_pwm1_duty(a);//duty cycle con una variable para variar el PWM

      if(!input(PIN_A0)){                  //¿se ha pulsado el boton?
         do{                           //SI -> eliminar...           
         }while(!input(PIN_A0));            //...rebotes del boton
     if(a<=198){
     a++;
     b++;
     }}
      if(!input(PIN_A1)){                  //¿se ha pulsado el boton?
         do{                           //SI -> eliminar...           
         }while(!input(PIN_A1));            //...rebotes del boton
     if(a>=2){
     a--;
     b--;
     }}
   
      lcd_gotoxy(1,2);
      printf(lcd_putc,"PWM  ");
      e=b;
      c=(e*100)/200;
      lcd_gotoxy(1,4);
      printf(lcd_putc,"PWM= %f ",c);   
     
      if(!input(PIN_A2)){                  //¿se ha pulsado el boton?
         do{                           //SI -> eliminar...           
         }while(!input(PIN_A2));            //...rebotes del boton
       
        break;
        }
   }
   
}


void frecuencia_18KHz(void){

   setup_ccp1(CCP_PWM); //ccp1 modo PWM
   setup_timer_2(T2_DIV_BY_1, 54, 1);
   
   a=20;   // punto medio del duty de 10 bits
   set_pwm1_duty(a);//duty cycle con una variable para variar el PWM
   
   while(TRUE){
   
      set_pwm1_duty(a);//duty cycle con una variable para variar el PWM

      if(!input(PIN_A0)){                  //¿se ha pulsado el boton?
         do{                           //SI -> eliminar...           
         }while(!input(PIN_A0));            //...rebotes del boton
     if(a<=220){
     a++;
     b++;
     }}
      if(!input(PIN_A1)){                  //¿se ha pulsado el boton?
         do{                           //SI -> eliminar...           
         }while(!input(PIN_A1));            //...rebotes del boton
     if(a>=2){
     a--;
     b--;
     }}
      lcd_gotoxy(1,2);
      printf(lcd_putc,"PWM2  ");
      e=b;
      c=(e*100)/222;
      lcd_gotoxy(1,4);
      printf(lcd_putc,"PWM= %f",c);     
      if(!input(PIN_A2)){                  //¿se ha pulsado el boton?
         do{                           //SI -> eliminar...           
         }while(!input(PIN_A2));            //...rebotes del boton
       
        break;
        }
}}

void frecuencia_16KHz(void){

   setup_ccp1(CCP_PWM); //ccp1 modo PWM
   setup_timer_2(T2_DIV_BY_1, 61, 1);
   
   a=20;   // punto medio del duty de 10 bits
   set_pwm1_duty(a);//duty cycle con una variable para variar el PWM
   
   while(TRUE){
   
      set_pwm1_duty(a);//duty cycle con una variable para variar el PWM

      if(!input(PIN_A0)){                  //¿se ha pulsado el boton?
         do{                           //SI -> eliminar...           
         }while(!input(PIN_A0));            //...rebotes del boton
     if(a<=248){
     a++;
     b++;
     }}
      if(!input(PIN_A1)){                  //¿se ha pulsado el boton?
         do{                           //SI -> eliminar...           
         }while(!input(PIN_A1));            //...rebotes del boton
     if(a>=2){
     a--;
     b--;
     }}
      lcd_gotoxy(1,2);
      printf(lcd_putc,"PWM3  ");
      e=b;
      c=(e*100)/250;
      lcd_gotoxy(1,4);
      printf(lcd_putc,"PWM= %f",c);
      if(!input(PIN_A2)){                  //¿se ha pulsado el boton?
         do{                           //SI -> eliminar...           
         }while(!input(PIN_A2));            //...rebotes del boton
       
        break;
        }
}}

void frecuencia_14KHz(void){

   setup_ccp1(CCP_PWM); //ccp1 modo PWM
   setup_timer_2(T2_DIV_BY_1, 70, 1);
   
   a=20;   // punto medio del duty de 10 bits
   set_pwm1_duty(a);//duty cycle con una variable para variar el PWM
   
   while(TRUE){
   
      set_pwm1_duty(a);//duty cycle con una variable para variar el PWM

      if(!input(PIN_A0)){                  //¿se ha pulsado el boton?
         do{                           //SI -> eliminar...           
         }while(!input(PIN_A0));            //...rebotes del boton
     if(a<=283){
     a++;
     b++;
     }}
      if(!input(PIN_A1)){                  //¿se ha pulsado el boton?
         do{                           //SI -> eliminar...           
         }while(!input(PIN_A1));            //...rebotes del boton
     if(a>=2){
     a--;
     b--;
     }}
      lcd_gotoxy(1,2);
      printf(lcd_putc,"PWM4  ");
      e=b;
      c=(e*100)/285;
      lcd_gotoxy(1,4);
      printf(lcd_putc,"PWM= %f",c);     
      if(!input(PIN_A2)){                  //¿se ha pulsado el boton?
         do{                           //SI -> eliminar...           
         }while(!input(PIN_A2));            //...rebotes del boton
       
        break;
        }
}}

void frecuencia_12KHz(void){

   setup_ccp1(CCP_PWM); //ccp1 modo PWM
   setup_timer_2(T2_DIV_BY_1, 82, 1);
   
   a=20;   // punto medio del duty de 10 bits
   set_pwm1_duty(a);//duty cycle con una variable para variar el PWM
   
   while(TRUE){
   
      set_pwm1_duty(a);//duty cycle con una variable para variar el PWM

      if(!input(PIN_A0)){                  //¿se ha pulsado el boton?
         do{                           //SI -> eliminar...           
         }while(!input(PIN_A0));            //...rebotes del boton
     if(a<=331){
     a++;
     b++;
     }}
      if(!input(PIN_A1)){                  //¿se ha pulsado el boton?
         do{                           //SI -> eliminar...           
         }while(!input(PIN_A1));            //...rebotes del boton
     if(a>=2){
     a--;
     b--;
     }}
      lcd_gotoxy(1,2);
      printf(lcd_putc,"PWM5  ");
      e=b;
      c=(e*100)/333;
      lcd_gotoxy(1,4);
      printf(lcd_putc,"PWM= %f",c);
      if(!input(PIN_A2)){                  //¿se ha pulsado el boton?
         do{                           //SI -> eliminar...           
         }while(!input(PIN_A2));            //...rebotes del boton
       
        break;
        }
}}

void frecuencia_10KHz(void){

   setup_ccp1(CCP_PWM); //ccp1 modo PWM
   setup_timer_2(T2_DIV_BY_1, 99, 1);
   
   a=20;   // punto medio del duty de 10 bits
   set_pwm1_duty(a);//duty cycle con una variable para variar el PWM
   
   while(TRUE){
   
      set_pwm1_duty(a);//duty cycle con una variable para variar el PWM

      if(!input(PIN_A0)){                  //¿se ha pulsado el boton?
         do{                           //SI -> eliminar...           
         }while(!input(PIN_A0));            //...rebotes del boton
     if(a<=398){
     a++;
     b++;
     }}
      if(!input(PIN_A1)){                  //¿se ha pulsado el boton?
         do{                           //SI -> eliminar...           
         }while(!input(PIN_A1));            //...rebotes del boton
     if(a>=2){
     a--;
     b--;
     }}
      lcd_gotoxy(1,2);
      printf(lcd_putc,"PWM7  ");
      e=b;
      c=(e*100)/400;
      lcd_gotoxy(1,4);
      printf(lcd_putc,"PWM= %f",c);     
      if(!input(PIN_A2)){                  //¿se ha pulsado el boton?
         do{                           //SI -> eliminar...           
         }while(!input(PIN_A2));            //...rebotes del boton
       
        break;
        }
}}

void frecuencia_8KHz(void){

   setup_ccp1(CCP_PWM); //ccp1 modo PWM
   setup_timer_2(T2_DIV_BY_1, 124, 1);
   
   a=20;   // punto medio del duty de 10 bits
   set_pwm1_duty(a);//duty cycle con una variable para variar el PWM
   
   while(TRUE){
   
      set_pwm1_duty(a);//duty cycle con una variable para variar el PWM

      if(!input(PIN_A0)){                  //¿se ha pulsado el boton?
         do{                           //SI -> eliminar...           
         }while(!input(PIN_A0));            //...rebotes del boton
     if(a<=498){
     a++;
     b++;
     }}
      if(!input(PIN_A1)){                  //¿se ha pulsado el boton?
         do{                           //SI -> eliminar...           
         }while(!input(PIN_A1));            //...rebotes del boton
     if(a>=2){
     a--;
     b--;
     }}
      lcd_gotoxy(1,2);
      printf(lcd_putc,"PWM8  ");
      e=b;
      c=(e*100)/500;
      lcd_gotoxy(1,4);
      printf(lcd_putc,"PWM= %f",c);     
      if(!input(PIN_A2)){                  //¿se ha pulsado el boton?
         do{                           //SI -> eliminar...           
         }while(!input(PIN_A2));            //...rebotes del boton
       
        break;
        }
}}

void frecuencia_6KHz(void){

   setup_ccp1(CCP_PWM); //ccp1 modo PWM
   setup_timer_2(T2_DIV_BY_1, 165, 1);
   
   a=20;   // punto medio del duty de 10 bits
   set_pwm1_duty(a);//duty cycle con una variable para variar el PWM
   
   while(TRUE){
   
      set_pwm1_duty(a);//duty cycle con una variable para variar el PWM

      if(!input(PIN_A0)){                  //¿se ha pulsado el boton?
         do{                           //SI -> eliminar...           
         }while(!input(PIN_A0));            //...rebotes del boton
     if(a<=664){
     a++;
     b++;
     }}
      if(!input(PIN_A1)){                  //¿se ha pulsado el boton?
         do{                           //SI -> eliminar...           
         }while(!input(PIN_A1));            //...rebotes del boton
     if(a>=2){
     a--;
     b--;
     }}
      lcd_gotoxy(1,2);
      printf(lcd_putc,"PWM9  ");
      e=b;
      c=(e*100)/666;
      lcd_gotoxy(1,4);
      printf(lcd_putc,"PWM= %f",c);     
      if(!input(PIN_A2)){                  //¿se ha pulsado el boton?
         do{                           //SI -> eliminar...           
         }while(!input(PIN_A2));            //...rebotes del boton
       
        break;
        }
}}
void frecuencia_5KHz(void){

   setup_ccp1(CCP_PWM); //ccp1 modo PWM
   setup_timer_2(T2_DIV_BY_1, 199, 1);
   
   a=20;   // punto medio del duty de 10 bits
   set_pwm1_duty(a);//duty cycle con una variable para variar el PWM
   
   while(TRUE){
   
      set_pwm1_duty(a);//duty cycle con una variable para variar el PWM

      if(!input(PIN_A0)){                  //¿se ha pulsado el boton?
         do{                           //SI -> eliminar...           
         }while(!input(PIN_A0));            //...rebotes del boton
     if(a<=798){
     a++;
     b++;
     }}
      if(!input(PIN_A1)){                  //¿se ha pulsado el boton?
         do{                           //SI -> eliminar...           
         }while(!input(PIN_A1));            //...rebotes del boton
     if(a>=2){
     a--;
     b--;
     }}
      lcd_gotoxy(1,2);
      printf(lcd_putc,"PWM10  ");
      e=b;
      c=(e*100)/800;
      lcd_gotoxy(1,4);
      printf(lcd_putc,"PWM= %f",c);
      if(!input(PIN_A2)){                  //¿se ha pulsado el boton?
         do{                           //SI -> eliminar...           
         }while(!input(PIN_A2));            //...rebotes del boton
       
        break;
        }
}}


saludos!




Desconectado septiembre_negro

  • PIC18
  • ****
  • Mensajes: 310
Re: calcular pwm
« Respuesta #8 en: 31 de Mayo de 2010, 23:22:10 »
hola septiembre_negro, bueno te comento, lo que puede pasarte son varias cosas;

primero alomejor tu motor no es del voltaje del cual le estas aplicando, en ocaciones suele suseder esto, por ejemplo si tienes un motor de 9V y le inyectas 12V en este caso te aumenta las RPM pero no el torque, por que este te desminuira.

segundo alomejor tu driver no tiene la corriente que requiere el motor.

alomejor estas aplicando un driver dañado.

lo otro que puede ser, es que la frecuencia del PWM no es la correcta para tu motor, y como saver cual es la mas indicada para esto??, bueno lo que yo hice en un momento dado y por la sujerencia de varios en este foro fue que a mas bajo empiesa a funcionar el motor del PWM va a ser mejor el decempeño del motor. por ejemplo le aplico 5 PWM de distintas frec, por ejemplo de 8KHz, 13KHz, 15KHz, 18KHz o 20KHz y los pruebo de a 1 con un duty cicle del 10% por ejmplo y veo si el motor me parte con alguna de estas frecuencias al 10% del duty y si es así, es la recomendada para tu motor.

de todas formas, te dejo una simulacion y el codigo, el cual hice para probar los PWM para unos motores que estoy usando. el programa que hice le puse 9 PWM diferentes con un rango de trabajo del 0 a 100%.
en la simulacion tambien te dejo un driver que uso yo para la parte de potencia del pic, en donde se conecta directo el motor.

bueno espero que te sirva de algo.

el codigo es este:

Código: [Seleccionar]
#include <16F873a.h>
#device adc=10
#FUSES NOWDT, HS, NOPUT, NOPROTECT, BROWNOUT, NOLVP, NOCPD, NOWRT
#use delay (clock=4000000) //Fosc=20Mhz
#define use_portb_lcd TRUE //definir portb lcd
#include<lcd420.c> //libreria manejo lcd de 20x4 modificada por suky para el puerto D
#use standard_io(A)
#use standard_io(C)

void frecuencia_20KHz(void);

void frecuencia_18KHz(void);

void frecuencia_16KHz(void);

void frecuencia_14KHz(void);

void frecuencia_12KHz(void);

void frecuencia_10KHz(void);

void frecuencia_8KHz(void);

void frecuencia_6KHz(void);

void frecuencia_5KHz(void);


int16 a;//variables para el PWM
int frecuencia,frec,b=20;
float c,e;


void main(){//programa principal
lcd_init();         //inicializa lcd

  while(true){
      if(!input(PIN_A0)){                  //¿se ha pulsado el boton?
         do{                           //SI -> eliminar...            
         }while(!input(PIN_A0));            //...rebotes del boton
     if(frecuencia<=9){
     frecuencia++;
     }}
      if(!input(PIN_A1)){                  //¿se ha pulsado el boton?
         do{                           //SI -> eliminar...            
         }while(!input(PIN_A1));            //...rebotes del boton
     if(frecuencia>=2){
     frecuencia--;
     }}
     lcd_gotoxy(1,1);
     printf(lcd_putc,"Escoja una frec ");
     lcd_gotoxy(1,2);
     printf(lcd_putc,"de PWM. opt 1-10");
     lcd_gotoxy(1,3);
     printf(lcd_putc,"Frec %i ",frecuencia);
     lcd_gotoxy(1,4);
     printf(lcd_putc,"                ");    
      if(!input(PIN_A2)){                  //¿se ha pulsado el boton?
         do{                           //SI -> eliminar...            
         }while(!input(PIN_A2));            //...rebotes del boton    
   frec=frecuencia;
      }
      else{
      frec=0;
      }
      
switch( frec )
   {
   case 1:
         lcd_gotoxy(1,1);
         printf(lcd_putc,"Frec de 20KHz");
         frecuencia_20KHz();
           break;
   case 2:
         lcd_gotoxy(1,1);
         printf(lcd_putc,"Frec de 18KHz");  
         frecuencia_18KHz();
           break;
   case 3:
         lcd_gotoxy(1,1);
         printf(lcd_putc,"Frec de 16KHz");  
         frecuencia_16KHz();
           break;
   case 4:
         lcd_gotoxy(1,1);
         printf(lcd_putc,"Frec de 14KHz");  
         frecuencia_14KHz();
           break;
   case 5:
         lcd_gotoxy(1,1);
         printf(lcd_putc,"Frec de 12KHz");  
         frecuencia_12KHz();
           break;
   case 7:
         lcd_gotoxy(1,1);
         printf(lcd_putc,"Frec de 10KHz");  
         frecuencia_10KHz();
           break;

   case 8:
         lcd_gotoxy(1,1);
         printf(lcd_putc,"Frec de 8KHz ");  
         frecuencia_8KHz();
           break;
   case 9:
         lcd_gotoxy(1,1);
         printf(lcd_putc,"Frec de 6KHz ");  
         frecuencia_6KHz();
           break;
   case 10:
         lcd_gotoxy(1,1);
         printf(lcd_putc,"Frec de 5KHz ");  
         frecuencia_5KHz();
           break;          

   } }
}

void frecuencia_20KHz(void){

   setup_ccp1(CCP_PWM); //ccp1 modo PWM
   setup_timer_2(T2_DIV_BY_1, 49, 1);
  
   a=20;   // punto medio del duty de 10 bits
   set_pwm1_duty(a);//duty cycle con una variable para variar el PWM
  
   while(TRUE){
  
      set_pwm1_duty(a);//duty cycle con una variable para variar el PWM

      if(!input(PIN_A0)){                  //¿se ha pulsado el boton?
         do{                           //SI -> eliminar...            
         }while(!input(PIN_A0));            //...rebotes del boton
     if(a<=198){
     a++;
     b++;
     }}
      if(!input(PIN_A1)){                  //¿se ha pulsado el boton?
         do{                           //SI -> eliminar...            
         }while(!input(PIN_A1));            //...rebotes del boton
     if(a>=2){
     a--;
     b--;
     }}
    
      lcd_gotoxy(1,2);
      printf(lcd_putc,"PWM  ");
      e=b;
      c=(e*100)/200;
      lcd_gotoxy(1,4);
      printf(lcd_putc,"PWM= %f ",c);    
      
      if(!input(PIN_A2)){                  //¿se ha pulsado el boton?
         do{                           //SI -> eliminar...            
         }while(!input(PIN_A2));            //...rebotes del boton
        
        break;
        }
   }
    
}


void frecuencia_18KHz(void){

   setup_ccp1(CCP_PWM); //ccp1 modo PWM
   setup_timer_2(T2_DIV_BY_1, 54, 1);
  
   a=20;   // punto medio del duty de 10 bits
   set_pwm1_duty(a);//duty cycle con una variable para variar el PWM
  
   while(TRUE){
  
      set_pwm1_duty(a);//duty cycle con una variable para variar el PWM

      if(!input(PIN_A0)){                  //¿se ha pulsado el boton?
         do{                           //SI -> eliminar...            
         }while(!input(PIN_A0));            //...rebotes del boton
     if(a<=220){
     a++;
     b++;
     }}
      if(!input(PIN_A1)){                  //¿se ha pulsado el boton?
         do{                           //SI -> eliminar...            
         }while(!input(PIN_A1));            //...rebotes del boton
     if(a>=2){
     a--;
     b--;
     }}
      lcd_gotoxy(1,2);
      printf(lcd_putc,"PWM2  ");
      e=b;
      c=(e*100)/222;
      lcd_gotoxy(1,4);
      printf(lcd_putc,"PWM= %f",c);      
      if(!input(PIN_A2)){                  //¿se ha pulsado el boton?
         do{                           //SI -> eliminar...            
         }while(!input(PIN_A2));            //...rebotes del boton
        
        break;
        }
}}

void frecuencia_16KHz(void){

   setup_ccp1(CCP_PWM); //ccp1 modo PWM
   setup_timer_2(T2_DIV_BY_1, 61, 1);
  
   a=20;   // punto medio del duty de 10 bits
   set_pwm1_duty(a);//duty cycle con una variable para variar el PWM
  
   while(TRUE){
  
      set_pwm1_duty(a);//duty cycle con una variable para variar el PWM

      if(!input(PIN_A0)){                  //¿se ha pulsado el boton?
         do{                           //SI -> eliminar...            
         }while(!input(PIN_A0));            //...rebotes del boton
     if(a<=248){
     a++;
     b++;
     }}
      if(!input(PIN_A1)){                  //¿se ha pulsado el boton?
         do{                           //SI -> eliminar...            
         }while(!input(PIN_A1));            //...rebotes del boton
     if(a>=2){
     a--;
     b--;
     }}
      lcd_gotoxy(1,2);
      printf(lcd_putc,"PWM3  ");
      e=b;
      c=(e*100)/250;
      lcd_gotoxy(1,4);
      printf(lcd_putc,"PWM= %f",c);
      if(!input(PIN_A2)){                  //¿se ha pulsado el boton?
         do{                           //SI -> eliminar...            
         }while(!input(PIN_A2));            //...rebotes del boton
        
        break;
        }
}}

void frecuencia_14KHz(void){

   setup_ccp1(CCP_PWM); //ccp1 modo PWM
   setup_timer_2(T2_DIV_BY_1, 70, 1);
  
   a=20;   // punto medio del duty de 10 bits
   set_pwm1_duty(a);//duty cycle con una variable para variar el PWM
  
   while(TRUE){
  
      set_pwm1_duty(a);//duty cycle con una variable para variar el PWM

      if(!input(PIN_A0)){                  //¿se ha pulsado el boton?
         do{                           //SI -> eliminar...            
         }while(!input(PIN_A0));            //...rebotes del boton
     if(a<=283){
     a++;
     b++;
     }}
      if(!input(PIN_A1)){                  //¿se ha pulsado el boton?
         do{                           //SI -> eliminar...            
         }while(!input(PIN_A1));            //...rebotes del boton
     if(a>=2){
     a--;
     b--;
     }}
      lcd_gotoxy(1,2);
      printf(lcd_putc,"PWM4  ");
      e=b;
      c=(e*100)/285;
      lcd_gotoxy(1,4);
      printf(lcd_putc,"PWM= %f",c);      
      if(!input(PIN_A2)){                  //¿se ha pulsado el boton?
         do{                           //SI -> eliminar...            
         }while(!input(PIN_A2));            //...rebotes del boton
        
        break;
        }
}}

void frecuencia_12KHz(void){

   setup_ccp1(CCP_PWM); //ccp1 modo PWM
   setup_timer_2(T2_DIV_BY_1, 82, 1);
  
   a=20;   // punto medio del duty de 10 bits
   set_pwm1_duty(a);//duty cycle con una variable para variar el PWM
  
   while(TRUE){
  
      set_pwm1_duty(a);//duty cycle con una variable para variar el PWM

      if(!input(PIN_A0)){                  //¿se ha pulsado el boton?
         do{                           //SI -> eliminar...            
         }while(!input(PIN_A0));            //...rebotes del boton
     if(a<=331){
     a++;
     b++;
     }}
      if(!input(PIN_A1)){                  //¿se ha pulsado el boton?
         do{                           //SI -> eliminar...            
         }while(!input(PIN_A1));            //...rebotes del boton
     if(a>=2){
     a--;
     b--;
     }}
      lcd_gotoxy(1,2);
      printf(lcd_putc,"PWM5  ");
      e=b;
      c=(e*100)/333;
      lcd_gotoxy(1,4);
      printf(lcd_putc,"PWM= %f",c);
      if(!input(PIN_A2)){                  //¿se ha pulsado el boton?
         do{                           //SI -> eliminar...            
         }while(!input(PIN_A2));            //...rebotes del boton
        
        break;
        }
}}

void frecuencia_10KHz(void){

   setup_ccp1(CCP_PWM); //ccp1 modo PWM
   setup_timer_2(T2_DIV_BY_1, 99, 1);
  
   a=20;   // punto medio del duty de 10 bits
   set_pwm1_duty(a);//duty cycle con una variable para variar el PWM
  
   while(TRUE){
  
      set_pwm1_duty(a);//duty cycle con una variable para variar el PWM

      if(!input(PIN_A0)){                  //¿se ha pulsado el boton?
         do{                           //SI -> eliminar...            
         }while(!input(PIN_A0));            //...rebotes del boton
     if(a<=398){
     a++;
     b++;
     }}
      if(!input(PIN_A1)){                  //¿se ha pulsado el boton?
         do{                           //SI -> eliminar...            
         }while(!input(PIN_A1));            //...rebotes del boton
     if(a>=2){
     a--;
     b--;
     }}
      lcd_gotoxy(1,2);
      printf(lcd_putc,"PWM7  ");
      e=b;
      c=(e*100)/400;
      lcd_gotoxy(1,4);
      printf(lcd_putc,"PWM= %f",c);      
      if(!input(PIN_A2)){                  //¿se ha pulsado el boton?
         do{                           //SI -> eliminar...            
         }while(!input(PIN_A2));            //...rebotes del boton
        
        break;
        }
}}

void frecuencia_8KHz(void){

   setup_ccp1(CCP_PWM); //ccp1 modo PWM
   setup_timer_2(T2_DIV_BY_1, 124, 1);
  
   a=20;   // punto medio del duty de 10 bits
   set_pwm1_duty(a);//duty cycle con una variable para variar el PWM
  
   while(TRUE){
  
      set_pwm1_duty(a);//duty cycle con una variable para variar el PWM

      if(!input(PIN_A0)){                  //¿se ha pulsado el boton?
         do{                           //SI -> eliminar...            
         }while(!input(PIN_A0));            //...rebotes del boton
     if(a<=498){
     a++;
     b++;
     }}
      if(!input(PIN_A1)){                  //¿se ha pulsado el boton?
         do{                           //SI -> eliminar...            
         }while(!input(PIN_A1));            //...rebotes del boton
     if(a>=2){
     a--;
     b--;
     }}
      lcd_gotoxy(1,2);
      printf(lcd_putc,"PWM8  ");
      e=b;
      c=(e*100)/500;
      lcd_gotoxy(1,4);
      printf(lcd_putc,"PWM= %f",c);      
      if(!input(PIN_A2)){                  //¿se ha pulsado el boton?
         do{                           //SI -> eliminar...            
         }while(!input(PIN_A2));            //...rebotes del boton
        
        break;
        }
}}

void frecuencia_6KHz(void){

   setup_ccp1(CCP_PWM); //ccp1 modo PWM
   setup_timer_2(T2_DIV_BY_1, 165, 1);
  
   a=20;   // punto medio del duty de 10 bits
   set_pwm1_duty(a);//duty cycle con una variable para variar el PWM
  
   while(TRUE){
  
      set_pwm1_duty(a);//duty cycle con una variable para variar el PWM

      if(!input(PIN_A0)){                  //¿se ha pulsado el boton?
         do{                           //SI -> eliminar...            
         }while(!input(PIN_A0));            //...rebotes del boton
     if(a<=664){
     a++;
     b++;
     }}
      if(!input(PIN_A1)){                  //¿se ha pulsado el boton?
         do{                           //SI -> eliminar...            
         }while(!input(PIN_A1));            //...rebotes del boton
     if(a>=2){
     a--;
     b--;
     }}
      lcd_gotoxy(1,2);
      printf(lcd_putc,"PWM9  ");
      e=b;
      c=(e*100)/666;
      lcd_gotoxy(1,4);
      printf(lcd_putc,"PWM= %f",c);      
      if(!input(PIN_A2)){                  //¿se ha pulsado el boton?
         do{                           //SI -> eliminar...            
         }while(!input(PIN_A2));            //...rebotes del boton
        
        break;
        }
}}
void frecuencia_5KHz(void){

   setup_ccp1(CCP_PWM); //ccp1 modo PWM
   setup_timer_2(T2_DIV_BY_1, 199, 1);
  
   a=20;   // punto medio del duty de 10 bits
   set_pwm1_duty(a);//duty cycle con una variable para variar el PWM
  
   while(TRUE){
  
      set_pwm1_duty(a);//duty cycle con una variable para variar el PWM

      if(!input(PIN_A0)){                  //¿se ha pulsado el boton?
         do{                           //SI -> eliminar...            
         }while(!input(PIN_A0));            //...rebotes del boton
     if(a<=798){
     a++;
     b++;
     }}
      if(!input(PIN_A1)){                  //¿se ha pulsado el boton?
         do{                           //SI -> eliminar...            
         }while(!input(PIN_A1));            //...rebotes del boton
     if(a>=2){
     a--;
     b--;
     }}
      lcd_gotoxy(1,2);
      printf(lcd_putc,"PWM10  ");
      e=b;
      c=(e*100)/800;
      lcd_gotoxy(1,4);
      printf(lcd_putc,"PWM= %f",c);
      if(!input(PIN_A2)){                  //¿se ha pulsado el boton?
         do{                           //SI -> eliminar...            
         }while(!input(PIN_A2));            //...rebotes del boton
        
        break;
        }
}}


saludos!








Hola
Te agradezco, los archivos de proteus están excelentes bastante didácticos     :-/ :-/ :-/ .
Ahora me queda claro mi error, es  producto de mi ignorancia; resulta que el motor que tengo bajo tortura es de 5.6 v y al  puente h le aplico 12vcc  :mrgreen: , esto es debido  a que el driver que utilizo el voltaje del motor debe ser superior al voltaje de la parte lógica 5vcc.  así que no teniendo otro motor a  mano  se me hizo fácil conectarlo  :oops: .


« Última modificación: 31 de Mayo de 2010, 23:25:58 por septiembre_negro »

Desconectado japifer_22

  • PIC18
  • ****
  • Mensajes: 405
Re: calcular pwm
« Respuesta #9 en: 01 de Junio de 2010, 20:14:32 »
que bueno que te allas dado cuenta del error. saludos! :lol:

Desconectado yeremayo

  • PIC10
  • *
  • Mensajes: 8
Re: calcular pwm
« Respuesta #10 en: 01 de Diciembre de 2010, 04:53:33 »
Hola japifer_22 espero que no sea demaciado tarde para comentarte esto, antes que nada un saludo te comento que lleve a cabo el circuito que propones para el pwm en mi proto board y lamentablemente no logre nada voy a seguirle intentando pero me gustaria que me guiaras sobre que voltajes debo tener en los transistores, si la frecuencia se altera al pasar por la primera resistencia y a cuanto se altera, no cuento con un osciloscopio pero tengo un frecuenciometro y al medir a la salida del pic tengo los 20khz que quiero pero al pasar de la primera resistencia la frecuencia medida por mi frecuenciometro sube a mas de 100khz eso es normal? ya revise la resistencia y esta correcta (4.7k) pero el motor nunka se mueve.

un saludo

Desconectado ilcapo_cba

  • PIC10
  • *
  • Mensajes: 4
Re: calcular pwm
« Respuesta #11 en: 29 de Diciembre de 2013, 11:11:01 »
hola expertos!

al circuito de la figura mostrada para conectar los moteres,,se puede conectar a 24V ? porque tengo motorcitos de esa tension, gracias

Desconectado estalli2

  • PIC10
  • *
  • Mensajes: 12
Re: calcular pwm
« Respuesta #12 en: 29 de Octubre de 2014, 09:31:12 »
 :-/ :-/ GRACIAS japifer_22! TAMBIEN VENIA BUSCANDO UNA BUENA EXPLICACION HACE TIEMPO!  ((:-)) ((:-)) ((:-))

Desconectado gabrielnbr89

  • PIC10
  • *
  • Mensajes: 10
Re: calcular pwm
« Respuesta #13 en: 14 de Julio de 2015, 19:13:22 »
Hola gente! Estuve estudiando este tema con la hoja de datos a mano com es costumbre... Se trata del PIC18F4550. En la sección
"CAPTURE/COMPARE/PWM MODE->PWM Mode" (pag. 148) hay un diagrama simplificado del módulo CCP2 cuando se trabaja en modo PWM. y Luego aparecen las ecuaciones que dan el período de la señal y el ciclo de trabajo.
Viendo dicho diagrama y el diagrama del temporizador 2 es fácil entender de donde sale la ecuación que nos da el período de la señal. Pero no logro entender como sale la ecuación para el ciclo de trabajo.
No entiendo por que desaparece el factor "4" de la ecuación?!!! A caso para el ciclo de trabajo [CCPR"L:CCP2CON<5:4>] no se compara con el timer 2?
Alguien lo entiende? O es que al simplificarse el diagrama se pierde información explicita de lo qu epregunto?

Ademas andando por ahi encontre esta ecuación:
DC=( [CCPR"L:CCP2CON<5:4>]*(Pre-escalar del timer2) ) / (FOSC*Tpwm)
Que da un valor entre 1 y 0. Aparentemente nos da digamos el porcentaje del ciclo de trabajo con respecto al período de la señal. Pero como se deduce ésta ecuación? es corecta?

Espero sus respuestas... saludos!!

Desconectado KILLERJC

  • Colaborador
  • DsPIC33
  • *****
  • Mensajes: 8242
Re: calcular pwm
« Respuesta #14 en: 14 de Julio de 2015, 21:08:06 »
Estoy mas que seguro que es por que el timer2 es de 8 bits, entonces como haces para compararlo con un valor de 10 bits ?

Al timer2 se le anexa o concatena 2 bits mas ( o un reloj interno (imagino que Fosc) o el preescaler segun el datasheet), quedando:

TMR2:2bits

Pero hacer eso es lo mismo que si al TMR2 lo multiplicas por 4, ya que estas rotando su posicion, por eso desaparece el 4.

Lo que dependa que sea el reloj interno o el preescaler esos ultimos bits , es segun el preescaler del TMR2,
Si es 1/16 y sabiendo que ya tenes 1/4 desde la entrada(del Fosc), esos 2 bits sera un reloj de Fosc/4
Si es 1/4 , entonces o puede usar el reloj del cristal con un 1/2 si no me equivoco.
Y si es 1/1, ya ahi deberia usar el reloj del cristal directo para esos ultimos 2 bits.

Al menos es lo que yo haria :).

Citar
Pero como se deduce ésta ecuación? es corecta?

DC=( [CCPR"L:CCP2CON<5:4>]*(Pre-escalar del timer2) ) / (FOSC*Tpwm)

Acomodemosla un poco diferente

DC=( [CCPR"L:CCP2CON<5:4>]*(Pre-escalar del timer2) ) * Tosc/ (Tpwm)

DC = Ton / (Toff + Ton)

Ton + Toff = Tpwm  En eso no hay duda

ton = [CCPR"L:CCP2CON<5:4>]*(Pre-escalar del timer2) ) * Tosc

Acordate que de aca al comparar se multiplico por 4 el TMR2, o para si queres hacerlo equivalente seria dividir los CCPR por 4, y que luego multiplicado por el 4*Tosc se va.