Тема: DAC CS8416 + CS4398 (Arduino)(2)
Доработка ЦАП
Доработан индикатор ERROR - нет звука отображается как "NO SOUND", не подключен кабель COAX отображается как ERROR
#include <Wire.h>
#include <EEPROM.h>
#include <Encoder.h> // http://rcl-radio.ru/wp-content/uploads/2019/05/Encoder.zip
#include <MsTimer2.h> // http://rcl-radio.ru/wp-content/uploads/2018/11/MsTimer2.zip
#include <LiquidCrystal_I2C.h> //Библиотека - http://forum.rcl-radio.ru/misc.php?action=pan_download&item=45&download=1
LiquidCrystal_I2C lcd(0x27,16,2); // Устанавливаем дисплей
Encoder myEnc(9, 8);//CLK, DT
byte v1[8] = {0x07,0x07,0x07,0x07,0x07,0x07,0x07,0x07};
byte v2[8] = {0x07,0x07,0x00,0x00,0x00,0x00,0x00,0x00};
byte v3[8] = {0x00,0x00,0x00,0x00,0x00,0x00,0x1F,0x1F};
byte v4[8] = {0x1F,0x1F,0x00,0x00,0x00,0x00,0x1F,0x1F};
byte v5[8] = {0x1C,0x1C,0x00,0x00,0x00,0x00,0x1C,0x1C};
byte v6[8] = {0x1C,0x1C,0x1C,0x1C,0x1C,0x1C,0x1C,0x1C};
byte v7[8] = {0x00,0x00,0x00,0x00,0x00,0x00,0x07,0x07};
byte v8[8] = {0x1F,0x1F,0x00,0x00,0x00,0x00,0x00,0x00};
int a[3],vol,vol_d,menu,in,dem,form;
byte i,d1,d2,d3,d4,d5,d6,e1,e2,e3;
unsigned long times,times1,oldPosition = -999,newPosition;
bool w,w1,www=1,mute;
byte dem_dac,dem_res,for_dac,for_res,err,err_old;
void setup(){
Wire.begin();
delay(100);
// Serial.begin(9600);
MsTimer2::set(3, to_Timer);MsTimer2::start();
lcd.init();lcd.backlight();
lcd.createChar(1, v1);lcd.createChar(2, v2);lcd.createChar(3, v3);lcd.createChar(4, v4);lcd.createChar(5, v5);lcd.createChar(6, v6);lcd.createChar(7, v7);lcd.createChar(8, v8);
lcd.setCursor(0,0);lcd.print("CS8416 00");lcd.print(wireRead(0x10,0x7F),BIN);
lcd.setCursor(0,1);lcd.print("CS4398 0");lcd.print(wireRead(0x4C,0x01),BIN);
delay(2000);
pinMode(10,INPUT);// SW
pinMode(11,INPUT_PULLUP); // кнопка MUTE
if(EEPROM.read(100)!=0){for(int i=0;i<101;i++){EEPROM.update(i,0);}}// очистка памяти при первом включении
vol = EEPROM.read(0);in = EEPROM.read(1);dem_dac = EEPROM.read(2);dem_res = EEPROM.read(3);for_dac = EEPROM.read(4);for_res = EEPROM.read(5);
// Write 8416
Wire.beginTransmission(0x10);
Wire.write (0x00);
//-------------------//
Wire.write (0b00000000);
Wire.write (0b10000010);// 128Fs
Wire.write (0b00000000 + (dem_res << 4));
Wire.write (0b00000000);
Wire.write (0b10000000 + (in << 3));
Wire.write (0b10000000 + (for_res));
Wire.write (0xFF);
Wire.write (0x00);
Wire.write (0x00);
Wire.write (0x00);
Wire.endTransmission();
// End Write ////////////////////////////////////
delay(10);
// Write 4398
wireWrite(0x4C, 0x02, 0b00000010 + (dem_dac << 2) + (for_dac << 4));
wireWrite(0x4C, 0x03, 0b00001001);// default
wireWrite(0x4C, 0x04, 0b11000000);// default
wireWrite(0x4C, 0x05, vol);
wireWrite(0x4C, 0x06, vol);
wireWrite(0x4C, 0x07, 0b10110000);// default
wireWrite(0x4C, 0x08, 0b01000000);// default
wireWrite(0x4C, 0x09, 0b00001000);// default
// End Write ////////////////////////////////////
lcd.clear();
}
void loop(){
/// MENU //////////////////////////////
if(digitalRead(10)==LOW){menu++;if(menu>3){menu=0;};delay(200);lcd.clear();www=1;}
/// MUTE /////////////////////////////
if(digitalRead(11)==LOW && mute==0){mute=1;wireWrite(0x4C, 0x04, 0b11011000);delay(300);www=1;}
if(digitalRead(11)==LOW && mute==1){mute=0;wireWrite(0x4C, 0x04, 0b11000000);delay(300);www=1;}
/// VOLUME ////////////////////////////
if(menu==0){
if (newPosition != oldPosition){oldPosition = newPosition;www=0;
vol=vol+newPosition;myEnc.write(0);newPosition=0;times=millis();w=1;w1=1;
if(vol<0){vol=0;}if(vol>99){vol=99;}
wireWrite(0x4C, 0x05, vol);
wireWrite(0x4C, 0x06, vol);
}
if(www==1||w==1){www=0;w=0;
if(mute==1){ lcd.setCursor(0,0);lcd.print("MUTE ");}
if(err==0&&mute==0){ lcd.setCursor(0,0);lcd.print("VOLUME ");}
if(err==22&&mute==0){lcd.setCursor(0,0);lcd.print("ERROR ");}
if(err==8&&mute==0){ lcd.setCursor(0,0);lcd.print("NO SOUND");}
lcd.setCursor(0,1);lcd.print("COAX ");lcd.print(in);
vol_d=99-vol;a[0]=vol_d/10;a[1]=vol_d%10;
for(i=0;i<2;i++){
switch(i){
case 0: e1=9,e2=10,e3=11;break;
case 1: e1=12,e2=13,e3=14;break;
}
switch(a[i]){
case 0: d1=1,d2=8,d3=6,d4=1,d5=3,d6=6;break;
case 1: d1=32,d2=2,d3=6,d4=32,d5=32,d6=6;break;
case 2: d1=2,d2=8,d3=6,d4=1,d5=4,d6=5;break;
case 3: d1=2,d2=4,d3=6,d4=7,d5=3,d6=6;break;
case 4: d1=1,d2=3,d3=6,d4=32,d5=32,d6=6;break;
case 5: d1=1,d2=4,d3=5,d4=7,d5=3,d6=6;break;
case 6: d1=1,d2=4,d3=5,d4=1,d5=3,d6=6;break;
case 7: d1=1,d2=8,d3=6,d4=32,d5=32,d6=6;break;
case 8: d1=1,d2=4,d3=6,d4=1,d5=3,d6=6;break;
case 9: d1=1,d2=4,d3=6,d4=7,d5=3,d6=6;break;
}
lcd.setCursor(e1,0);lcd.write((uint8_t)d1);lcd.setCursor(e2,0);lcd.write((uint8_t)d2);lcd.setCursor(e3,0);lcd.write((uint8_t)d3);
lcd.setCursor(e1,1);lcd.write((uint8_t)d4);lcd.setCursor(e2,1);lcd.write((uint8_t)d5);lcd.setCursor(e3,1);lcd.write((uint8_t)d6);
}}
}
//////// INPUT ////////////////////////////////////
if(menu==1){
if (newPosition != oldPosition){oldPosition = newPosition;
in=in-newPosition;myEnc.write(0);newPosition=0;times=millis();w=1;w1=1;
if(in<0){in=0;}if(in>7){in=7;}
Wire.beginTransmission(0x10);
Wire.write (0x00);
Wire.write (0b00000000);
Wire.write (0b10000010);
Wire.write (0b00000000 + (dem_res << 4));
Wire.write (0b00000000);
Wire.write (0b10000000 + (in << 3));
Wire.write (0b10000000 + (for_res));
Wire.write (0xFF);
Wire.write (0x00);
Wire.write (0x00);
Wire.write (0x00);
Wire.endTransmission();}
delay(10);
if(www==1||w==1){www=0;w=0;
lcd.setCursor(0,0);lcd.print("INPUT SELECTOR");
lcd.setCursor(0,1);lcd.print("COAXIAL "); lcd.print(in);lcd.print(" ");
}
}
/// DE-EMPHASIS //////////////////////////////////
if(menu==2){
if (newPosition != oldPosition){oldPosition = newPosition;
dem=dem-newPosition;myEnc.write(0);newPosition=0;times=millis();w=1;w1=1;
if(dem<0){dem=0;}if(dem>3){dem=3;}
Wire.beginTransmission(0x10);
Wire.write (0x00);
Wire.write (0b00000000);
Wire.write (0b10000010);
Wire.write (0b00000000 + (dem_res << 4));
Wire.write (0b00000000);
Wire.write (0b10000000 + (in << 3));
Wire.write (0b10000000 + (for_res));
Wire.write (0xFF);
Wire.write (0x00);
Wire.write (0x00);
Wire.write (0x00);
Wire.endTransmission();
delay(10);
wireWrite(0x4C, 0x02, 0b00000010 + (dem_dac << 2) + (for_dac << 4));
delay(10);
}
if(www==1||w==1){www=0;w=0;
lcd.setCursor(0,0);lcd.print("DE-EMPHASIS SEL");
lcd.setCursor(0,1);
switch(dem){
case 0: lcd.print("No De-emphasis");dem_dac=0;dem_res=0;break;
case 1: lcd.print("44.1 kHz ");dem_dac=1;dem_res=2;break;
case 2: lcd.print("48.0 kHz ");dem_dac=2;dem_res=3;break;
case 3: lcd.print("32.0 kHz ");dem_dac=3;dem_res=1;break;
}
}
}
/// Serial Format Select //////////////////////////////////
if(menu==3){
if (newPosition != oldPosition){oldPosition = newPosition;
form=form-newPosition;myEnc.write(0);newPosition=0;times=millis();w=1;w1=1;
if(form<0){form=0;}if(form>2){form=2;}
Wire.beginTransmission(0x10);
Wire.write (0x00);
Wire.write (0b00000000);
Wire.write (0b10000010);
Wire.write (0b00000000 + (dem_res << 4));
Wire.write (0b00000000);
Wire.write (0b10000000 + (in << 3));
Wire.write (0b10000000 + (for_res));
Wire.write (0xFF);
Wire.write (0x00);
Wire.write (0x00);
Wire.write (0x00);
Wire.endTransmission();
delay(10);
wireWrite(0x4C, 0x02, 0b00000010 + (dem_dac << 2) + (for_dac << 4));
delay(10);
}
if(www==1||w==1){www=0;w=0;
lcd.setCursor(0,0);lcd.print("FORMAT SELECT");
lcd.setCursor(0,1);
switch(form){
case 0: lcd.print("L-Just 24 bit");for_dac=0;for_res=0;break;
case 1: lcd.print("I2S 24 bit");for_dac=1;for_res=5;break;
case 2: lcd.print("R-Just 24 bit");for_dac=3;for_res=8;break;
}
}
}
////////////////////////////////////////////////////////
delay(100);
if(millis()-times1>1000){times1=millis();err = wireRead(0x10,0x0C);delay(10);}
if(err!=err_old){err_old = err;www=1;}
if(millis()-times>10000 && w1==1){w1=0;EEPROM.update(0,vol);EEPROM.update(1,in);
EEPROM.update(2,dem_dac);EEPROM.update(3,dem_res);EEPROM.update(4,for_dac);EEPROM.update(5,for_res);
menu=0;www=1;lcd.clear();}
}
void wireWrite(byte addr, byte reg, byte data){
Wire.beginTransmission(addr);
Wire.write (reg);
Wire.write (data);
Wire.endTransmission();
}
byte wireRead(int addr, int reg){
Wire.beginTransmission(addr);
Wire.write (reg);
Wire.endTransmission();
delay(10);
Wire.requestFrom(addr,1);
while(Wire.available()<1);
byte value = Wire.read();
return value;
}
void to_Timer(){newPosition = myEnc.read()/4;}