Show Posts
Pages: 1 2 3 [4] 5
46  Forum 2005-2010 (read only) / Interfacing / Re: using more than 8 leds on: April 02, 2008, 12:15:11 am
According to the datasheet, (pages 304+) each pin can source 40mA. As for maximum current for the whole chip, I can't tell. :|
If you want to drive the LEDs from a constant power source rather than the Arduino but still control them, you can use some transistors and use the Arduino's I/O pins to switch the current flow through the LEDs on and off. You'd be looking at wiring them up as illustrated here:
Of course, you don't need to have 4 LEDs, or you can have more... It's up to you - and how much current the transistor you use is able to handle without bursting into flames. smiley-razz

To handle more than 16 LEDs, you're going to have to either purchase I/O expanders, like the Microchip MCP23008 (one I'm using) that will add more I/O lines to your Arduino, or do some tricky multiplexing as illustrated here: Though it shows you how to use an LED matrix, you can wire up your LEDs in a similar way to achieve the same end.

EDIT: Seems I missed a part of the datasheet... Seems the total output current for the analog pins (which can double as output pins), plus pins 0-4 should not exceed 150mA, and the total output current for pins 5 - 13 should not exceed 150mA. I'd try to stay below that as much as possible though, but that's just me, and I'm paranoid. ;p
47  Forum 2005-2010 (read only) / Interfacing / Re: Wire library on a device address >  than on: March 16, 2008, 05:45:07 pm
I'd assume it's some sort of buffer thing... Wire sticking the data you're writing out into the buffer, sends it along the wire, and then waits for a read. When it doesn't receive any data, it passes back whatever is in the buffer... which happens to be exactly what you wrote in. ... I could be wrong though, but this would sort of make sense as to why we get data out instead of a failure (which would be preferable in this case.)

Anyway. Good luck with your project! (:
48  Forum 2005-2010 (read only) / Interfacing / Re: Wire library on a device address >  than on: March 16, 2008, 12:35:12 pm
I2C addresses consist of only 7 bits. The last bit is Read/Write - Write when 0, read when 1. So, if you have a data sheet that says the address of a device is 0xA4, likely that's the Write address. The Wire library is poorly documented on this, but you have to pass the device address, which is the top 7 bits. So your A4 will become 0x52 and the Wire library will figure out whether you want the read or the write address.

So, to answer your question, the 7 bit address B1010010 will be made into B10100100 for writes to the device and B10100101 for reads from it, while the 8-bit address I couldn't say what would happen... probably that it will get made into an incorrect 9-bit address. Wire's functions expect the 7-bit device address - without the Read/Write bit.

I had a _lot_ of problems with I2C until I figured this out. I was trying to read input from an I/O expander, and the data that was getting read back to me was exactly what I had 'written' to the device moments before, but the voltage of the output pins reflected otherwise. So, although it may appear to be working properly, the device hasn't actually received any data. It really frustrated me, because this little 'quirk' is documented nowhere on the Arduino or Wiring site. I had to read about it on a blog somewhere on the internet.
49  Forum 2005-2010 (read only) / Interfacing / Re: RGB LEDs on: March 14, 2008, 01:25:20 pm
It depends. Do you want to drive each LED individually, or in 3 groups?
50  Forum 2005-2010 (read only) / Interfacing / Re: External Power Supply Matrix on: February 29, 2008, 12:54:46 pm
You'd only really need the transistor at one place in the circuit. Since current only flows when there is a complete path, one break is enough to prevent it moving.... The short answer is that it should work with only your NPN transistor before ground.

... Just make sure you connect your arduino pin to base, and connect both grounds. (:
51  Forum 2005-2010 (read only) / Interfacing / Re: SD-20 ic controler on: March 07, 2008, 09:11:56 pm
The I2C bus is also called the TWI (Two-Wire Interface) in the ATmega168 data sheets.

Lucky for you, the Arduino environment comes with a library that implements all the tricky stuff for you. It's the Wire library. You can probably do a search of the forum to pull up any other info you might need on it. (:
52  Forum 2005-2010 (read only) / Interfacing / Re: Interrupt multiplexing with MCP23008 on: February 17, 2008, 02:20:32 pm
Yup. The Arduino 5V and Ground are the only power connections I have in this circuit.
53  Forum 2005-2010 (read only) / Interfacing / Interrupt multiplexing with MCP23008 on: February 16, 2008, 07:33:02 pm
I'm having an issue with handling multiple interrupts. I have a Microchip I2C I/O expander connected to my Arduino board. The INT pin of the MCP is connected to pin 2 on the Arduino (Interrupt 0), and the I/O pins on the MCP are connected to switches and other junk that I want to capture interrupts from. This side works fine, they're all working properly. The Interrupts on the Arduino are enabled, and it works if I ground the line myself... the problem is that the MCP23008 should be doing this itself. I've gone through the data sheet several times, trying to figure it out, and I just can't seem to make it all work properly.

Can anyone offer any advice/suggestions? Here is the code I'm using. The Lcd functions are in a separate file, work perfectly fine by themselves, and don't touch anything except LCD pins and such.  : |

/* Alarm clock "Proof of concept"

#include <Wire.h>      // I2C library from Wire.
//#include <avr/pgmspace.h>  // Program memory from Atmel
#include <stdio.h>     // printf and family

--               LCD communication pin definitions               --
const int int_pin = 2;   // Pin Arduino is using Interrupts on
const int lcd_rs = 3;    // RS pin of LCD
const int lcd_rw = 4;    // R/W pin of LCD
const int lcd_en = 5;    // Enable pin of LCD
const int lcd_db[] = {6, 7, 8, 9, 10, 11, 12, 13}; // LCD data pins
const int lcd_db_size = 8;  // # data pins in array

--                      Strings and buffers                      --
char string_buffer[17];     // 16 characters + null
const char str_12hr_time[] = "   %2x:%02x:%02x%cM   ";
const char str_24hr_time[] = "    %02x:%02x:%02x    ";
const char str_date[]      = "  %3s, %3s %02x  ";
const char str_weekday[][4] = {"Sun", "Mon", "Tue", "Wed", "Thr", "Fri", "Sat"};
const char str_months[][4]  = {"Jan", "Feb", "Mar", "Apr", "May", "Jun",
                                 "Jul", "Aug", "Sep", "Oct", "Nov", "Dec"};

--                    Interrupt Shennanigans                     --
volatile bool int_flag;         // Place to hold interrupt flag
byte int_mask;                  // Bit mask of each interrupt line that was toggled.
const byte int_active = B00011111; // I/O expander lines with something that triggers interrupts

// Interrupt service function
void Interrupt()
  // All we need to do is indicate that an interrupt's been fired.
  int_flag = true;

// Setup junk.
void setup()
  // Set up I2C first.
  pinMode(2, INPUT);
  // Configure RTC for 1Hz Clockout
  // Set up the I/O Expander to produce interrupts
  // Fire up the LCD
  Wire.requestFrom(0x51, 11);
  while (Wire.available())
    Serial.println(Wire.receive(), BIN);
  // Start interrupts to falling edge
  attachInterrupt(0, Interrupt, FALLING);

// The main guts.
void loop()
  // Check if an interrupt has fired.
  if (int_flag)
    // Clear the interrput flag now - if our routine takes too long, we might (will) miss
    // the next interrupt, which WILL diddle things up.
    int_flag = false;
    // Get data from the I/O expander to see which buggers fired.
    Wire.requestFrom(0x20, 2);
    Serial.println(int_mask = Wire.receive(), BIN);
    Serial.println(Wire.receive(), BIN);
    // Do ... something.
    if (int_mask & 0x01)
      byte sec, mins, hrs, day, wkd, mth;
      // CLKOUT fired. Update LCD.
      Wire.requestFrom(0x51, 6);
      sec = Wire.receive() & B01111111;
      mins = Wire.receive() & B01111111;
      hrs = Wire.receive() & B00111111;
      day = Wire.receive() & B00111111;
      wkd = Wire.receive() & B00000111;
      mth = Wire.receive() & B00011111;
      // Write new time
      sprintf(string_buffer, str_24hr_time, hrs, mins, sec);
      sprintf(string_buffer, str_date, str_weekday[wkd], str_months[mth - 1], day);
      LcdSetPos(1, 0);
54  Forum 2005-2010 (read only) / News / Re: Arduino 0011 released. on: April 01, 2008, 01:13:54 pm
The macro is need any where you would have previously used as a cast.  It allows people to avoid learning the cast syntax.
I think I can see where you're coming from, trying to make things easier for newbies, but I think the casting syntax isn't that complicated that it should need a macro.

Are there any intro-level tutorials for writing C/C++ on the Arduino on the site anywhere? Perhaps if there were some basic C tutorials available, macros like this wouldn't be needed, as the tutorials should cover basics like casting.
55  Forum 2005-2010 (read only) / Frequently-Asked Questions / Re: Assemler results, where? on: April 11, 2008, 07:07:57 pm
You can use the avr-objdump utility with the -S option (I think) on a .hex file to disassemble your sketch. Using it on a .elf file will let you see your C++ inline with the assembly. Can't recall that option off the top of my head.
56  Forum 2005-2010 (read only) / Frequently-Asked Questions / Re: Handbook/Guide of common ICs? on: August 03, 2008, 10:24:56 am
I've used this site:
It has a listing of a bunch of common 4000 series CMOS chips.
57  Forum 2005-2010 (read only) / Frequently-Asked Questions / Re: Write to pgmspace? on: June 25, 2008, 01:24:23 pm
then have your Arduino drive its own RESET low to reset itself.
I'm too lazy to double check this now but I seem to recall attaching to your own reset line is specifically "prohibited" by Atmel. Or maybe it was something else...
Maybe it was having something on the reset line when using the AVR Dragon or a similar debugger? For those, Atmel says the debugger needs full control of the line, and having a capacitor or something else on it will bugger with things.
58  Forum 2005-2010 (read only) / Frequently-Asked Questions / Re: Changing the clock speed? on: May 17, 2008, 11:11:45 am
How can I get the bootloader on the actual microcontroller to accept a 20Mhz crystal to I can upload sketches through my USB port as I used to?

The bootloader has no control over clock speed. Just swap out the 16MHz crystal for the 20MHz, and the ATmega will run at 20MHz. The bootloader has no way of telling what speed it is running at so you don't need to worry about what speeds it will "accept".
One thing you will have to watch out for is that the different clock speed will mess with delay, delayMicroseconds and millis.
59  Forum 2005-2010 (read only) / Frequently-Asked Questions / Re: Relays and SSR's?? on: April 27, 2008, 02:44:21 pm
You could use a shift register, or an I/O expander, or come up with a trickier way of multiplexing.
60  Forum 2005-2010 (read only) / Frequently-Asked Questions / Re: powering large numbers of LEDs on: April 20, 2008, 01:49:52 pm
You can use a transistor to drive the LEDs, as you said. A transistor is essentially the same thing as a relay, except that relays isolate the switching and switched current/voltages. But since LEDs run on DC and are similar voltages anyway, a transistor would be just fine. There's some schematics for that in the playground somewhere.
Pages: 1 2 3 [4] 5