INTRO

This blog has been sort of a notebook for me to write down my own learning with Arduino and the TPA boards. Therefore the information presented assumes that the reader’ is learning at a pace equal to mine.

Beginners are overwhelmed with the amount of information here so this post is to help those by outlining the basics of building a controller board for the superb kits produced by Russ and Brian of Twisted Pear Audio. TPA is also developing a controller for their products so this is an alternative to their solution utilizing low cost, and widely available parts. (As of July 2011  April 2013, the TPA controller board in not yet available, so this is the only “ready-to-run” option)

Basically, all modern audio chips have a software interface and they communicate with a micro-controller through a communication protocol called “I2C”. I have chosen the Arduino platform because I am not a programmer and Arduino is geared towards that audience. In addition, the Arduino community provides a lot of help for beginners and non-programmers.

HIFIDUINO is about building a controller that can talk to those audio chips. So far I’ve interfaced to the OPUS DAC with the WM8741 and the Buffalo II boards. But the same platform can be used to interface to other chips such the WM8804 spdif interface and even the brand new TI PCM51x2 DACs with lots and lots of features that are available only through s/w programming.

The controller consists of:

Arduino board

NOTE: if you use Arduino UNO R2, there is a potential bug: http://hifiduino.wordpress.com/code/#comment-718

Any official board or clone will work. The current (v.09) code size is about 14K bytes, so even the bottom of the line Arduino will work. All of he following models work: UNO, Dueminalove, Seeeduino v.2.2, NANO and others. I have used the UNO and the Dueminalove. I have even used the Freeduino. If you want to be dead sure that it will work, then purchase the latest official Arduino UNO (R3 or above)

The Freeduino with a companion stationary shield

Rotary encoder

The rotary encoder is used to change volume and settings. In theory, you can use any “quadrature” or “gray code” encoder. However, I find that the preferred characteristics of the encoder are:

  • About 30 cycles per turn. This gives a good “feel” when changing the volume, changing 30 db per revolution -not too fast or too slow
  • Built-switch. The switch is used to change from volume control to DAC settings control. This is not mandatory, you can implement with a separate switch
  • A rotary encoder with “clicks” is preferred because you can feel the clicks when you select the different settings. I tried a rotary encoder without “clicks” and it does not work well because selection of the different settings take advantage of pushing the encoder to activate the switch. Often one you push the switch you can also inadvertently move the encoder. Rotary encoders without detentes (“clicks”) are not recommended.

I use a Panasonic model that has been discontinued, but available from Electronic Goldmine. Other candidates are: Bourns PEC11, BI EN12. The current version of the code (v.09) does not require that you build a debouncing circuit as the debouncing is done in the software (I had used the rotary encoder without hardware debouncing or a long while, but I finally added the debouncing capacitors).

  • More on debouncing: link
  • Here I recommend the “most suitable” rotary encoder: link

LCD display

The code assumes a 20×4 LCD. Any LCD that is compatible with the HD44780 protocol will work with the code: Do a search for “20×4 LCD HD44780″ on eBay. The one I purchased is from Sure Electronics. You can also purchase directly from their website: [link]. Nowadays it is available pretty much everywhere. Here is another good source: iTeadStudio

As it turned out, a larger portion of the code is the user interface and it assumes a 20×4 LCD. Thus, if you use a different form-factor LCD (for example a 16×2 LCD, you will have to overhaul a lot of code.

NOTE: if you use Arduino UNO R2, there is a potential bug: http://hifiduino.wordpress.com/code/#comment-718

IR receiver and a remote control

The code supports the Apple Aluminum Remote. Any IR receiver should work. However, I would recommend the Vishay TSOP32438 because it is designed for the 38KHz frequency used by the Apple Remote. The 32438 model also provides noise immunity. Additional information: [link]

Here is a good article on “how to choose IR receiver”: [link]

In fact, any one of these would work:

TSOP32338SS1V

TSOP32438SS1V

TSOP38238SS1V

TSOP38338SS1V

IR

A level converter from 5V to 3.3V for the I2C lines


This part maybe optional. As the I2C inputs of the Buffalo are “supposed to be” 5v tolerant, but the data sheet does not say specifically and I have not determined that to be the case with 100% certainty. (You can easily build it if you do not wish to buy the module)

You can build your own level shifting by following this diagram from this document [link]

levelShift

I Made my own here: [link]

levelshifter

GET GOING

The best use of this project is for you to experiment with your own choice of components and ideas. You can reuse whatever part of the code you wish (as I have reused code from other contributors. -This is the spirit of open hardware and software of the Arduino community). If you do this you will find that the audio hobby is not just about changing cables, capacitors and power supplies :-)

However, if you wish to just replicate what I have done, this is what you do:

  • Get familiar with the Arduino development environment. At the minimum you must know how to compile code and upload to an Arduino. The Arduino tutorials listed in the side bar are a good start.
  • Procure the parts above and hook them up according to the different hookup diagrams in this blog. The current code does not require that you build a debouncing circuit for the rotary encoder so you can skip the debouncing circuit
  • Download the latest version of the code from the code tab. Compile and Upload to the Arduino
  • Done!

This is what my controller looks like:

User Interface summary

Here is a very nice summary of an older (v. 09) user interface from マルチチャネルDAC製作記 blog and in particular this post [link]

I have updated the user interface a bit: http://hifiduino.wordpress.com/2012/01/09/code-compatible-with-arduino-1-0/

Newer versions are a refinement. But the overall user interface is pretty much the same

NOTE: if you use Arduino UNO R2, there is a potential bug: http://hifiduino.wordpress.com/code/#comment-718
EASY ORDER (DIGIKEY)

Arduino UNO R3: 1050-1024-ND [link]

ANOTHER IMPLEMENTATION

Here is another implementation of the controller with a hand made Arduino “shield” to facilitate connections: LCD, Arduino, shield, rotary encoder and IR receiver.

DSC03397

DSC03388

The shield has the following components:

  • 5V to 3.3 Level translator with external pull up resistors (1.5K ohm) and local 0.1 uF power supply (5 and 3.3V) bypass. This will ensure clean I2C signals. External pull ups may or may not be required. Depends on your environment.
  • Potentiometer for LCD contrast adjustment
  • Potentiometer that adjust the current to the base of a transistor controlling the brightness of the LCD
  • Arduino reset button (since the reset button of the Arduino is covered by the shield)
  • Underneath, I had implemented a debouncing circuit for the rotary encoder. The code does not need the hardware debouncing circuit since it uses s/w debouncing, but it does not hurt.

DSC03389

The external 1.5 Kohm I2C pull up resistors were added afterwards to solve a noisy I2C connection. In most cases, the internal pull-up resistors or the pull-up resistors built-in in the level translator board should be good enough. I had also added power supply bypass capacitors to further clean up the I2C lines.

DSC03401

The h/w debounce circuit was built in accordance to a BOURNS “Signal Conditioning Technical Note” paper [link]. This is not required by the current version of the code because s/w debouncing is used. However, it is always a good idea to reduce spurious interrupts.

DSC03402

Connecting the LCD

DSC03391

DSC03390

DSC03392

Connecting the rotary encoder (with switch)

DSC03393

I find this rotary encoder very good. With solid clicks and good feel. You really need a rotary encoder with “clicks” because it is also used to make adjustment. I had also used an encoder without clicks and as you push the encoder to actuate the switch and make selections, you would also slightly rotate the encoder making inadvertent adjustments.

More info on rotary encoders:

  • More on debouncing: link
  • Here I recommend the “most suitable” rotary encoder: link

DSC03387

Connecting the IR receiver

DSC03396

  1. Michael
    2012/08/30 at 19:52

    Hi! Great blog just burned the last 2 hours reading your posts.

    Even though I have some experience with Arduinos and a little with DACs (working in a laboratory) I was wondering if you could recommend a easy guide of a full built to get started (including some links where to order stuff).

    Thx in advance

    Michael

    • BlogGeanDo
      2012/08/30 at 21:57

      I enjoyed writing the blog :-)
      The information here tells you what to buy and where…

    • BlogGeanDo
      2012/08/31 at 06:13

      The software described here works with the buffalo DAC. You can check http://www.twistedpearaudio.com

  2. Anonymous
    2013/02/08 at 13:07

    Hi, this is fantastic! Thanks for posting all this. I want to build my own 5v – 3.3v converter and see in the above photo that you have done the same. Can you point me in the right direction to a circuit diagram or list of components etc?
    Cheers!

    • BlgGear
      2013/02/08 at 17:29

      Added info in the post…

  3. f. arhun
    2013/05/27 at 03:21

    Hi GLT, Your work here is much appreciated as in diyaudio. Thanks a lot!
    I’ve added “the system” to my diyinhk es9018 v.5 DAC. I use sainsmart uno R3 with large 20×4 LCD. Nothing has any frills! I made hifiduino successfully work in a way, only with one problem: the DAC requires reset once hifiduino starts, and each time when something is attempted to be changed (such as volume and other settings) through the remote or rotary encoder. Some basic nut or bolt is loose I suppose!!

    If you have any insight what might be the culprit or which direction should I look will be very helpful.

    Thanks in advance.

    • BlgGear
      2013/05/27 at 21:57

      Tell me more. What happens right after you power both the DAC and Arduino. Usually you can start them at the same time. If you can externally mute the outputs, you can startup the DAC first and then Arduino. Also, I would recommend having all the wiring as twisted pairs (I2S and I2C) and make sure no wires crosses over the DAC chip

  4. f. arhun
    2013/05/28 at 02:04

    Thanks for your answer. At the moment I have seperate power supplies for the DAC and Hifiduino unit with seperate switches, but starting them at the same time will not be a problem and eventually it will get the power from DAC psu. The problem with any interaction of Hifiduino with the DAC causing stalling I think may be due to current I2C wiring, which I haven’t tried to perfect it yet. Do you think using pull up resistors on SDA SCL lines will be any help? My DAC is very clean, with all seperate Salas shunt regulators after two stage inline regulation, etc. although everything is still on test setup, with minimized and careful wirings. I’ll try powering up both units at the same time and work on I2C line and I’ll post more info later

    Thanks again.

    F. Arhun

  5. Moltke
    2013/05/31 at 04:20

    I also made me a small system with a DIYHK PCB. :)
    No leveltranslater used, because the DAC’s I2C pins are 5V convertible.

    I use an I2S signal, and I can see the samplerate is changing on the display (Means the system is communicating with the DAC and I’ts running), but I can’t measure any output of the DAC. I use 100 ohms resistors on the output, but I assume I should be able to measure something else than a DC voltage?

    Do I need to remap the DAC different compared to the BII DAC?
    Great page btw.

    • BlgGear
      2013/06/01 at 17:19

      If you are using the I2S inputs of the diyinhk board, there is nothing to change. How are you measuring? Unless you have an oscilloscope, it is not easy to measure music with a voltmeter…

  6. WT
    2013/06/15 at 13:47

    I just found your great block. I wonder if your code can be used with Buffalo 32s

    • BlgGear
      2013/06/15 at 17:20

      I believe it should work as is. Just try it.

  7. wt
    2013/06/17 at 07:05

    Thanks. Order Arduino board and other parts already. Should be fun.

  8. Wt
    2013/06/18 at 16:37

    Just finish asambly but can not control the dac. On display board, it show no lock in up right corner. But the system play music as usual. The Buffalo 32s is locked to Mac mini using itune and audirvana plus fine. Could you please guide me to the right direction.

    • BlgGear
      2013/06/18 at 17:55

      Did you remove the microprocessor in the B32S? only one microprocessor can control the board.

  9. wt
    2013/06/19 at 03:54

    I did. First time that I connected I have not remove the microprosessor in Buffalo32S and Arduino just freeze, the screen show all white. Then I turn everything off and remove microprocessor in Buffalo32S and connect again, Arduino turn on normal with welcome screen and display response when I turn encoder. I try both open and shut Address pin on buffalo32S with no effect. I have not connect the IR receiver thought.

    • BlgGear
      2013/06/19 at 07:20

      So the chip is not responding at all. The default address is “open pin”. Ensure the I2C wires are correct. Also need to connect GND between Arduino and DAC. Can you post some photos somewhere?

  10. Wt
    2013/06/20 at 03:52

    I2c wires are checked. Ground is connect. Let try picture. https://www.dropbox.com/s/mj2q0djhi08cul1/Photo%2019-6-2556%2C%2021%2048%2019.jpg

  11. Wt
    2013/06/20 at 03:53

  12. Wt
    2013/06/20 at 03:58

    I first connect with level converter that I order. But last night I build it my own because I thought the level converter was not function but that was not the case
    Picture https://www.dropbox.com/s/zkosq9gmdqhqjd3/Photo%2019-6-2556%2C%2021%2049%2050.jpg

    • BlgGear
      2013/06/20 at 04:39

      Can’t see anything that is obviously wrong. Things you can try:
      – Use the older Arduino 1.0 (I have not upgraded the Arduino IDE to the latest one)
      – Try adding pull ups to the I2C. (I have used 1.5K pull ups in noisy environments)
      – Flip the I2C wires
      – See if the I2C lines are indeed connected to the chip (I suppose you have the datasheet)
      – If the Arduino does not freeze, and changing the volume does nothing, then either the Arduino is not communicating or the DAC is not responding – I have never experienced this. Typically if you have noise in the I2C, the Arduino would hang…
      – In theory, there is no difference between any of the Sabre32 DACs. I’ve heard people using it with BII, BIII, Acko, diyinhk and QuangHao DACs
      – Good Luck!

  13. Wt
    2013/06/20 at 07:30

    It works now!!!. Flip the i2c wire works. May be Buffalo32s have a mistake in printing.
    Thank you so much in helping me figure this out. Really appreciate your help.

    • BlgGear
      2013/06/20 at 15:07

      Enjoy!

  14. 2014/02/20 at 21:45

    How does one contact with you about a project I see here.

    This is quite exciting to me –

    HiRes SD Card Player: SDTrans192 v. 3.0

    Thank You,

    Mark

    • BlgGear
      2014/02/21 at 01:24

      That project belongs to Mr Bunpei at diyaudio.com

  15. sebastian
    2014/08/05 at 14:58

    If I turn the volume al the way up to 00, without a DAC connected, this value is stored in eprom right? because If I power up the adurino it’s back to 50

    • BlgGear
      2014/08/08 at 04:22

      This is how the code works. The volume is not remembered. Every time it starts with a default value. The Default value can be changed.
      This is to prevent starting up with a high volume if you were listening to high volume before…

  16. Derek
    2014/08/30 at 23:43

    Was thinking of using an Adafruit Pro Trinket 3V 12MHz board but they don’t have pins 2 and 7 available. Is it possible to reassign your pin 2 and 7 functions to, say, pins 6 and 13?

  17. Derek
    2014/09/02 at 18:20

    Have had a look at the code and believe that, although I’m new to this, I can take a stab at altering the pins. Only doubt is, I read a comment saying pins 2 and 3 are interrupts; so if 2 is not available on the Pro Trinket and I have only one interrupt pin, am I sunk?

    Haven’t got all the bits yet but will take a shot at it unless you say it can’t be done with the Pro Trinket. I need a small footprint controller to fit it all in.

    • BlgGear
      2014/09/05 at 22:54

      I am only using one interrupt. You will have to use that interrupt pin for the rotary encoder.

  18. Derek
    2014/09/06 at 13:17

    Okay, thanks. Once I get everything I’ll report progress. And thanks for the project.

  19. Derek
    2014/09/17 at 01:10

    Got it to work with the Adafruit Pro Trinket 3V. Minor alterations to the code for the LCD pin inputs and interrupt. Also, because the Pro Trinket is 3V there’s no need for level converters with the diyinhk K2M. Used an Adafruit quarter-size perma-proto board so it’s a very small footprint.

    Used with an Alix SBC using Voyage MPD and a Class D module to make an ‘all-in-one’ music server/remote controlled volume control/amplifier unit that fits on an 11×16 base – including linear power supplies.

    As it’s the first time I’ve ever used any kind of microcontroller or code I’m grateful for the extensive blog and explanation on the code – much appreciated. I’m old enough to still be amazed by what people will share on these blogs. Tip of the hat to you, sir.

    Only issue so far is that when I first plug it in the volume is really loud until I move the rotary encoder or touch the Apple remote. Will go through the code and blog again as I recall seeing something about muting the DAC on startup. May also just require stopping the music server before powering down so it does not boot with music playing – although that’s not always under our control!

    Thanks for a great project.

    • BlgGear
      2014/09/21 at 23:45

      The issue is that when the micro-processor is programming the registers (eg setting the volume), the DAC is not ready. If you turn the DAC first, then it will be at full volume. But when the microprocessor starts it is able to program the registers and lower the volume. In the past turning on both the DAC and the microprocessor at the same time (at least with the regular ES9018 DAC), the DAC seems to start just a tiny bit faster than the microprocessor, so that you get loud volume for a fraction of a sec and then the microprocessor sets the volume to the default value.

      The solution for this is not to have any active source during startup.

  1. No trackbacks yet.

Leave a Reply

Fill in your details below or click an icon to log in:

WordPress.com Logo

You are commenting using your WordPress.com account. Log Out / Change )

Twitter picture

You are commenting using your Twitter account. Log Out / Change )

Facebook photo

You are commenting using your Facebook account. Log Out / Change )

Google+ photo

You are commenting using your Google+ account. Log Out / Change )

Connecting to %s

Follow

Get every new post delivered to your Inbox.

Join 205 other followers