android指南针似乎不可靠

标签 android compass-geolocation sensors android-sensors

过去几天我一直在开发一个小型指南针应用程序,并且已经启动并运行了代码,但似乎指南针读数不准确。校准两部手机后,我的第一次测试发现这一点是因为我只是将手机靠在平面上看读数,然后将其水平翻转并将其放在同一个平面上(转 180* 圈),结果确实如此不改变 180* 它更接近 240*。

然后我测试了与指南针的读数,有时读数似乎很接近,但在其他点上却相差超过 50*。我什至试着把我的手机和指南针放在地板上,让指南针远离任何磁干扰,结果相同(注意我也将指南针和手机分开,通过与书的边缘对齐来保持它们在同一方向) .

然后我将示例应用程序放在另一部手机上(第一个是 nexus S,第二个是 Motorola droid 1)。两部手机之间的差异范围从在某些点相等,但在大多数点之间相差 50 到 15 度。

我浏览了文档,也浏览了许多不同的论坛帖子,但没有看到任何人有相同的结果。我的代码中可能有一些小错误导致我的读数不正确,或者我没有看到一些记录的错误。

任何见解或建议将不胜感激!

这是我的 SensorEventListener 类中的传感器更改代码

public void onSensorChanged(SensorEvent event)
    {
        // If the sensor data is unreliable return
        if (event.accuracy == SensorManager.SENSOR_STATUS_UNRELIABLE)
        {
            Toast.makeText(main.this, "Sensor Status Unreliable",Toast.LENGTH_SHORT).show();
        }





        // Gets the value of the sensor that has been changed
        switch (event.sensor.getType())
        {
        case Sensor.TYPE_ACCELEROMETER:
            m_vfgravity = event.values.clone();
            break;
        case Sensor.TYPE_MAGNETIC_FIELD:
            m_vfgeomag = event.values.clone();
            break;
        }

        if (m_vfgravity != null && m_vfgeomag != null)
        {
            if(SensorManager.getRotationMatrix(m_vfinR, m_vfI, m_vfgravity, m_vfgeomag))
            {
                SensorManager.getOrientation(m_vfinR, m_vforientVals);

                m_fCompBearing = (float) Math.round((Math.toDegrees(m_vforientVals[0])) *2)/2;

                //convert to 0-360 from -180-180
                if(m_fCompBearing < 0.0)
                {
                    m_fCompBearing = 360 + m_fCompBearing;
                }


                mCompHead.setText("" + (int)m_fCompBearing);
            }

            calcOffset();   
            rotateCmp();
        }
    }

并在创建我的 Activity 时编码
    mSMngr = (SensorManager) getSystemService(Context.SENSOR_SERVICE);
    mSListener = new cSensorListener();

    mSMngr.registerListener(mSListener,
            mSMngr.getDefaultSensor(Sensor.TYPE_MAGNETIC_FIELD),
            SensorManager.SENSOR_DELAY_UI);
    mSMngr.registerListener(mSListener,
            mSMngr.getDefaultSensor(Sensor.TYPE_ACCELEROMETER),
            SensorManager.SENSOR_DELAY_UI);

提前致谢!

编辑:还用 droid X 尝试过,但结果最差......当手机滚动 45 度(围绕计算机坐标系 z 轴旋转)时,返回的罗盘航向可以改变 180 度,实际上是航向值当向同一方向旋转时,它会朝着与其他手机相反的方向移动。即使在设置中校准后,这是唯一产生此结果的手机。他们也是我测试过的指南针动态壁纸,但没有相同的问题。所以我认为我可以在软件中做一些事情来避免这种情况。

最佳答案

尽管作者回答了他自己的问题,但我必须在这里加一句,以强调 Android 平台上任何类型的指南针功能几乎完全无用。

我得出的结论是,任何依赖 Android 指南针应用程序的人都在自找麻烦,它们都不能可靠地工作,这不是开发人员的错。

谷歌和制造商根本没有提供一种方法来从这些设备中获得可靠的准确性,甚至没有提供一种方法来确定准确性是否可靠,这甚至更糟,因为有时它们是可靠的,很多时候它们不是,并且是否有人信任这些设备进行真正的定向运动上帝帮助他们。

作者可能认为他获得更好结果的原因是他们在已弃用的方向传感器上使用了相当不错的噪声过滤器(为什么他们不能在较新的方法上这样做超出了我的理解),并且在校准后在单个设备上进行了有限的测试。这似乎可行,但在使用许多设备的现场中,我发现在大多数情况下,可靠性始终存在问题。

首先,磁性和方向传感器产生的噪音是可怕的,是的,这可以通过适当的 DSP 技术来克服,并且使用 2.3 和陀螺仪的手机总体上会变得更好,但是对于 Google 和 Mfg 浪费这么多开发人员时间感到羞耻硬件和软件输出的劣质实现。

其次,我已经测试了至少 18 部具有适当 DSP 过滤的手机,虽然这可以清除噪音,但对准确性没有帮助,即使是相同型号的手机也有不同的输出(尽管有些型号似乎比其他型号更好)

第三,您几乎无法确定传感器是否已校准,即使进行痉挛的数字 8 运动也可能会或可能不会校准手机,并且用户永远不会真正知道它是否在工作,除非您有指南针来验证,有点失败不是吗?

注意:您可以将磁传感器彼此相乘和求和,然后取该 sqrt(x*x+y*y+z*z) 的平方根,并确保它在 25 到 65 左右之间,这是您的一个指标可以用来检测异常场,但它并不完全可靠,我猜总比没有好。

第四,许多手机完全不可靠,无论是否经过校准,这不仅限于型号类型,还可能是制造商的质量问题,我真的不知道为什么,但我可以说 3 台 HTC ARIA 产生了截然不同的结果(一个 30 度,另一个 50 度,第三个几乎点)同样的事情,令人难以置信,联系等。

我测试了 18 部手机,如果您可以正确校准,其中许多手机都非常接近准确,但其中许多手机需要 2-10 次尝试(我们在每次校准尝试后都使用高精度罗盘进行了验证),而且多次他们根本无法校准根本。

注意:您确实必须考虑到真正的北偏移量的偏角,如果您可以访问当前的 GPS 坐标、高度、时间等,您可以使用 android 中的 API 来完成。问题不是偏角,如果您是与指南针相比,无论如何这都不是问题,因为它也会受到局部磁场的影响。

Fith,冷启动总是需要在我们测试的每部手机上进行校准步骤,其中包括 X、不可思议的 Aria、Nexus 和 Thunderbolt。换句话说,当您第一次开始传感器监听时,95% 的时间都需要校准步骤(即使坏了的时钟每天也正确两次),因此如果您坚持添加此功能,我只会告诉您的用户在每个监听器事件的开始。

如果您让传感器保持运行(对电池不利),那么您可能需要或可能不需要根据遇到的字段重新校准)上述方法适用于此。

最重要的是,当它们工作时,它们看起来很酷,但您目前永远无法确定方位角的准确性,这使得它们对于任何实际工作都非常不可靠且毫无用处。

就我个人而言,我会在移动时使用 GPS 轴承,然后如果可能的话,使用旋转矢量方法,它可能并不完美,但它会比您在当前手机系列中的方位角实现方式要好得多。

很抱歉冗长的回复,但我已经浪费了将近一个月的时间来尝试在专业 DSP 工程师的帮助下使其工作,而且我们已经写了很多关于 android 平台在这方面很有用的文章。

在我看来,“有时这行得通,有时行不通,除非您有真正的指南针,否则您永远无法确定”免责声明应该放在每个指南针应用程序中。

关于android指南针似乎不可靠,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/6256256/

相关文章:

android - 为什么不同设备的传感器值如此不同?

Arduino 温度传感器

c - 中断外的Arduino串行通信

Java缩放图像

iPhone 3D 指南针

iphone - 使用指南针方向旋转图像以定向到众所周知的点

android - iOS/Android 设备方向(俯仰、偏航、滚动)。用加速度计好还是陀螺仪好?

android - 制作添加到另一个布局的透明布局

android - 具有主视图/详细 View 的导航体系结构组件

javascript - 如何将消息从 node.js 服务器发送到 Android 应用程序?