Hello,

I have been using a MAG 3110 magnetometer to try and find the readings on three axis. However, when I used the sample magnetometer program that gets the basic reading from the sensor using Wire.h, I get readings way off the charts, especially for the x-axis.

Ranges from one run: x: 64945 - 64337 y: 24092 - 670 z: 1152 - 994

Ranges from second run: x:64917- 64375 y:1016 - 481 z:1165 -1030

I've programmed in a manual scaling to get ranges close to 0, however x is still abnormally high. Since it is a 16 bit processor, the max x can go is 65536, and it is pretty close to that point. Could you please explain to me why x is so high and how to fix it / get it into the correct range? Any help would be appreciated.

Thanks :) -AtomicDragon

"X-axis, Y-axis, and Z-axis 16-bit output sample data of the magnetic field strength expressed as signed 2's complement numbers."

The outputs are 16-bit SIGNED integer (int).

64945 is actually -591 and 64437 is actually -1119.

These are much closer to the 0 you desire.

Since the readings are in tenths of a microTesla and the earth's magnetic field is on the order of 50 microTesla you should expect your reading to vary +/- 500 as you rotate relative to the earth's magnetic field.

You also have to provide zero compensation since the sensor has a zero-flux offset of up to 10,000.

Thank you for the quick response

I see that it is a signed 2’s complement number, and your explanation makes sense. The signed is to allow for negative numbers and the range between the numbers make sense.

However its still strange that x is so far from y and z. I looked up the direct feed from the MSB and LSB of each output and I found the x MSB to be 252 while the y and z were 3 and 4. The LSB of all three sensors ranged from 0 - 250ish. These numbers include rotating the device in all directions.

Why is x at 252 while y and z are around 3? still a bit confused.

Thanks
-AtomicDragon

Here is the code for finding the value of x. I took it directly from the sample code. Am I doing anything wrong?

{
int xl, xh; //define the MSB and LSB

Wire.beginTransmission(MAG_ADDR); // transmit to device 0x0E
Wire.write(0x01); // x MSB reg
Wire.endTransmission(); // stop transmitting

delayMicroseconds(2); //needs at least 1.3us free time between start and stop

Wire.requestFrom(MAG_ADDR, 1); // request 1 byte
while(Wire.available()) // slave may send less than requested
{
}

delayMicroseconds(2); //needs at least 1.3us free time between start and stop

Wire.beginTransmission(MAG_ADDR); // transmit to device 0x0E
Wire.write(0x02); // x LSB reg
Wire.endTransmission(); // stop transmitting

delayMicroseconds(2); //needs at least 1.3us free time between start and stop

Wire.requestFrom(MAG_ADDR, 1); // request 1 byte
while(Wire.available()) // slave may send less than requested
{
}

int xout = (xl|(xh << 8)); //concatenate the MSB and LSB
return xout;
}

atomicdragon: Why is x at 252 while y and z are around 3? still a bit confused.

Well... a high byte of 252 would be about -1024 so that's fairly close to a high byte of 3 which would be 768, especially since anything within +/-10,000 would be a valid zero.

Measure the maximum and minimum values for all three axes as you turn the magnetometer in all directions. Then find the mid-pint between the high and low and use that for your zero offset. Subtract that from your readings.

Thank you for your responses :) you have been a great help to me. I think I have it now, but if I get any more problems I'll post them.

Thanks! -AtomicDragon

Let me just jump in this as I to have a problem finding out what is what regarding the data coming from this magnometer.
To simplify my little question I will tell you that I’m doing this with the data:

and then

var m = ((Int16)XAxis)/10;

And get something like ± 3500…

I really don’t get this! (And I need to;))

``````var m = ((Int16)XAxis)/10;
``````

What is a "var", and what is an "Int16"?

I really don't get this, and I need to.

A var is a data-type that can contain a wide variate of objects and can be used by implicit casting. (Nice to have when dealing with different data-types mixed together.

And "Int16" is a signed Integer.

Aaaaand the values I get out if MAG 3110 is for me right now about a hundred times to high (or low)... That means that I'm not really getting this;)

Ned help! ugently! :fearful:

A var is a data-type that can contain a wide variate of objects and can be used by implicit casting. (Nice to have when dealing with different data-types mixed together.

And "Int16" is a signed Integer.

So, we're not talking about Arduino here, are we?

We're talking about something similar: Fez Domino. Not really that much difference. Fez is Arduino-compatible and runs dot.net.

But the issue is the same and I to don't really get those values from this 3-axis sensor... :astonished:

Have you asked your question at the Fez Domino or dot.net fora?

Did you post all your code there, and if so, why not here?

Well... I found this topic and that we have the same problem. There's nothing to understand the difference between platforms, this is an issue regarding signed integers and understanding the MAG3110.(This thread)

Would you be happier if I told you that I'm also a user of Arduino, Basicstamp and a lot of MicroChip gadgets? ;)

I feel tempted to just divide the data with 100 and forget all about it... But would it be totally off then? :P

Johnwasser question please , If my application don't care about earth magnetic field values But the change of them, Should I make the calibration steps ?

I mean whether the sensor is calibrated or not the change in values duo to other objects distorting earth magnetic field will be the same right ?