Я использую Nano Arduino (ATMega 328) для связи с двумя 12-битными чипами АЦП MCP3208 на основе this code. У меня есть другое устройство (светодиодный драйвер TLC5940), привязанный к контактам, которые предлагаются на этой странице, но поскольку я использую бит-стук, не важно, какие контакты я использую. Таким образом, моя конфигурация такая же, как в приведенном выше примере, за исключением того:Несколько аналого-цифровых преобразователей на Arduino с использованием бит-бит SPI
For ADC 1:
CLK -> Arduino D6
DOUT (MISO) -> Arduino D5
DIN (MOSI) -> Arduino D12
SS -> Arduino D7
For ADC 2:
CLK -> Arduino D6
DOUT (MISO) -> Arduino D5
DIN (MOSI) -> Arduino D12
SS -> Arduino D8
Таким образом, проблема заключается в том, что я получаю данные из АЦП 1, но не от АЦП 2. Я должен быть в состоянии выбрать АЦП 2 путем, потянув вывод выбора низкий, но все, что я получаю, равно 0. Есть 16 фотодиодов, подключенных к 4 операционным усилителям TLC2274. Вот код Arduino:
//Scott Little, BrainGoggles, 2013, GNU GPL v3
#include <SoftwareSerial.h>
#include "Tlc5940.h"
SoftwareSerial bluetooth(4,2); //TX 4, RX 2
#define SELPIN 7 //Selection Pin for 1st ADC
#define SELPIN2 8 //Selection Pin for 2nd ADC
#define DATAOUT 12//MOSI
#define DATAIN 5//MISO
#define SPICLOCK 6//Clock
int readvalue;
byte readvaluearray[32];
int intensity = 0;
void setup()
{
/* Call Tlc.init() to setup the tlc.
You can optionally pass an initial PWM value (0 - 4095) for all channels.*/
Tlc.init(); //interferes with other SPI
Tlc.clear(); //set pin modes
pinMode(SELPIN, OUTPUT); //adc 1 selection pin
pinMode(SELPIN2, OUTPUT); //adc 2 selection pin
pinMode(DATAOUT, OUTPUT);
pinMode(DATAIN, INPUT);
pinMode(SPICLOCK, OUTPUT);
//disable devices to start with
digitalWrite(SELPIN,HIGH);
digitalWrite(SELPIN2,HIGH);
digitalWrite(DATAOUT,LOW);
digitalWrite(SPICLOCK,LOW);
bluetooth.begin(9600);
Serial.begin(9600);
}
void loop()
{
if (bluetooth.available()) // Wait until a character is received
{
char val = (char)bluetooth.read();
Serial.println(val);
switch(val) // Perform an action depending on the command
{
case 't'://increase intensity when an 'e' is received
intensity = plus(intensity);
break;
case 'y'://decrease intensity when an 'r' is received
intensity = minus(intensity);
break;
case 'q'://turn the light on when a 'q' is received
on();
break;
case 'w'://turn the light off when a 'w' is received
off();
break;
}
}
for (int i=0; i<8; i++){ //read from ADC 1
readvalue = read_adc(i+1);
readvaluearray[2*i] = highByte(readvalue);
readvaluearray[2*i+1] = lowByte(readvalue);
}
for (int i=8; i<16; i++){ //read from ADC 2
readvalue = read_adc2(i-7);
readvaluearray[2*i] = highByte(readvalue);
readvaluearray[2*i+1] = lowByte(readvalue);
}
bluetooth.write(readvaluearray,32);
Serial.println("new");
for (int i=0;i<16;i++){
Serial.println(word(readvaluearray[2*i],readvaluearray[2*i+1]));
}
delay(2000);
}
int read_adc(int channel){
int adcvalue = 0;
byte commandbits = B11000000; //command bits - start, mode, chn (3), dont care (3)
//allow channel selection
commandbits|=((channel-1)<<3);
digitalWrite(SELPIN,LOW); //Select adc
// setup bits to be written
for (int i=7; i>=3; i--){
digitalWrite(DATAOUT,commandbits&1<<i);
//cycle clock
digitalWrite(SPICLOCK,HIGH);
digitalWrite(SPICLOCK,LOW);
}
digitalWrite(SPICLOCK,HIGH); //ignores 2 null bits
digitalWrite(SPICLOCK,LOW);
digitalWrite(SPICLOCK,HIGH);
digitalWrite(SPICLOCK,LOW);
//read bits from adc
for (int i=11; i>=0; i--){
adcvalue+=digitalRead(DATAIN)<<i;
//cycle clock
digitalWrite(SPICLOCK,HIGH);
digitalWrite(SPICLOCK,LOW);
}
digitalWrite(SELPIN, HIGH); //turn off device
return adcvalue;
}
int read_adc2(int channel){
int adcvalue = 0;
byte commandbits = B11000000; //command bits - start, mode, chn (3), dont care (3)
//allow channel selection
commandbits|=((channel-1)<<3);
digitalWrite(SELPIN2,LOW); //Select adc
// setup bits to be written
for (int i=7; i>=3; i--){
digitalWrite(DATAOUT,commandbits&1<<i);
//cycle clock
digitalWrite(SPICLOCK,HIGH);
digitalWrite(SPICLOCK,LOW);
}
digitalWrite(SPICLOCK,HIGH); //ignores 2 null bits
digitalWrite(SPICLOCK,LOW);
digitalWrite(SPICLOCK,HIGH);
digitalWrite(SPICLOCK,LOW);
//read bits from adc
for (int i=11; i>=0; i--){
adcvalue+=digitalRead(DATAIN)<<i;
//cycle clock
digitalWrite(SPICLOCK,HIGH);
digitalWrite(SPICLOCK,LOW);
}
digitalWrite(SELPIN2, HIGH); //turn off device
return adcvalue;
}
void on(void)
{
Tlc.set(1, 4095); //set pin 5 to max brightness
Tlc.update(); //execute set
//bluetooth.println("on");
//Serial.println("on");
}
void off(void)
{
Tlc.set(1, 0); //set pin 5 to min brightness
Tlc.update(); //execute set
//bluetooth.println("off");
//Serial.println("off");
}
int plus(int value)
{
value = value + 64;
if (value > 4095){value = 4095;}
Tlc.set(1, value); //set pin 5 to min brightness
Tlc.update(); //execute set
Serial.println(value);
return value;
}
int minus(int value)
{
value = value - 64;
if (value < 0){value = 0;}
Tlc.set(1, value); //set pin 5 to min brightness
Tlc.update(); //execute set
Serial.println(value);
return value;
}
Вот пример вывода, что я получаю:
new
374
372
311
313
356
276
337
387
0
0
0
0
0
0
0
0
Обновление (11/12/2013): если я отключу каждую строку с помощью TLC (отключите TLC), я могу читать данные с обоих АЦП. У меня нет конденсаторов или резисторов, подключенных к АЦП. Кто-нибудь еще видел эту проблему? – scottlittle
Обновление (11/13/2013, 12:37 утра CT): Если я отключу только tlc.init(), я могу читать оба АЦП, но светодиоды не включаются. Комментарий к tlc.init() говорит, что он вмешивается в SPI, но мне интересно, почему это будет сделано, если контакты полностью разные. Я использую стандартные контакты для TLC: https://code.google.com/p/tlc5940arduino/wiki/ArduinoDiecimilaHardwareSetup – scottlittle
Кроме того, если вы посмотрите комментарии к коду google (комментарий выше), вы увидите, что соединение на D7 предполагается, что D11. Я правильно подключен к D11. – scottlittle