Hola grupo, quiero construir un dimmer de 12 canales y la verdad no se por donde empezar, no se nada de PIC nunca trabaje con uno. Alguien podria ayudarme o proporcionarme algun circuito, estuve buscando y solo hay de unos pocos canales 4 u 8 como mucho
Adjunto un circuito de un dimmer de 4 canales, alguien podria confirmarme si se puede expandir hasta 12 canales este proyecto?
Y aqui el programa:
//**************************************************************//
// Name : DMX 4 ch Dimmer //
// Author : Dan Fredell //
// Date : 16 Apr, 2013 //
// Version : 1.1 //
// Website : //
//**********************************z ******************************
/*File modifacations:
* hardware/arduino/boards.txt uno.build.f_cpu=20000000L
* It tells the software that the hardware is running at 20MHz
*
* In cores/arduino/HardwareSerial.cpp remove 42 lines,
* this allows us to make our own intrupt for DMX signal in
* From
* #if !defined(USART0_RX_vect) && defined(USART1_RX_vect)
* to
* #if defined(USART1_RX_vect)
*/
/*
* V1.1 - fixed issue of flashing output caused by AC interrupting the DMX data
*/
//double dim = 0; // Dimming level (0-128) 0 = on, 128 = 0ff
int AC_pin[4] = {
6,7,8,12}; // Output to Opto Triac
int LED_pin[4] = {
5,9,10,11}; // Output to Opto Triac
int brightness[4];
int LEDBrightness[4];
boolean zeroCross[]={
false,false,false,false};
int PrevLEDValue[]={
0,0,0,0};
unsigned long startZeroTime=0;
unsigned long timeElapsed=0;//Time until end of cycle
volatile uint8_t DmxRxField[4]; //array of DMX vals (raw) DMX Max:255 Min:0
volatile uint16_t DmxAddress; //start address
enum {
IDLE, BREAK, STARTB, STARTADR}; //DMX states
volatile uint8_t gDmxState;
void setup() {
delay(500);//Wait for the system to charge
//Setup DMX
gDmxState= IDLE; // initial state
DmxAddress = 1; // The desired DMX Start Adress. Starts at 1
Serial.begin(250000);//Read DMX signal via RX
//Setup Outputs
attachInterrupt(1,zeroCrossInterupt,FALLING);
for(int ch=0;ch<4;ch++){
pinMode(AC_pin[ch],OUTPUT);
pinMode(LED_pin[ch],OUTPUT);
digitalWrite(AC_pin[ch],HIGH);
analogWrite(LED_pin[ch],255);
delay(1000);
digitalWrite(AC_pin[ch],LOW);
analogWrite(LED_pin[ch],0);
}
}
void zeroCrossInterupt(){
startZeroTime=micros();
gDmxState= IDLE;
for(int ch=0;ch<4;ch++){
brightness[ch]=map(DmxRxField[ch],0,265,8000,0);
zeroCross[ch]=true;
}
}
void loop() {
timeElapsed=micros()-startZeroTime;
/**
* This is the main loop. I use timeElapsed instead of delay to allow for more then 1 output.
* The +50 is to elimnate random noisy high and low values
* DmxRxField[ch] > 10 because at DMX val8 it flickers
*/
for(int ch=0;ch<4;ch++){
if(zeroCross[ch] && timeElapsed > brightness[ch] && timeElapsed < brightness[ch]+50 && DmxRxField[ch]>10){
digitalWrite(AC_pin[ch], HIGH); // fire the Triac
delayMicroseconds(10); //pause briefly to ensure the triac turned on
digitalWrite(AC_pin[ch], LOW); // turn off the Triac gate (triac will not turn off until next zero cross)
zeroCross[ch]=false;
}
if(PrevLEDValue[ch]!=DmxRxField[ch]){//Change the LED value only if it changed
analogWrite(LED_pin[ch],DmxRxField[ch]);
PrevLEDValue[ch]=DmxRxField[ch];
}
}
}
//ISR method from http://playground.arduino.cc/DMX/Ardmx
ISR(USART_RX_vect) {
static uint16_t DmxCount;
uint8_t USARTstate= UCSR0A; //get state before data!
uint8_t DmxByte = UDR0; //get data
uint8_t DmxState = gDmxState; //just load once from SRAM to increase speed
if (DmxState == STARTADR)
{
DmxRxField[DmxCount++]= DmxByte; //get channel
if (DmxCount >= sizeof(DmxRxField)) //all ch received?
{
gDmxState= IDLE; //wait for next break
}
} else if (USARTstate &(1<<FE0)) //check for break
{
DmxCount = DmxAddress; //reset channel counter (count channels before start address)
gDmxState= BREAK;
}
else if (DmxState == BREAK)
{
if (DmxByte == 0) gDmxState= STARTB; //normal start code detected
else gDmxState= IDLE;
}
else if (DmxState == STARTB)
{
if (--DmxCount == 0) //start address reached?
{
DmxCount= 1; //set up counter for required channels
DmxRxField[0]= DmxByte; //get 1st DMX channel of device
gDmxState= STARTADR;
}
}
}