Skip to content

[Question]: sensors_plus reports different magnetic values in Android and iOS platforms #2655

Not planned
@Hung-Hsun

Description

@Hung-Hsun

What is your question?

I listen magnetometerEventStream to get magnetic values of the device in x, y, z directions. However, when I executed in Android and iOS devices which are oriented in almost same attitude, they reported very different values of MagnetometerEvent as shown below.

Android:
I/flutter (30017): [MagnetometerEvent (x: 7.65749979019165, y: 17.76624870300293, z: 17.66499900817871)]

iOS:
flutter: [MagnetometerEvent (x: 192.7864227294922, y: 8.718887329101562, z: -91.60765075683594)]

My code snippet is:

void listenMagnetometerEvent() {
_magnetometerEventStream ??= magnetometerEventStream().listen(
(MagnetometerEvent event) {
_magnetometerEventNotifier.value = event;
print(event);
},
onError: (error) {
_magnetometerEventStream = null;
throw Exception('Listen magnetometer event error: $error');
},
cancelOnError: true,
);
}

Checklist before submitting a question

  • I searched issues in this repository and couldn't find such bug/problem
    I Google'd a solution and I couldn't find it
    I searched on StackOverflow for a solution and I couldn't find it
    I read the README.md file of the plugin
    I am using the latest version of the plugin
    All dependencies are up to date with flutter pub upgrade
    I did a flutter clean
    I tried running the example project

Activity

Silverviql

Silverviql commented on Mar 29, 2024

@Silverviql

There was already a similar problem, they apparently never fixed it #781

you can try using https://pub.dev/packages/motion_sensors or dchs_motion_sensors,
they seem to write that it gives the correct values

Zabadam

Zabadam commented on Mar 29, 2024

@Zabadam
Contributor

Without follow-up, I was unsure if the issue was ever resolved until now.

It seems still the discrepancy is caused by the source of the magnetometer data.

motion_sensors uses motionManager.startDeviceMotionUpdates() and sensors_plus calls _motionManager.startMagnetometerUpdates().

I do not have an iOS device to test, but perhaps you could try modifying the local package's code to use startDeviceMotionUpdates() and see if that resolves the issue. I never was able to do this myself, and I've needed someone else to try this.

Silverviql

Silverviql commented on Mar 30, 2024

@Silverviql

@Zabadam can you roll out an update so that I don’t have to rewrite the implementation in the project using motion_sensors? ))))

startDeviceMotionUpdates

I don't know Swift took sample code from https://github.com/zesage/motion_sensors/blob/6dafc3639b3e96460fabc639768a60b431b53610/ios/Classes/SwiftMotionSensorsPlugin.swift#L146

It turned out like this and now the data looks correct

`class FPPMagnetometerStreamHandlerPlus: NSObject, MotionStreamHandler {

var samplingPeriod = 200000 {
    didSet {
        _initMotionManager()
        _motionManager.magnetometerUpdateInterval = Double(samplingPeriod) * 0.000001
    }
}

func onListen(
        withArguments arguments: Any?,
        eventSink sink: @escaping FlutterEventSink
) -> FlutterError? {
    _initMotionManager()
    _motionManager.startDeviceMotionUpdates(using: CMAttitudeReferenceFrame.xArbitraryCorrectedZVertical, to: OperationQueue()) { data, error in
        if _isCleanUp {
            return
        }
        if (error != nil) {
            sink(FlutterError(
                    code: "UNAVAILABLE",
                    message: error!.localizedDescription,
                    details: nil
            ))
            return
        }
        if data != nil {
            let magneticField = data!.magneticField.field
            sendTriplet(x: magneticField.x, y: magneticField.y, z: magneticField.z, sink: sink)
        }
    }
    return nil
}

func onCancel(withArguments arguments: Any?) -> FlutterError? {
    _motionManager.stopDeviceMotionUpdates()
    return nil
}

func dealloc() {
    FPPSensorsPlusPlugin._cleanUp()
}

}`

I am attaching a screen recording with the values

  1. With the old implementation
  2. Values ​​for comparison with the Swift application
  3. Already corrected code with correct values ​​and comparing them with values ​​from another application
IMG_0059.MP4
Zabadam

Zabadam commented on Mar 30, 2024

@Zabadam
Contributor

@Zabadam can you roll out an update so that I don’t have to rewrite the implementation in the project using motion_sensors? ))))

I don't know Swift

Me neither, ha! It looks like you were able to accomplish just what I was looking for anyway, because...

I am attaching a screen recording with the values

  1. With the old implementation
  2. Values ​​for comparison with the Swift application
  3. Already corrected code with correct values ​​and comparing them with values ​​from another application

in the final portion of the video, you are using our sensors_plus but with startDeviceMotionUpdates() manually coded in place of startMagnetometerUpdates(), correct?

If yes, then a PR could be made where the function call is simply swapped out.
Edit: And the field is accessed from the event's magneticField, which you correctly caught your code above.

(Or is the final part of the video a demonstration of your app with the package replaced entirely be motion_sensors?)

Edit:
Just now I have realized what happened.
In the past, I did indeed make a follow-up PR that swapped out the "magnetometer updates" call for a "device motion updates" call.

For that fix, I never did receive confirmation of corrected behavior, but it was merged anyway (as some other sensor functions were already utilizing device motion and it seemed appropriate to implement).

When this package was updated to Swift, the revised usage of the device motion sensor was somehow reverted back to utilizing the raw magnetometer sensor.

miquelbeltran

miquelbeltran commented on Mar 30, 2024

@miquelbeltran
Member

Hi Zabadam, if you want to resubmit those changes in a PR, I can give some assistance reviewing and merging the fixes.

Silverviql

Silverviql commented on Mar 30, 2024

@Silverviql

@Zabadam can you roll out an update so that I don’t have to rewrite the implementation in the project using motion_sensors? ))))
I don't know Swift

Me neither, ha! It looks like you were able to accomplish just what I was looking for anyway, because...

I am attaching a screen recording with the values

  1. With the old implementation
  2. Values ​​for comparison with the Swift application
  3. Already corrected code with correct values ​​and comparing them with values ​​from another application

in the final portion of the video, you are using our sensors_plus but with startDeviceMotionUpdates() manually coded in place of startMagnetometerUpdates(), correct?

If yes, then a PR could be made where the function call is simply swapped out. Edit: And the field is accessed from the event's magneticField, which you correctly caught your code above.

(Or is the final part of the video a demonstration of your app with the package replaced entirely be motion_sensors?)

Edit: Just now I have realized what happened. In the past, I did indeed make a follow-up PR that swapped out the "magnetometer updates" call for a "device motion updates" call.

For that fix, I never did receive confirmation of corrected behavior, but it was merged anyway (as some other sensor functions were already utilizing device motion and it seemed appropriate to implement).

When this package was updated to Swift, the revised usage of the device motion sensor was somehow reverted back to utilizing the raw magnetometer sensor.

yes I posted what code I entered manually

I didn’t use motion_sensors, I took a look at how it was implemented and modified it to fit your code

Silverviql

Silverviql commented on Apr 3, 2024

@Silverviql

@Zabadam Haven't you updated yet?

franz-velasco

franz-velasco commented on May 20, 2024

@franz-velasco

Is there an update regarding this? Thanks!

Zabadam

Zabadam commented on Jun 3, 2024

@Zabadam
Contributor

Hello, all, sorry for delay. A PR with this fix should be made shortly.

Zabadam

Zabadam commented on Jun 3, 2024

@Zabadam
Contributor

@franz-velasco @Silverviql @Hung-Hsun

It would be very helpful if someone could confirm proper functionality now that DeviceMotion is in use:

dependencies
  # Testing calibrated magnetometer on iOS (https://github.com/fluttercommunity/plus_plugins/pull/3019)
  sensors_plus:
    git:
      url: https://github.com/Zabadam/plus_plugins.git
      ref: 1e2248d # Branch mag-sensor-ios
      path: packages/sensors_plus/sensors_plus
Silverviql

Silverviql commented on Jun 5, 2024

@Silverviql

@Zabadam yes it works correctly, the same line needs to be changed there, I dropped a couple above

github-actions

github-actions commented on Sep 4, 2024

@github-actions

This issue is stale because it has been open 60 days with no activity. Remove stale label or comment or this will be closed in 15 days

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Metadata

Metadata

Assignees

No one assigned

    Labels

    StalequestionFurther information is requested

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

      Participants

      @miquelbeltran@Hung-Hsun@Silverviql@Zabadam@franz-velasco

      Issue actions

        [Question]: sensors_plus reports different magnetic values in Android and iOS platforms · Issue #2655 · fluttercommunity/plus_plugins