Code:
#include <SoftwareSerial.h>
#include <SPI.h>
// Pin # constants:
const int d0 = 22;
const int d1 = 23;
const int d2 = 24;
const int d3 = 25;
const int d4 = 26;
const int d5 = 27;
const int d6 = 28;
const int d7 = 29;
const int chipA=30;
const int chipB=31;
const int datapin=32;
const int mr=33;
int potMax[8] = {0,0,0,0,0,0,0,0};
int potMin[8] = {1023, 1023, 1023, 1023, 1023, 1023, 1023, 1023};
int motorSpeeds[8] = {2, 2, 2, 2, 5, 2, 20, 2};
int motorSpeeds2[8] = {2, 2, 2, 2, 3, 3, 2, 2};
/*
Wiring on Behringer BCF-2000 fader circuit board (to Arduio MEGA2560)
40-pin ribbon connector:
| | Red strip along this edge
| |
| |
| |
40 39 38 37 36 35 34 33 32 31 30 29 28 27 26 25 24 23 22 21
[] [] [] [] [] [] [] [] [] [] [] [] [] [] [] [] [] [] [] []
[] [] [] [] [] [] [] [] [] [] [] [] [] [] [] [] [] [] [] []
20 19 18 17 16 15 14 13 12 11 10 9 8 7 6 5 4 3 2 1
pin 1 on cable is Vcc (+5v)
pin 11 on cable is Gnd
pin 26 is the TLC1542C CS pin (SPI bus SS signal, connect to pin 53 on Arduino MEGA2560 board)
pin 25 is the TLC1542C Address pin (SPI bus MOSI signal, connect to pin 51 on MEGA2560 board)
pin 5 is the TLC1542C Data out pin (SPI bus MISO signal, connect to pin 50 on MEGA2560 board)
pin 6 is the TLC1542C I/O clock pin (SPI bus SCK signal, connect to pin 52 on MEGA2560 board)
pin 7 is the "end of conversion" pin. (Connect to pin 48 on the MEGA2560 board)
pin 14 is the clock pin that sets +voltage to D0..D7 (pots 1-8), connect to pin 30 on MEGA2560
pin 34 is the clock pin that sets -voltage to D0..D7 (pots 1-8), connect to pin 31 on MEGA2560
pin 16 is D0, connect to pin 22 on MEGA2560
pin 36 is D1, connect to pin 23 on MEGA2560
pin 17 is D2, connect to pin 24 on MEGA2560
pin 37 is D3, connect to pin 25 on MEGA2560
pin 18 is D4, connect to pin 26 on MEGA2560
pin 38 is D5, connect to pin 27 on MEGA2560
pin 19 is D6, connect to pin 28 on MEGA2560
pin 39 is D7, connect to pin 29 on MEGA2560
*/
// readADC-
// Reads the ADC value (10 bits) for the specified pot:
int readADC( int pot )
{
int result;
int resultLow;
int resultHigh;
if( pot > 7 ) pot = 7;
if( pot < 0 ) pot = 0;
digitalWrite( SS, LOW ); // Activate chip select line.
SPI.transfer( pot<<4 ); // Select Pot #i (0..7) before we begin
while( digitalRead(48)); // Wait for conversion to complete
resultLow = SPI.transfer(pot<<4); // Get the L.O. data byte (only two bits here)
resultHigh= SPI.transfer(pot<<4); // Get the H.O. data byte (remaining 8 of 10 bits)
result = (resultLow >> 6) + (resultHigh << 2); // Compute 10-bit result.
digitalWrite( SS, HIGH ); // Turn off the chip
return result;
}
// moveDown-
// Moves the specified pot (pot argument) towards the bottom.
// Time of travel is determined by time x (timeOn-timeOff).
// timeOn and timeOff provide a pseudo-duty cycle to slow
// down the motor and make positioning more accurate.
void moveDown( int pot, int time, int timeOn, int timeOff )
{
// Argument check:
if( pot > 7 ) pot = 7;
if( pot < 0 ) pot = 0;
// Repeat this "time" times to generate some speed.
for( int i=0; i < time; ++i )
{
digitalWrite( d0+pot, HIGH ); // Put high on data line
digitalWrite( chipA, LOW ); // and strobe the clock on
digitalWrite( chipA, HIGH ); // the 74HC273 chip.
digitalWrite( chipA, LOW );
delay( timeOn ); // Delay with power on
digitalWrite( d0+pot, LOW ); // Put LOW on data line
digitalWrite( chipA, LOW ); // and strobe the clock on
digitalWrite( chipA, HIGH ); // the 74HC273 chip.
digitalWrite( chipA, LOW );
delay( timeOff );
}
}
// moveUp-
// Moves the specified pot (pot argument) towards the top.
// Time of travel is determined by time x (timeOn-timeOff).
// timeOn and timeOff provide a pseudo-duty cycle to slow
// down the motor and make positioning more accurate.
void moveUp( int pot, int time, int timeOn, int timeOff )
{
// Argument check:
if( pot > 7 ) pot = 7;
if( pot < 0 ) pot = 0;
// Repeat this "time" times to generate some speed.
for( int i=0; i < time; ++i )
{
digitalWrite( d0+pot, HIGH ); // Put high on data line
digitalWrite( chipB, LOW ); // and strobe the clock on
digitalWrite( chipB, HIGH ); // the 74HC273 chip.
digitalWrite( chipB, LOW );
delay( timeOn ); // Delay with power on
digitalWrite( d0+pot, LOW ); // Put LOW on data line
digitalWrite( chipB, LOW ); // and strobe the clock on
digitalWrite( chipB, HIGH ); // the 74HC273 chip.
digitalWrite( chipB, LOW );
delay( timeOff ); // Delay with power off
}
}
// Calibrate all the faders on the BCF-2000
// to compute their minimum and maximum values.
void calibrate( void )
{
int potVal;
int PotDone;
int PotCnt;
int PotLast;
// Compute the maximum position for each pot:
for( int pot=0; pot<8; ++pot)
{
potMax[pot] = 0;
PotCnt = 0;
PotDone = 0;
PotLast = 0;
while( !PotDone )
{
moveUp( pot, 10, 2, 1 );
potVal = readADC( pot );
if( PotLast >= potVal )
{
// When we're stuck at the current location
// for two consecutive calls, assume we've
// jammed and this is as far as we can go.
++PotCnt;
PotDone = PotCnt > 2;
}
else
{
PotCnt = 0;
}
PotLast = potVal;
if( potVal > potMax[pot] )
{
potMax[pot] = potVal;
}
}
Serial.print( "maxPot[" );
Serial.print( pot );
Serial.print( "]=" );
Serial.println( potMax[pot] );
}
// Compute minimum position for each pot.
for( int pot=0; pot<8; ++pot)
{
PotCnt = 0;
PotDone = 0;
PotLast = 1024;
potMin[pot] = 1024;
while( !PotDone )
{
moveDown( pot, 10, 3, 2 );
potVal = readADC( pot );
if( PotLast <= potVal )
{
// When we're stuck at the current location
// for two consecutive calls, assume we've
// jammed and this is as far as we can go.
++PotCnt;
PotDone = PotCnt > 2;
}
else
{
PotCnt = 0;
}
PotLast = potVal;
if( potVal < potMin[pot] )
{
potMin[pot] = potVal;
}
}
Serial.print( "minPot[" );
Serial.print( pot );
Serial.print( "]=" );
Serial.println( potMin[pot] );
}
}
// potGoto-
// Positions the specified pot (pot argument) at the location specified (0..1024)
void potGoto( int pot, int position )
{
int desiredPosn;
int curPosn = readADC( pot );
// Validate arguments.
if( pot > 7 ) pot = 7;
if( pot < 0 ) pot = 0;
if( position > potMax[pot] )
{
desiredPosn = potMax[pot];
}
else if( position < potMin[pot] )
{
desiredPosn = potMin[pot];
}
else
{
desiredPosn = position;
}
// Determine which direction we're going.
// Note: This code will overshoot by a bit.
// Really need a PID algorithm here. However, my
// BCF-2000 is so messed up that it wouldn't
// buy me anything to add it.
if( desiredPosn < curPosn )
{
// Need to drive fader down to specified position
while( desiredPosn < curPosn )
{
// Note: timeOn/timeOff parms are a kludge for my board.
moveDown( pot, 1, motorSpeeds[pot], motorSpeeds2[pot] );
curPosn = readADC( pot );
}
}
else // desiredPosn >= curPosn
{
while( desiredPosn > curPosn )
{
// Note: timeOn/timeOff parms are a kludge for my board.
moveUp( pot, 1, motorSpeeds[pot], motorSpeeds2[pot] );
curPosn = readADC( pot );
}
}
Serial.print( "Pot: ");
Serial.print( pot );
Serial.print( ", GotoPosn: " );
Serial.print( position );
Serial.print( ", finalPosn: " );
Serial.println( curPosn );
}
// Usual Arduino stuff:
void setup() {
Serial.begin( 9600 );
SPI.begin();
SPI.setClockDivider(SPI_CLOCK_DIV64); // The TLC1542C chip on the BCF-2000 is *slow*
SPI.setBitOrder( MSBFIRST ); // Data arrives most significant bit first
digitalWrite( SS, HIGH ); // Initialize with TLC1542C unselected
pinMode( 48, INPUT ); // EOC on TLC1542 comes in on pin 48 as an input
pinMode(d0, OUTPUT );
pinMode(d1, OUTPUT );
pinMode(d2, OUTPUT );
pinMode(d3, OUTPUT );
pinMode(d4, OUTPUT );
pinMode(d5, OUTPUT );
pinMode(d6, OUTPUT );
pinMode(d7, OUTPUT );
pinMode(chipA, OUTPUT );
pinMode(chipB, OUTPUT );
pinMode(mr, OUTPUT );
digitalWrite( mr, LOW );
digitalWrite( mr, HIGH );
digitalWrite( d0, LOW );
digitalWrite( d1, LOW );
digitalWrite( d2, LOW );
digitalWrite( d3, LOW );
digitalWrite( d4, LOW );
digitalWrite( d5, LOW );
digitalWrite( d6, LOW );
digitalWrite( d7, LOW );
digitalWrite( chipA, LOW );
digitalWrite( chipB, LOW );
pinMode( 2, OUTPUT );
pinMode( 3, OUTPUT );
pinMode( 4, OUTPUT );
// Calibrate the pots to determine their min and max positions:
calibrate();
}
void loop() {
for( int pot=0; pot < 8; ++pot )
{
for( int posn=100; posn < 900; posn+=100 )
{
potGoto( pot, posn );
}
for( int posn=900; posn > 100; posn-=100 )
{
potGoto( pot, posn );
}
}
delay(2000);
Serial.println( "" );
}
Enjoy.
Connect With Us