Working on a project for a friend for a fairly large sprinkler controller. Using a pic16f1825 and GCB, I am using the DMX protocol to drive the relay boards. These can be connected using standard ethernet cables and the cable run can be pretty damn long. I am still sorting out the code and I will post it shortly. The final project will use a DS3231 with 4k of eeprom to start, stop different zones at different times, etc. I am only using the TX pin on the pic to drive the DMX differential line driver.
Here is a short video of testing the DMX relay boards.
Here is the test code for the DMX relays. I am using the TX pin on the pic at 250k baud to drive a 75176 differential bus transciever but only using the transmit side. According to wiki, this can drive up to 1200 meters (3900 feet) of cable. A lot of DMX recievers can also use ethernet cable which makes things nice.
The TransDMX sub handles the UART TX pin to work with the DMX protocol. I used a logic analyzer and the DMX timing is excellent when using a 20MHZ crystal. I tried a few tests on some DMX RGB lights and they work fine using this timing also. I will post the RGB video and code soon. Transmitting all 512 channels, you can get about 44 updates per second, more if you use less channels (pretty damn fast). Once I have this completed, I would like to attempt making a DMX library for GCB.
For more info on the DMX protocol, check out this link...
The particular relay boards I am using don't require a constant stream of DMX signal. You can send a stream only whenever you want to change a value. However, if you want a constant DMX stream, you could simply set up a timer interrupt to call the TransDMX sub at regular intervals if needed.
One slight problem, I couldn't figure out how to dim the MaxChan variable as a word. DMX can go up to 512 channels, but when I try to dim as word, the compiler errors. (STARTUP1Invalid variable name: 24 - Remmed out in code below), So right now the maximum amount of channels is 255. Not a problem in my case, but could be for others using high DMX channel numbers. Using v0.98.00.
The Led is to show activity for debugging.
I love me some GCB! More to come...
#chip 16F1825, 20
#config OSC = HS, Pllen = OFF
'USART settings
#define USART_BAUD_RATE 250000 ' Initializes USART port to 250000 baud
#define USART_TX_BLOCKING ' wait for tx register to finish
#define DMXout portC.4 ' Pin 6 TX - out to 75176 DMX driver
dir DMXout out ' Set pin directions
set DMXout on ' DMX MARK condition (DMX idle)
#define LED portC.2 ' Pin 8 C.2 - Debug LED
dir LED out
set LED off
RCSTA = 0b01010000 ' serial port disabled (SPEN = 0), 9 bit data (RX9 = 1) not sure if needed here in RX
TXSTA = 0b01100101 ' 9 bit data (TX9 = 1), TXEN = 1, high speed (BRGH = 1), place for 9th bit = 1 (TX9D = 1)
'dim MaxChan as word '<<<<< ERROR - compiler doesn't like this???????
#define MaxChan 24 ' Max number of DMX Channels to send (24 Relays)
dim DMXCHAN(MaxChan) ' Create DMX array
#define RlyON 255
#define RlyOFF 0
for Bb = 1 to 10 ' Blink "I'm alive" LED
pulseout led, 60 ms
wait 60 ms
next Bb
ClrAll ' Clear DMX array
' Test 3 8 channel relay boards (24 channels)
do
For Bb = 1 to 2
For Aa = 1 to MaxChan
SendChan Aa, RlyON
wait 60 ms
SendChan Aa, RlyOFF
wait 60 ms
Next Aa
Next Bb
For Aa = 1 to 5
SendAll RlyON
wait 100 ms
SendAll RlyOff
wait 100 ms
Next Aa
For Bb = 1 to 3
For Aa = 1 to MaxChan
SendChan Aa, RlyON
wait 60 ms
Next Aa
For Aa = MaxChan to 1 step -1
SendChan Aa, RlyOFF
wait 60 ms
Next Aa
Next Bb
loop
'************************ SEND 1 DMX CHANNEL *********************
' this sub changes a particular DMX channel (Chan) to a value (0 - 255)
sub SendChan(Chan, Value)
DMXCHAN(Chan) = Value
TransDMX
end sub
'*********************** SEND ALL DMX CHANNELS *******************
' this sub sets all DMX channels to a value (0 - 255)
sub SendAll(Value)
for Xx = 1 to MaxChan
DMXCHAN(Xx) = Value
next Xx
TransDMX
end sub
'*********************** CLEAR ALL DMX CHANNELS *******************
' this sub sets all DMX array values to 0
sub ClrAll
for Xx = 1 to MaxChan
DMXCHAN(Xx) = 0
next Xx
TransDMX
end sub
'****************** TRANSMIT DMX Channels *************
' this sub transmits (MaxChan) of the DMX array + some extra 0s
sub TransDMX
set LED on 'Show DMX activity on LED
set DMXout off
wait 100 us 'BREAK - 100us
set DMXout on
wait 6 us 'MARK AFTER BREAK (MAB) - 12.75us
RCSTA.SPEN = 1 'enable USART
HSerSend 0 'STARTCODE (always 0)
for Zz = 1 to MaxChan 'Channel 1 - (MaxChan)
HSerSend DMXCHAN(Zz)
next Zz
'if MaxChan < 482 then
for Xtra = 1 to 30 'Semd xtra zeros for some DMX receivers that need it
HSerSend 0
next Xtra
'end if
RCSTA.SPEN = 0 'disable USART
set DMXout on 'DMX MARK condition (DMX idle)
set LED off
end sub
Last edit: Moto Geek 2017-11-19
If you would like to refer to this comment somewhere else in this project, copy and paste the following link:
I could help but notice '<<<<< ERROR - compiler doesn't like this???????
This because if you Dim MaxChan as a WORD then aa, bb, zz, xx, XTRA have to be WORDs also - why? you are trying to assign a WORD to a BYTE counter. So, the compiler is moaning as your types do not match.
If you would like to refer to this comment somewhere else in this project, copy and paste the following link:
AAAAAHHHHHH!!!! That makes perfect sense!!! I will change the types and report back.
Here is a quick video of using a 30 channel DMX mosfet board and splitting it up into 10 RGB channels. I was able to "cut the cord" using a wireless DMX transmitter and reciever. This was done just to check compatibility with other DMX devices. Works good. The pic can transmit the DMX data very quickly. I have to stop playing and go outside to see what thats all about.... sun, fresh air, etc...
looks great Bad, but may I suggest that as the Code is included, you remove the sentence that reads "I am still sorting out the code and I will post it shortly."
Cheers
Chris
If you would like to refer to this comment somewhere else in this project, copy and paste the following link:
Your Bed, i'm Bad.
Appologies from a Dislexic South African ;>)
Not being unix literate I wouldn't know what bed is an acronym of.
It took me months to work out what sudo stood for.
If you would like to refer to this comment somewhere else in this project, copy and paste the following link:
An acronym is a short word formed from the initial letters of several words (fc ~ football club)
My name is much to type in, so I searched an abbrevation. So nothing special, no Unix special
If you would like to refer to this comment somewhere else in this project, copy and paste the following link:
Hi i have a question about the part where it says
"TXSTA = 0b01100101 ' 9 bit data (TX9 = 1), TXEN = 1, high speed (BRGH = 1), place for 9th bit = 1 (TX9D = 1)"
you're specifying 9 bit data, but wikipedia says:
"At the datalink layer, a DMX512 controller transmits asynchronous serial data at 250 kbit/s. The data format is fixed at one start bit, eight data bits (least significant first[7]), two stop bits and no parity."
i'm using an atmega2560 and i don't know whether to specify 8 bit or 9 bit data.
thanx, mike
If you would like to refer to this comment somewhere else in this project, copy and paste the following link:
please see the answer there.
you need 8 bit data as specifyed but 2 stop bits which the atmega2560's usart is ca[able. Also MotoGeek clarified turning the usart on and off which you also will need for the DMX protocol.
GL
Mike
If you would like to refer to this comment somewhere else in this project, copy and paste the following link:
Hi can someone look at my code and tell me what's wrong with it? i'm tryin to send a DMX packet with a mega2560 and a simple DMX shield that's connected to TX0, RX0 and a DE signal on pin 2 (port e,4).
i loaded the board with an arduino sketch and it worked correctly with all the same hardware. the slave device, a relay board, has an LED that flashes when the sketch is running. then i used AVRdude with all the same parameters to load this gcb code and i get no result. no flash, no relay action.
i'm using motogeek's code with very little modification.
thanx, mike
#chip mega2560, 16
'USART settings
'#define USART_BAUD_RATE 250000 ' Initializes USART port to 250000 baud
'ATmega640/V-1280/V-1281/V-2560/V-2561/V page 226
UBRR0L = 0b00000011 ' USART0 baud = 250000
#define USART_TX_BLOCKING ' wait for tx register to finish
#define DMXout PORTE.1 ' Pin 1 TX - out to MAX481 DMX driver
dir DMXout out ' Set pin directions
set DMXout on ' DMX MARK condition (DMX idle)
#define DE PORTE.4
dir DE out
set DE on
#define LED PORTB.7 ' Pin B.7 - Debug LED
dir LED out
set LED off
UCSR0C = 0b00001011 ' Async, no parity, 2 stop bits, 8 bits
TXEN0 = 0 ' disable TX
'dim MaxChan as integer
#define MaxChan 24 ' Max number of DMX Channels to send (24 Relays)
dim DMXCHAN(MaxChan) ' Create DMX array
dim Aa, Bb, Xx as word
#define RlyON 255
#define RlyOFF 0
for Bb = 1 to 10 ' Blink "I'm alive" LED
pulseout led, 60 ms
wait 60 ms
next Bb
ClrAll ' Clear DMX array
' this routing will cycle a bunch of relays on and off at 2.5Hz
do
SendAll RlyON
wait 500 ms
SendAll RlyOff
wait 500 ms
loop
'************************ SEND 1 DMX CHANNEL *********************
' this sub changes a particular DMX channel (Chan) to a value (0 - 255)
sub SendChan(Chan, Value)
DMXCHAN(Chan) = Value
TransDMX
end sub
'*********************** SEND ALL DMX CHANNELS *******************
' this sub sets all DMX channels to a value (0 - 255)
sub SendAll(Value)
for Xx = 1 to MaxChan
DMXCHAN(Xx) = Value
next Xx
TransDMX
end sub
'*********************** CLEAR ALL DMX CHANNELS *******************
' this sub sets all DMX array values to 0
sub ClrAll
for Xx = 1 to MaxChan
DMXCHAN(Xx) = 0
next Xx
TransDMX
end sub
'****************** TRANSMIT DMX Channels *************
' this sub transmits (MaxChan) of the DMX array + some extra 0s
sub TransDMX
set LED on 'Show DMX activity on LED
set DMXout off
wait 100 ms 'BREAK - 100ms
set DMXout on
wait 100 ms 'MARK AFTER BREAK (MAB) - 100ms
TXEN0 = 1 'enable TX
HSerSend 0 'STARTCODE (always 0)
set DMXout on
wait 100 ms 'Mark Time Between Frames (MTBF) - 100ms
set DMXout off
for Zz = 1 to MaxChan 'Channel 1 - (MaxChan)
HSerSend DMXCHAN(Zz)
next Zz
'if MaxChan < 482 then
for Xtra = 1 to 30 'Semd xtra zeros for some DMX receivers that need it
HSerSend 0
next Xtra
'end if
TXEN0 = 0 ' disable TX
set DMXout on 'DMX MARK condition (DMX idle)
wait 100 ms 'MARK for at least 100ms
set LED off
end sub
If you would like to refer to this comment somewhere else in this project, copy and paste the following link:
funny.... with the mega board running i close Great Cow Basic, open arduino 1.8.5 and connect to the mega. i open the serial monitor (since it's outputting it's data on USART0) and i see a repeated stream of DMX packets. but then i get out a second mega, one that's programmed (and used many times) to pass serial data between USART1 and USART0 . i remove the DMX shield from mega1 and connect USART0 (mega1) to USART1 (mega2). connect arduino 185 to mega2, open serial monitor, and get nothing.
edit: oh yeah i write to the mega registers directly cause i'm paranoid about getting it configured right.
Last edit: louie 2018-04-20
If you would like to refer to this comment somewhere else in this project, copy and paste the following link:
ok hold on..... well now that made a difference using the "define baud rate" when i flash the board i get 1 to 3 relay clicks, like there's one or two packets that are working, but no more than that. i hit FLASH again and i get another couple of clicks.
Last edit: louie 2018-04-20
If you would like to refer to this comment somewhere else in this project, copy and paste the following link:
well no matter what i change, even the baudrate, i get the same result. every time i hit FLASH i get 1 to 3 clicks of the relays. the only thing i've done that has any effect at all is if i set the slave address to 2 then i get no action at all. the address has to be 1
If you would like to refer to this comment somewhere else in this project, copy and paste the following link:
Mike,
Let's divide and conquer!
First take the DMX relay board off of the mega2560. We need to work only with the mega2560.
Have you successfully tried the LED demo? should flash the led on pin 13 = portB.7
#chip mega2560, 16
' #include ;
' no solution specifc includes, default includes are always included
; ----- Define Hardware settings
' this is required to tell the microprocessor the port is an output
'Set the pin direction to output:
dir PORTB.7 out
; ----- Variables
' none specified in the example. All byte variables are defined upon use.
; ----- Main body of program commences here.
Start:
Set PORTB.7 ON 'turn LED on
Wait 100 ms 'wait 100 milliseconds
Set PORTB.7 OFF 'turn LED off
Wait 900 ms 'wait 900 milliseconds
Goto Start 'jump back to the start of the program
If this don't work then we have to work on the flashAVR.bat file in GCB. We have to set it for the correct AVR ,mega2560, and the correct comport, com13 in my case
REM Call AVRdude for Arduino_Mega2560 bootloader - Alternative #1, see also below
REM You will have to confirm the com (communications) port - currently set for com6
"AVRdude\avrdude.exe" -c wiring -p m2560 -P COM13 -b 115200 -D -U flash:w:%1:i
I am sorry if this is too remedial but this is where I had to start this morning.
We are working from the windows IDE or from console??
I have a version of your program running to terminal. I get the led flashing periodically and the tx led on the mega2560 indicating transmitting.
I am using the terminal on the GCB IDE. set for 250000 and 2 stops.
The packet sent looks like :
Working on a project for a friend for a fairly large sprinkler controller. Using a pic16f1825 and GCB, I am using the DMX protocol to drive the relay boards. These can be connected using standard ethernet cables and the cable run can be pretty damn long. I am still sorting out the code and I will post it shortly. The final project will use a DS3231 with 4k of eeprom to start, stop different zones at different times, etc. I am only using the TX pin on the pic to drive the DMX differential line driver.
Here is a short video of testing the DMX relay boards.
https://youtu.be/KBexZWPj-tU
Last edit: Moto Geek 2017-11-19
Here is the test code for the DMX relays. I am using the TX pin on the pic at 250k baud to drive a 75176 differential bus transciever but only using the transmit side. According to wiki, this can drive up to 1200 meters (3900 feet) of cable. A lot of DMX recievers can also use ethernet cable which makes things nice.
The TransDMX sub handles the UART TX pin to work with the DMX protocol. I used a logic analyzer and the DMX timing is excellent when using a 20MHZ crystal. I tried a few tests on some DMX RGB lights and they work fine using this timing also. I will post the RGB video and code soon. Transmitting all 512 channels, you can get about 44 updates per second, more if you use less channels (pretty damn fast). Once I have this completed, I would like to attempt making a DMX library for GCB.
For more info on the DMX protocol, check out this link...
http://www.dmx512-online.com/packt.html
The particular relay boards I am using don't require a constant stream of DMX signal. You can send a stream only whenever you want to change a value. However, if you want a constant DMX stream, you could simply set up a timer interrupt to call the TransDMX sub at regular intervals if needed.
One slight problem, I couldn't figure out how to dim the MaxChan variable as a word. DMX can go up to 512 channels, but when I try to dim as word, the compiler errors. (STARTUP1Invalid variable name: 24 - Remmed out in code below), So right now the maximum amount of channels is 255. Not a problem in my case, but could be for others using high DMX channel numbers. Using v0.98.00.
The Led is to show activity for debugging.
I love me some GCB! More to come...
Last edit: Moto Geek 2017-11-19
Nice.
I could help but notice '<<<<< ERROR - compiler doesn't like this???????
This because if you Dim MaxChan as a WORD then aa, bb, zz, xx, XTRA have to be WORDs also - why? you are trying to assign a WORD to a BYTE counter. So, the compiler is moaning as your types do not match.
AAAAAHHHHHH!!!! That makes perfect sense!!! I will change the types and report back.
Here is a quick video of using a 30 channel DMX mosfet board and splitting it up into 10 RGB channels. I was able to "cut the cord" using a wireless DMX transmitter and reciever. This was done just to check compatibility with other DMX devices. Works good. The pic can transmit the DMX data very quickly. I have to stop playing and go outside to see what thats all about.... sun, fresh air, etc...
Have a look
https://youtu.be/iqwe_KPOoUE
Last edit: Moto Geek 2017-11-19
Moto, very cool projects. I like the clacking of the relays. Thanks for sharing!
Me to, and the leds. Nice to watch. A coil gun came to mind.
The Author gave me his ok to publish this very nice Project as Showcase for our Homepage.
So be it: http://gcbasic.sourceforge.net/Typesetter/index.php/Driving-a-bunch-of-relays-using-one-pin-on-pic
looks great Bad, but may I suggest that as the Code is included, you remove the sentence that reads "I am still sorting out the code and I will post it shortly."
Cheers
Chris
Lol Double LOL, Ok You're right, fixed, And No, even sometimes my English is very BAD, my Nick is bed (unix login acronym)
But a huge Thank You for reading and reporting the Typo!
Last edit: bed 2017-12-12
Your Bed, i'm Bad.
Appologies from a Dislexic South African ;>)
Not being unix literate I wouldn't know what bed is an acronym of.
It took me months to work out what sudo stood for.
No problem, Sir :-)
An acronym is a short word formed from the initial letters of several words (fc ~ football club)
My name is much to type in, so I searched an abbrevation. So nothing special, no Unix special
Hi i have a question about the part where it says
"TXSTA = 0b01100101 ' 9 bit data (TX9 = 1), TXEN = 1, high speed (BRGH = 1), place for 9th bit = 1 (TX9D = 1)"
you're specifying 9 bit data, but wikipedia says:
"At the datalink layer, a DMX512 controller transmits asynchronous serial data at 250 kbit/s. The data format is fixed at one start bit, eight data bits (least significant first[7]), two stop bits and no parity."
i'm using an atmega2560 and i don't know whether to specify 8 bit or 9 bit data.
thanx, mike
Mike,
I tried to answer this yesterday on your other thread. https://sourceforge.net/p/gcbasic/discussion/demonstrationcode/thread/d11ed005/?limit=25#092d
please see the answer there.
you need 8 bit data as specifyed but 2 stop bits which the atmega2560's usart is ca[able. Also MotoGeek clarified turning the usart on and off which you also will need for the DMX protocol.
GL
Mike
Hi can someone look at my code and tell me what's wrong with it? i'm tryin to send a DMX packet with a mega2560 and a simple DMX shield that's connected to TX0, RX0 and a DE signal on pin 2 (port e,4).
i loaded the board with an arduino sketch and it worked correctly with all the same hardware. the slave device, a relay board, has an LED that flashes when the sketch is running. then i used AVRdude with all the same parameters to load this gcb code and i get no result. no flash, no relay action.
i'm using motogeek's code with very little modification.
thanx, mike
Does a simple LED flash using minimal code? Can you confirm the basic operation first?
yes it's flashing at the right rythm.
Ok I am on road. Can't compile etc but let us rule out the easy stuff.
Add #option explicit
OK there were 2 undeclared variables but that wasn't it.
Why the hand cranked init of the comm port? Check this is working with terminal application. Remove the tweaks and ensure commcomport is working.
funny.... with the mega board running i close Great Cow Basic, open arduino 1.8.5 and connect to the mega. i open the serial monitor (since it's outputting it's data on USART0) and i see a repeated stream of DMX packets. but then i get out a second mega, one that's programmed (and used many times) to pass serial data between USART1 and USART0 . i remove the DMX shield from mega1 and connect USART0 (mega1) to USART1 (mega2). connect arduino 185 to mega2, open serial monitor, and get nothing.
edit: oh yeah i write to the mega registers directly cause i'm paranoid about getting it configured right.
Last edit: louie 2018-04-20
mike, You should let the compiler figure the baud rate.
When you use the #define .
You get this in asm.
So more is involved than the one register you set.
Start there.
Mike
mike, You should let the compiler figure the baud rate.
When you use the #define .
You get this in asm.
So more is involved than the one register you set.
Start there.
Mike
ok hold on..... well now that made a difference using the "define baud rate" when i flash the board i get 1 to 3 relay clicks, like there's one or two packets that are working, but no more than that. i hit FLASH again and i get another couple of clicks.
Last edit: louie 2018-04-20
well no matter what i change, even the baudrate, i get the same result. every time i hit FLASH i get 1 to 3 clicks of the relays. the only thing i've done that has any effect at all is if i set the slave address to 2 then i get no action at all. the address has to be 1
Mike,
Let's divide and conquer!
First take the DMX relay board off of the mega2560. We need to work only with the mega2560.
Have you successfully tried the LED demo? should flash the led on pin 13 = portB.7
If this don't work then we have to work on the flashAVR.bat file in GCB. We have to set it for the correct AVR ,mega2560, and the correct comport, com13 in my case
I am sorry if this is too remedial but this is where I had to start this morning.
We are working from the windows IDE or from console??
I have a version of your program running to terminal. I get the led flashing periodically and the tx led on the mega2560 indicating transmitting.
I am using the terminal on the GCB IDE. set for 250000 and 2 stops.
The packet sent looks like :
This repeats . i don't see the address to '01' ?
First things first. Confirm you are programming the mega2560 with GCB not the arduino.
we'll solve this.
Mike