[Aporte] Mezclador de luz RGB

lo importante no es entender la libreria PWM.h sino saber como utilizarla..

al inicio de tu programa utiliza la funcion Función INIT_PWM() para habilitar el Timer0 e inicializar otras variables, luego de esto ya puedes utilizar la funcion WriteDuty(CH, VALUE) que escribe el ciclo util ya sea en el canal 0, 1 o 2

CH es el canal
VALUE es un numero entre 0 y 255, el ciclo útil del canal indicado

Saludos!!
 
Última edición:
gracias por tu aporte, yo quiero implementar tu proyecto, pero como no se nada de pics, apenas empiezo a verlos....y se me dificulta entender codigo...bueno tengo unas preguntas que ojala puedas contestar....en el codigo, estas utilizando un oscilador externo? o es para qeue trabaje el pic o para generar pwm?...
esto en el codigo esta asi :
#use delay(clock = 20000000) //libreria para generar retardos con un cristal de 20 mhz

no puedo utilizar el oscilador interno del pic?...

algo como esto?

#fuses INTRC //oscilador interno
#use delay(clock = 4000000) //libreria para generar retardos con un cristal de 4 mhz
es necesario tener un oscilador externo para que funcione circuito?...otra duda es que como lo mandaste no me jala en proteus...lo corro y no hace nada....gracias
 
este lo programe en lenguaje PIC CCS con vsm studio,... trabaja con un cristal externo de 20Mhz esta compilado para el pic18F4550,... sin embargo se lo puede compilar para el pic 16F877 16F871 16F84 16F628...

incluyo simulacion en ISIS

este tiene mayor resolucion y mejor control,..



gracias por tu aporte, yo quiero implementar tu proyecto, pero como no se nada de pics, apenas empiezo a verlos....y se me dificulta entender codigo...bueno tengo unas preguntas que ojala puedas contestar....en el codigo, estas utilizando un oscilador externo? o es para qeue trabaje el pic o para generar pwm?...
esto en el codigo esta asi :
#use delay(clock = 20000000) //libreria para generar retardos con un cristal de 20 mhz

no puedo utilizar el oscilador interno del pic?...

algo como esto?

#fuses INTRC //oscilador interno
#use delay(clock = 4000000) //libreria para generar retardos con un cristal de 4 mhz
es necesario tener un oscilador externo para que funcione circuito?...otra duda es que como lo mandaste no me jala en proteus...lo corro y no hace nada....gracias

el cristal interno del PIC te da como maximo 8Mhz.. lo que influiria en el tiempo del desborde del timer0.. lo que afectaria directamente en la resolucion .. tendrias que hacer algunas modificaciones en el codigo tambien.. mas seguro comprate un crystal de 20Mhz. saludos
 

Adjuntos

  • 3.RGBControl.rar
    96 KB · Visitas: 321
Última edición:
Gracias por contestar pero tengo el problema de que al simularlo con proteus y con el pic16f877a no tiene la misma resolución o frecuencia. No se a que se deba.
Esto es lo que cambie del código. Solo lo adapte para el pic....

Código:
////////////////////////////////////////////////////////////////////////
//Control de 3 canales PWM por software                               //
//se utiliza para mesclar el brillo de tres leds;rojo,verde,azul      //
//Funcionamiento;                                                     //
//         PIN_B0=0 Aumenta o disminuye ciclo util canal0    PIN_A0   //
//         PIN_B1=0 Aumenta o disminuye ciclo util canal0    PIN_A1   //
//         PIN_B2=0 Aumenta o disminuye ciclo util canal0    PIN_A2   //
//         PIN_B3=0 disminuye ciclo util, caso contrario aumenta      //
////////////////////////////////////////////////////////////////////////
#include <16f877a.h>
#fuses HS,NOWDT,NOPROTECT,NOLVP
#use delay(clock = 20000000)   //libreria para generar retardos con un cristal de 20 mhz
#Define LED1 PIN_B5            //ROJO
#Define LED2 PIN_B6            //VERDE
#Define LED3 PIN_B7            //AZUL
#include <PWM.h>               //libreria para generar PWM por software
void main (void)
{
unsigned byte i=0,j=0,k=0;
BYTE CONST SINE_WAVE[200] = {
128,132,136,139,143,147,150,154,158,161,165,169,172,176,179,
182,186,189,192,195,199,202,204,207,210,213,215,218,220,223,
225,227,229,231,233,235,237,238,240,241,242,243,244,245,246,
247,247,247,248,248,248,248,248,247,247,247,246,245,244,243,
242,241,240,238,237,235,233,231,229,227,225,223,220,218,215,
213,210,207,204,202,199,195,192,189,186,182,179,176,172,169,
165,161,158,154,150,147,143,139,136,132,128,124,120,117,113,
109,106,102,98,95,91,87,84,80,77,74,70,67,64,61,57,54,52,49,
46,43,41,38,36,33,31,29,27,25,23,21,19,18,16,15,14,13,12,11,
10,9,9,9,8,8,8,8,8,9,9,9,10,11,12,13,14,15,16,18,19,21,23,
25,27,29,31,33,36,38,41,43,46,49,52,54,57,61,64,67,70,74,77,
80,84,87,91,95,98,102,106,109,113,117,120,124};
BYTE sine_index=0;
BYTE sine_index1=66;
BYTE sine_index2=132;
Init_Pwm();                    //Inicia MACRO para generar PWM por software
set_tris_b(0x0F);              //B0,B1,B2,B3 Entradas botones, B4,B5,B6 Salidas LED RGB
port_b_pullups(true);          //Habilita resistencias de pullup


while(true)
    {
    while(!input(Pin_B4))
        {
        Write_Duty(0,SINE_WAVE[sine_index]);
        Write_Duty(1,SINE_WAVE[sine_index1]);
        Write_Duty(2,SINE_WAVE[sine_index2]);
        if(++sine_index>=200)sine_index=0;
        if(++sine_index1>=200)sine_index1=0;
        if(++sine_index2>=200)sine_index2=0;
        delay_ms(500);
        }
     if (!input(PIN_B3))
     {
     if (!input(PIN_B0)){i++;if(i==0)i=255;Write_Duty(0,i);}
     if (!input(PIN_B1)){j++;if(j==0)j=255;Write_Duty(1,j);}
     if (!input(PIN_B2)){k++;if(k==0)k=255;Write_Duty(2,k);}
     }
    else
     {
     if (!input(PIN_B0)){i--;if(i==255)i=0;Write_Duty(0,i);}
     if (!input(PIN_B1)){j--;if(j==255)j=0;Write_Duty(1,j);}
     if (!input(PIN_B2)){k--;if(k==255)k=0;Write_Duty(2,k);}
     }
     delay_ms(10);
    }
}
 
Última edición por un moderador:
ademas me aparecen en la simulacion de proteus errores:

pc=0x016d adc conversion started before wait......
pc=0x016d porta<0> is not configurated as analog input
pc=0x016d voltaje reference for adc conversion yield a 0 v range....
alguna sugerecia?
 
segun veo los errores de simulacion ocurren porque al puerto a lo toma como analogico

coloca al principio justo debajo de
#use delay(clock = 20000000) //libreria para generar retardos con un cristal de 20 mhz

las siguientes instrucciones..

#use fast_io(a)
#use fast_io(b)


luego configura el puerto a como salidas digitales

set_tris_a(0);
 
SIGUE igual...marca errores....y al implementarlo fisicamnente ,,,me di cuenta que parpadean o mas bien titilan (se nota cuando se apagan y prenden ) las luces al bajar intensidad...como incremento frecuencia o como soluciono esto?

gracias
 
sigue igual ...alguien tiene alguna ide ade problema?...yo puse asi el codigo que me digiste....

Código:
////////////////////////////////////////////////////////////////////////
//Control de 3 canales PWM por software                               //
//se utiliza para mesclar el brillo de tres leds;rojo,verde,azul      //
//Funcionamiento;                                                     //
//         PIN_B0=0 Aumenta o disminuye ciclo util canal0    PIN_A0   //
//         PIN_B1=0 Aumenta o disminuye ciclo util canal0    PIN_A1   //
//         PIN_B2=0 Aumenta o disminuye ciclo util canal0    PIN_A2   //
//         PIN_B3=0 disminuye ciclo util, caso contrario aumenta      //
////////////////////////////////////////////////////////////////////////
#include <16f877a.h>
//#fuses XT,NOWDT,NOPROTECT,PUT,NOLVP,BROWNOUT
#fuses HS,NOWDT,NOPROTECT,NOLVP
#use delay(clock = 20000000)   //libreria para generar retardos con un cristal de 20 mhz
#use fast_io(a)
#use fast_io(b)
#Define LED1 PIN_B5            //ROJO
#Define LED2 PIN_B6            //VERDE
#Define LED3 PIN_B7            //AZUL
#include <PWM.h>              //libreria para generar PWM por software


void main (void)
{
unsigned byte i=0,j=0,k=0;
BYTE CONST SINE_WAVE[200] = {
128,132,136,139,143,147,150,154,158,161,165,169,172,176,179,
182,186,189,192,195,199,202,204,207,210,213,215,218,220,223,
225,227,229,231,233,235,237,238,240,241,242,243,244,245,246,
247,247,247,248,248,248,248,248,247,247,247,246,245,244,243,
242,241,240,238,237,235,233,231,229,227,225,223,220,218,215,
213,210,207,204,202,199,195,192,189,186,182,179,176,172,169,
165,161,158,154,150,147,143,139,136,132,128,124,120,117,113,
109,106,102,98,95,91,87,84,80,77,74,70,67,64,61,57,54,52,49,
46,43,41,38,36,33,31,29,27,25,23,21,19,18,16,15,14,13,12,11,
10,9,9,9,8,8,8,8,8,9,9,9,10,11,12,13,14,15,16,18,19,21,23,
25,27,29,31,33,36,38,41,43,46,49,52,54,57,61,64,67,70,74,77,
80,84,87,91,95,98,102,106,109,113,117,120,124};
BYTE sine_index=0;
BYTE sine_index1=66;
BYTE sine_index2=132;
Init_Pwm();                    //Inicia MACRO para generar PWM por software
set_tris_a(0); 
set_tris_b(0x0F);              //B0,B1,B2,B3 Entradas botones, B4,B5,B6 Salidas LED RGB
port_b_pullups(true);          //Habilita resistencias de pullup


while(true)
    {
    while(!input(Pin_B4))
        {
        Write_Duty(0,SINE_WAVE[sine_index]);
        Write_Duty(1,SINE_WAVE[sine_index1]);
        Write_Duty(2,SINE_WAVE[sine_index2]);
        if(++sine_index>=200)sine_index=0;
        if(++sine_index1>=200)sine_index1=0;
        if(++sine_index2>=200)sine_index2=0;
        delay_ms(500);
        }
     if (!input(PIN_B3))
     {
     if (!input(PIN_B0)){i++;if(i==0)i=255;Write_Duty(0,i);}
     if (!input(PIN_B1)){j++;if(j==0)j=255;Write_Duty(1,j);}
     if (!input(PIN_B2)){k++;if(k==0)k=255;Write_Duty(2,k);}
     }
    else
     {
     if (!input(PIN_B0)){i--;if(i==255)i=0;Write_Duty(0,i);}
     if (!input(PIN_B1)){j--;if(j==255)j=0;Write_Duty(1,j);}
     if (!input(PIN_B2)){k--;if(k==255)k=0;Write_Duty(2,k);}
     }
     delay_ms(10);
    }
}

me sigue diciendo que la puerto a no esta configurado como analogica input y que el tiempo de adc conversion es menor que min TAd=1....
 
Última edición por un moderador:
hola kobian, el error respecto a entradas analogicas no deberia ser problema ya que todo se realiza en el puerto B, que es digital solamente.

sin embargo te mando el codigo compilado para el PIC16F877A, sin errores, espero te sirva. Revisa tambien la libreria PWM.H ahi comente algunas lineas para que puedas cambiar la frecuencia con la que desborda el timer0.

Suerte!!
 

Adjuntos

  • 5.RGB16F.rar
    66.6 KB · Visitas: 180
sin embargo te mando el codigo compilado para el PIC16F877A, sin errores, espero te sirva. Revisa tambien la libreria PWM.H ahi comente algunas lineas para que puedas cambiar la frecuencia con la que desborda el timer0.
Suerte!!

Podrias ayudarme a pasarlo al pic16f84a, lo he estado intentando pero no funciona como deberia, saludos..
 
Podrias ayudarme a pasarlo al pic16f84a, lo he estado intentando pero no funciona como deberia, saludos..

aqui lo tienes companero, compilado para el 16F84A... funcionando, en simualcion espero que tambien funcione en la realidad.

incluyo codigo y simulacion, dentro de la carpeta Release esta el .hex
 

Adjuntos

  • 5.RGB16F.rar
    59.9 KB · Visitas: 137
Un PicAxe (un 08/08m/08m2 quizá no) que tengo 3 entradas analógicas, también puede hacer algo parecido verdad? Suponiendo que el pic interpretase la resistencia de un potecniómetro con valores 0-255, sería técnicamente posible no?
 
Un PicAxe (un 08/08m/08m2 quizá no) que tengo 3 entradas analógicas, también puede hacer algo parecido verdad? Suponiendo que el pic interpretase la resistencia de un potecniómetro con valores 0-255, sería técnicamente posible no?


claro, que es factible de echo yo lo hice asi tambien, lo que te recomiendo que los potenciometros sean de muy buena calidad, para tener una señal analogica lineal.



----------------------------------------------------------------

tengo que informarles que los códigos para pic 16FXXXX no están funcionando bien, esto me di cuenta al tratar de ensamblarlo yo mismo; pasa que yo lo probé con un PIC18F4550 y que utilice la configuracion PLL5 y la directiva #use delay(clock=48000000). esto no es posible hacer con un pic de la familia 16FXXX

.. asi que la unica forma de ver funcionando a este sistema es utilizado ya sea un PIC18F2550 o PIC18F4550, lamento la confusion..
 
Última edición:
Hola dinoelectro, muchas gracias por el aporte.
Hace un tiempito a mi tambien se me ocurrio armar una libreria para PWM por software, pero lo plantee un poquito y me parecio demaciado trabajo y consumidor de recursos asi que me resigne sin siquiera intentar jeje.

Programo en Jalv2 y recien hice una prueba armando un codigo simple para cambiar el duty de entre 50% y 90% y funciona.

Dos preguntas, a
A que frecuencia te trabaja el PWM?
Porque usas el valor 128 como valor maximo duty?

A mi en el simulador ISIS usando un 16f877a a 20MHz el PWM me trabaja a 70Hz con una sola salida. Solo hice una prueba en el simulador, no se como se vera en la realidad.
 
Última edición:
Hola dinoelectro, muchas gracias por el aporte.
Hace un tiempito a mi tambien se me ocurrio armar una libreria para PWM por software, pero lo plantee un poquito y me parecio demaciado trabajo y consumidor de recursos asi que me resigne sin siquiera intentar jeje.

Programo en Jalv2 y recien hice una prueba armando un codigo simple para cambiar el duty de entre 50% y 90% y funciona.

Dos preguntas, a
A que frecuencia te trabaja el PWM?
Porque usas el valor 128 como valor maximo duty?

A mi en el simulador ISIS usando un 16f877a a 20MHz el PWM me trabaja a 70Hz con una sola salida. Solo hice una prueba en el simulador, no se como se vera en la realidad.

hola nestor, respondiendo a tus preguntas

en los nuevos códigos que publique puedes revizar que la libreria PWM.h esta bastante mejorada; ahora el DUTY cambia de 0-255.. con eso logramos mejor resolucion. fue un error mio haberla truncado hasta 128.

con esta nueva libreria podes tambien elejir la frecuencia de trabajo, revisala..

este dimmer lo hice funcionar con el 18F4550 y funciona de maravilla... con los pics 16F funciona pero se puede notar un lijero pero fastidioso parpadeo, la razon es que con estos pic no tienes la opción PLL5 y #use delay(clock=48000000)

espero tus sugerencias saludos!!
 
Última edición:
Atrás
Arriba