Triple Axis Magnetometer HMC5883L + Arduino

Monday, February 27 th , 2012

One of the first articles we did was on the hmc6352 digital compass. Well this is his older brother (or younger but smarter). I really don’t know what to say about the HMC5883L other than it is a three axis magnetometer, so it is capable of sensing in 3 directions.

That doesn’t mean that it is tilt compensated, because you really don’t know how it is orientated when the reading comes in. For that, you would need to combine this with an accelerometer to do that. But this can get you one step closer. If you are looking at using this as a digital compass, make sure to read the following section.

Magnetic Declination

Something I found interesting and obvious once I thought about it, is that all compasses point to magnetic north, and not true north. The difference between them is called Magnetic declination. And how much they vary depends on where you are, and… when it is, because as weird as it is, it changes over time (awesome animation of that). You can look up your Magnetic declination here.

Hooking it up

Hooking you HMC5883L up to your arduino is pretty simple. The HMC5883L is an I2C device, a type 2-wire serial connection, so we just need to connect the SDA (Data) and SCL (Clock) lines to your Arduino for communication. On your Arduino (everything but the mega) SDA is on analog pin 4, and SCL is on analog pin 5. On an arduino mega, SDA is digital 20, and SCL is digital 21. (The Arduino Leonardo will also be different). Other than these 2 lines, we just need to connect power(3.3v), ground and we are all set.

Code

The code for the HMC5883Lis a bit more complex than his single-axis brother, and the readings from it come in a few different forms, so we will be using a library to achieve this.

To make this code work, before you load the code, or even open the Arduino program, we need to place the “HMC5883L” folder into your Arduino Library. If you don’t know where that is by default, Look to the right.

If you click the download button to the right of “Arduino” you can download the whole thing as a zip, so you dont need to copy all the files.

Default Library Folder Location

On your Mac:: In (home directory)/Documents/Arduino/libraries
On your PC:: My Documents -> Arduino -> libraries
On your Linux box:: (home directory)/sketchbook/libraries

Tilt Sensing with the RPI-1031 + Arduino

Tuesday, February 14 th , 2012

Once in a while something comes out that I think is going to be really awesome, but when you get it, it is just so so. Im sure you all know what I mean… But yeah… This is one of those.

The RPI-1031 available from sparkfun is a pretty simple (heck, it is dead simple) sensor for sensing when it is tilted. And it does this really well. But it seriously only does that. If it is not tilted, it freaks out and reports tilt anyways.

It actually just uses a metal ball that rolls around inside (you can hear it moving around when you tip it). Because of how it is made, the ball is always up against one side even when it is flat. Unfortunately this means you can never know the difference between a reading, and it being flat, only changes in reading.

Hooking it up

This is as simple as it gets I guess. Just power and ground, then connect the 2 digital pins and you are done. These 2 digital pins will output LOW/LOW, LOW/HIGH, HIGH/LOW and HIGH/HIGH depending on the wall it is touching. Again, even if it is flat, it is still touching a wall.

Code

The code for this guy is really simple, it just checks 2 pins, to see what side is being touched – The simple function just takes the 2 digital outputs and returns 0,1,2 or 3 depending on the side.

//For the RPI-1031 - http://www.sparkfun.com/products/10621 

int tilt_s1 = 2;
int tilt_s2 = 3;

void setup(){
 pinMode(tilt_s1, INPUT);
 pinMode(tilt_s2, INPUT);
 Serial.begin(9600);
}

void loop(){
  int position = getTiltPos();
  Serial.println(position);
  delay(200); //only here to slow down the serial output
}

int getTiltPosition(){
   int s1 = digitalRead(tilt_s1);
   int s2 = digitalRead(tilt_s2);
   return (s1 << 1) | s2; //bitwise math to combine the values
}
Unless otherwise stated, this code is released under the MIT License – Please use, change and share it.