磁力计仅测地磁场矢量,不能直接提供地理位置或地理朝向;需融合加速度计、陀螺仪数据并校准,才能估算设备相对于磁北或真北的方位角。

磁力计(Magnetometer)本身不提供地理位置信息,也不能直接给出“地理位置的朝向”(如面向北京、朝向正南等)。它只测量设备周围环境的地磁场强度矢量(x, y, z),用于估算设备相对于地球磁北的方向角(heading)——也就是设备顶部所指的磁方位角(0° ≈ 磁北,90° ≈ 磁东,依此类推)。
要获得有意义的朝向(例如“当前面向正南”),需结合以下三步:获取磁力计原始数据 → 补偿设备姿态(用陀螺仪+加速度计融合为欧拉角或四元数)→ 计算校准后的真北/磁北朝向。HTML5 中没有直接的 Magnetometer 独立API 返回地理朝向,而是通过 Sensor API 中的 Magnetometer 与 Accelerometer、Gyroscope 配合实现。
✅ 前提条件:启用传感器权限并检查浏览器支持
现代浏览器(Chrome 86+、Edge 86+、Firefox Nightly 启用 flag)支持 Magnetometer,但需满足:
- 页面运行在 HTTPS 或 localhost 环境下
- 用户已授予
"sensors"权限(自动触发提示) - 设备硬件具备磁力计(多数手机和平板支持,桌面设备通常不支持)
✅ 获取原始磁力计数据(磁北方向粗略估计)
以下代码读取未校准的磁场值(单位:µT):
立即学习“前端免费学习笔记(深入)”;
if ('Magnetometer' in window) {
const mag = new Magnetometer({ frequency: 60 });
<p>mag.onreading = () => {
console.log('Bx:', mag.x, 'By:', mag.y, 'Bz:', mag.z);
// 示例:简单计算二维平面磁航向(忽略俯仰/翻滚,仅适用于水平持握)
const heading = Math.atan2(mag.y, mag.x) * 180 / Math.PI + 180;
console.log('磁航向(°,磁北为0):', (heading % 360).toFixed(1));
};</p><p>mag.onerror = (event) => {
console.error('磁力计不可用:', event.error);
};</p><p>mag.start();
} else {
console.warn('浏览器不支持 Magnetometer');
}✅ 结合加速度计与磁力计,计算真实朝向(推荐方案)
单纯用 Magnetometer 的 x/y 在设备倾斜时误差极大。正确做法是使用 LinearAccelerationSensor + Magnetometer,或更优解——直接使用高阶融合传感器:RelativeOrientationSensor(输出四元数)或 AbsoluteOrientationSensor(已对齐地磁北)。
若需地理真北(而非磁北),还需引入 世界地磁模型(WMM) 进行磁偏角校正(因磁北与真北存在地域性偏差,例如北京约偏西5.5°)。
- 用
AbsoluteOrientationSensor可直接获得相对于地理北的旋转(需设备支持且已校准) - 手动融合:通过
getRotationMatrix()类似 Android 的方式,在 JS 中用quatFromRotationMatrix()计算朝向,再转为方位角 - 简单近似:若设备基本水平,可用
atan2(By, Bx);若已知俯仰角 θ 和横滚角 φ,可投影修正磁场向量
✅ 注意事项与常见问题
- 软铁/硬铁干扰:手机壳、耳机、金属桌面会扭曲磁场,导致朝向跳变。建议引导用户做“8字校准”(部分浏览器会自动触发)
-
无GPS定位能力:磁力计无法获知“你在哪”,只知“你朝哪”。要显示“面向上海东方明珠”,需额外调用
navigator.geolocation获取经纬度,再结合目标坐标反算方位角 - iOS 限制:Safari 目前不支持 Magnetometer API(截至 iOS 17),仅部分 PWA 在特定条件下可用
-
功耗与采样率:高频采集(>30Hz)显著增加耗电,生产环境建议按需调节
frequency或使用requestAnimationFrame节流



















