Skip to content

[google_maps_flutter] Add a new zIndexInt param to marker and deprecate zIndex #8012

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Merged
merged 33 commits into from
Jun 17, 2025

Conversation

Hari-07
Copy link
Contributor

@Hari-07 Hari-07 commented Nov 3, 2024

Replace this paragraph with a description of what this PR is changing or adding, and why. Consider including before/after screenshots.
zIndex on marker is currently a double. This introduces inconsistency between its behaviours on android and ios since ios truncates it to an int. This PR aims to smooth out that difference by accepting an int param instead through the marker API in dart

List which issues are fixed by this PR. You must list at least one issue.
Fixes flutter/flutter#155897

Pre-launch Checklist

If you need help, consider asking for advice on the #hackers-new channel on Discord.

@Hari-07
Copy link
Contributor Author

Hari-07 commented Nov 4, 2024

The checking for default value in native code feels a little weird, but since this is a parameter we have a default value for in the dart layer, not sure what other option is there.

The only other one I could think of was checking for 0 in dart itself and then passing down null, for zIndex if that was the case which would mean making it nullable . That might need a bunch of changes and wasn't sure if it's worth it for a deprecation


int zIndexInt = marker.getZIndexInt().intValue();
float zIndex = marker.getZIndex().floatValue();
if (zIndexInt != 0) {
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Can you add a comment here that the reason we check for zero is that zIndexInt is supposed to take priority over zindex? |

Please also add a test in https://github.com/flutter/packages/blob/2c8f22670812996a00e45e6304f79f1fd9b02fa1/packages/google_maps_flutter/google_maps_flutter_android/android/src/test/java/io/flutter/plugins/googlemaps/ConvertTest.java to verify the behavior.

@@ -150,7 +150,12 @@ class Marker implements MapsObject<Marker> {
this.position = const LatLng(0.0, 0.0),
this.rotation = 0.0,
this.visible = true,
@Deprecated(
'Use zIndexInt instead. '
'Use of zIndex was deprecated as it gets truncated to int on iOS.',
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggested change
'Use of zIndex was deprecated as it gets truncated to int on iOS.',
'On iOS zIndex is truncated to an int, which can lead to incorrect/unstable ordering.',

@@ -219,8 +224,19 @@ class Marker implements MapsObject<Marker> {
///
/// Overlays are drawn in order of z-index, so that lower values means drawn
/// earlier, and thus appearing to be closer to the surface of the Earth.
@Deprecated(
'Use zIndexInt instead. '
'Use of zIndex was deprecated as it gets truncated to int on iOS.',
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggested change
'Use of zIndex was deprecated as it gets truncated to int on iOS.',
'On iOS zIndex is truncated to an int, which can lead to incorrect/unstable ordering.',

@@ -246,7 +262,12 @@ class Marker implements MapsObject<Marker> {
LatLng? positionParam,
double? rotationParam,
bool? visibleParam,
@Deprecated(
'Use zIndexIntParam instead. '
'Use of zIndex was deprecated as it gets truncated to int on iOS.',
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggested change
'Use of zIndex was deprecated as it gets truncated to int on iOS.',
'On iOS zIndex is truncated to an int, which can lead to incorrect/unstable ordering.',

Copy link
Member

@ditman ditman left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This is probably minor, but the web version is not handling the new zIndexInt value. We should address that, or create a follow-up ticket so somebody else can implement the desired behavior there.

Comment on lines 1 to 3
## NEXT
## 0.5.10+1

* Deprecate zIndex parameter in Marker and replace with zIndexInt.
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I'd expect to see a change here for the web?

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Thank you for the reminder, didn't think about web. I can just add that in right away

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Please, remember the PR styleguide. This changelog entry should be "Deprecates zIndex parameter..."

@@ -205,5 +206,21 @@ void main() {
}, throwsAssertionError);
});
});

testWidgets('interpretCorrectZIndexInConversion',
Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I didn't find any conversion tests in the web package, so Im not 100% sure if this is in the right place. Maybe it should be in a dedicated convert_test file

Future<gmaps.MarkerOptions> _markerOptionsFromMarker(
/// Computes the options for a new [gmaps.Marker] from an incoming set of options
/// [marker], and the existing marker registered with the map: [currentMarker].
@visibleForTesting
Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This feels a little weird, and I think maybe all the methods here could be static methods of a class

Copy link
Member

@ditman ditman Nov 12, 2024

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Yeah, this file started up being small, then grew to epic proportions. It should eventually disappear, but there's still some "stringly typed" API coming from the core plugin (everything that is backed by a JSON object, for example).

Thanks for adding a convert_test. We normally tested this as an integration test, by inderectly looking at the properties that we can read back from the google maps sdk if I'm not mistaken.

Copy link
Contributor Author

@Hari-07 Hari-07 Nov 12, 2024

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

this file started up being small, then grew to epic proportions. It should eventually disappear

Haha, classic!

Copy link
Member

@ditman ditman Nov 12, 2024

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

In order to not have to modify this method, I'd suggest you add the test to markers_test.dart, which is calling all the conversion methods when doing controller.addMarkers.

See this:

  • testWidgets('changeMarkers', (WidgetTester tester) async {
    gmaps.Marker? marker;
    gmaps.LatLng? position;
    final Set<Marker> markers = <Marker>{
    const Marker(markerId: MarkerId('1')),
    };
    await controller.addMarkers(markers);
    marker = controller.markers[const MarkerId('1')]?.marker;
    expect(marker, isNotNull);
    expect(marker!.draggable, isFalse);
    // By default, markers fall in LatLng(0, 0)
    position = marker.position;
    expect(position, isNotNull);
    expect(position!.lat, equals(0));
    expect(position.lng, equals(0));
    // Update the marker with draggable and position
    final Set<Marker> updatedMarkers = <Marker>{
    const Marker(
    markerId: MarkerId('1'),
    draggable: true,
    position: LatLng(42, 54),
    ),
    };
    await controller.changeMarkers(updatedMarkers);
    expect(controller.markers.length, 1);
    marker = controller.markers[const MarkerId('1')]?.marker;
    expect(marker, isNotNull);
    expect(marker!.draggable, isTrue);
    position = marker.position;
    expect(position, isNotNull);
    expect(position!.lat, equals(42));
    expect(position.lng, equals(54));
    });

(You'd just need to add the marker to the controller, then retrieve it by its MarkerId, and then check the zIndex property, similarly to how you're doing it now)

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

It looks like this still needs to be done?


// We compare with zero because zIndexInt if non zero should get higher priority than zIndex
int zIndexInt = marker.getZIndexInt().intValue();
float zIndex = marker.getZIndex().floatValue();
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

We should not be sending both values; see comments in platform_interface.

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

In fact, I believe once the other changes have been made, you can revert all of the Java changes in this PR.

@@ -1,3 +1,7 @@
## 2.9.6
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Deprecations are defined to be minor version bumps in semver.

@@ -1,3 +1,7 @@
## 2.9.6

* Deprecates zIndex parameter in Marker and replace with zIndexInt.
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Same comments as in the other packages.

this.zIndex = 0.0,
this.zIndexInt = 0,
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

zIndexInt should not be a new field, as this creates the possibility of inconsistent values in the same marker. Instead, it can be:

  const Marker({
    ...
    double zIndex = 0.0,
    int zIndexInt = 0,
    ...
  }): assert(zIndex == 0.0 || zIndexInt == 0, 'Only one of zIndex and zIndexInt can be provided'), zIndex = zIndexInt == 0 ? zIndex : zIndexInt.toDouble();

  ...
  /// ...
  // TODO(stuartmorgan): Make this an int when removing the deprecated double zIndex parameter.
  @Deprecated(...)
  final double zIndex;

  /// ...
  int get zIndexInt => zIndex.round();

Then there is only a single value. iOS can read zIndexInt since it will be truncated anyway, and Android can read zIndex with a comment explaining that it's using a deprecated parameter for backward compatibility.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

zIndex = zIndexInt == 0 ? zIndex : zIndexInt.toDouble()

This would need making Marker non -const

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Ah, so it would.

We'll need to go the slightly clunkier route of using a num then:

  const Marker({
    ...
    double zIndex = 0.0,
    int zIndexInt = 0,
    ...
  }): assert(zIndex == 0.0 || zIndexInt == 0, 'Only one of zIndex and zIndexInt can be provided'), _zIndexNum = zIndexInt == 0 ? zIndex : zIndexInt;

  final num _zIndexNum;

  double get zIndex => _zIndexNum.toDouble();

  int get zIndexInt => _zIndex.round();

@@ -198,6 +199,7 @@ class PlatformMarker {
final double rotation;
final bool visible;
final double zIndex;
final int zIndexInt;
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This should be removed; we don't need to send two values.

@@ -1503,6 +1503,7 @@ Marker _copyMarkerWithClusterManagerId(
rotation: marker.rotation,
visible: marker.visible,
zIndex: marker.zIndex,
zIndexInt: marker.zIndexInt,
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This won't be needed after the suggested change in the platform interface. The zIndex will just need a comment saying that the deprecated parameter is being used to avoid losing precision.

@stuartmorgan-g
Copy link
Contributor

From triage: @Hari-07 Are you still planning on updating this based on the latest review?

@Hari-07
Copy link
Contributor Author

Hari-07 commented Dec 10, 2024

I have been on a small break, will get back to this next week. Is the packages repo also affected by the flutter code style change and require a rebase?

@stuartmorgan-g
Copy link
Contributor

No, flutter/packages already uses dart format, so is unaffected.

@Hari-07
Copy link
Contributor Author

Hari-07 commented Jan 10, 2025

@stuartmorgan Sorry for further delays, got busy with the holiday season, will try and get to this at the earliest

@stuartmorgan-g
Copy link
Contributor

From triage: @Hari-07 was this ready for re-review? If so, it looks like it'll need a sync with main and then we can take a look again.

@Piinks
Copy link
Contributor

Piinks commented Apr 18, 2025

Greetings from stale PR triage, @Hari-07 do you have plans to return to this one?

@Hari-07 Hari-07 requested a review from vashworth as a code owner April 28, 2025 04:24
@Hari-07
Copy link
Contributor Author

Hari-07 commented Apr 28, 2025

Hey @Piinks yeah sure, I had actually made the change he had suggested but forgot to push it up for some reason. Also looks like a sync with main is needed. Doing that now.

Missed the email about this reply

@Hari-07
Copy link
Contributor Author

Hari-07 commented Jun 9, 2025

I removed all overrides for the platform interface package from all other packages, the override that's remaining now is from the main package to android and ios. Does this mean android/ios needs to be merged in as a separate PR and then the main package needs to target the new published version?

Or is it fine to bump the main package's version requirement to a version that isn't published yet

@stuartmorgan-g
Copy link
Contributor

Does this mean android/ios needs to be merged in as a separate PR and then the main package needs to target the new published version?

Yes.

Or is it fine to bump the main package's version requirement to a version that isn't published yet

That would fail essentially everything in CI, since the pub resolution would fail, and thus be unlandable.

@Hari-07
Copy link
Contributor Author

Hari-07 commented Jun 9, 2025

Ok cool, have made a PR with everything except the main package. Once that's in can update the main package here to target the newly released packages and then this should be good to merge finally

@Hari-07
Copy link
Contributor Author

Hari-07 commented Jun 9, 2025

@stuartmorgan-g it might be a good idea to have some kind of automated action that uses git checkout -- package/ to automatically create these partial PRs, that'd then allow you the reviewer to not have to check to make sure it has exactly the changes you expect, not more nor less, and easier for contributors too.

auto-submit bot pushed a commit that referenced this pull request Jun 16, 2025
…param to marker and deprecate zIndex (#9408)

*List which issues are fixed by this PR. You must list at least one issue.*
This is just the `web`, `android` and `ios` package part of #8012

## Pre-Review Checklist

[^1]: Regular contributors who have demonstrated familiarity with the repository guidelines only need to comment if the PR is not auto-exempted by repo tooling.
@Hari-07
Copy link
Contributor Author

Hari-07 commented Jun 16, 2025

Test failure

Running command: "flutter pub get" in /b/s/w/ir/x/w/packages/packages/google_maps_flutter/google_maps_flutter
Resolving dependencies...
Because google_maps_flutter depends on google_maps_flutter_ios ^2.15.4 which doesn't match any versions, version solving failed.


You can try the following suggestion to make the pubspec resolve:
* Consider downgrading your constraint on google_maps_flutter_ios: flutter pub add google_maps_flutter_ios:^2.15.3
Failed to update packages.

2.15.4 is the new version that was just merged in a few minutes back, so maybe it just takes time before that's published and then the tests need to be rerun?

@stuartmorgan-g
Copy link
Contributor

Autopublish happens after all post-submit tests complete successfully, which isn't quite finished.

@Hari-07
Copy link
Contributor Author

Hari-07 commented Jun 17, 2025

@stuartmorgan-g Could you trigger a rerun of the tests here?

Copy link
Contributor

@stuartmorgan-g stuartmorgan-g left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

LGTM!

@stuartmorgan-g stuartmorgan-g added the autosubmit Merge PR when tree becomes green via auto submit App label Jun 17, 2025
@auto-submit auto-submit bot merged commit 25d4fa4 into flutter:main Jun 17, 2025
78 checks passed
engine-flutter-autoroll added a commit to engine-flutter-autoroll/flutter that referenced this pull request Jun 17, 2025
@Hari-07 Hari-07 deleted the maps-zindex-ios-truncation-fix branch June 17, 2025 15:07
github-merge-queue bot pushed a commit to flutter/flutter that referenced this pull request Jun 17, 2025
flutter/packages@03a6abb...25d4fa4

2025-06-17 [email protected]
[google_maps_flutter] Add a new zIndexInt param to marker and deprecate
zIndex (flutter/packages#8012)
2025-06-17 [email protected] [pigeon] Use a
const for custom type ids for gobject generated files (#156100)
(flutter/packages#9306)
2025-06-16 [email protected]
[google_maps_flutter_platform_(web/android/ios)] Add a new zIndexInt
param to marker and deprecate zIndex (flutter/packages#9408)
2025-06-16 [email protected] [camera_avfoundation] fix race condition
when starting image stream on iOS (flutter/packages#8733)
2025-06-16 [email protected] Roll Flutter from
f79452e to 8303a96 (21 revisions) (flutter/packages#9433)

If this roll has caused a breakage, revert this CL and stop the roller
using the controls here:
https://autoroll.skia.org/r/flutter-packages-flutter-autoroll
Please CC [email protected] on the revert to ensure that a
human
is aware of the problem.

To file a bug in Flutter:
https://github.com/flutter/flutter/issues/new/choose

To report a problem with the AutoRoller itself, please file a bug:
https://issues.skia.org/issues/new?component=1389291&template=1850622

Documentation for the AutoRoller is here:
https://skia.googlesource.com/buildbot/+doc/main/autoroll/README.md
Ortes pushed a commit to Ortes/packages that referenced this pull request Jun 25, 2025
… marker and deprecate zIndex (flutter#9372)

*List which issues are fixed by this PR. You must list at least one issue.*
This is just the platform interface package part of flutter#8012 

## Pre-Review Checklist

[^1]: Regular contributors who have demonstrated familiarity with the repository guidelines only need to comment if the PR is not auto-exempted by repo tooling.
Ortes pushed a commit to Ortes/packages that referenced this pull request Jun 25, 2025
…param to marker and deprecate zIndex (flutter#9408)

*List which issues are fixed by this PR. You must list at least one issue.*
This is just the `web`, `android` and `ios` package part of flutter#8012

## Pre-Review Checklist

[^1]: Regular contributors who have demonstrated familiarity with the repository guidelines only need to comment if the PR is not auto-exempted by repo tooling.
Ortes pushed a commit to Ortes/packages that referenced this pull request Jun 25, 2025
…te zIndex (flutter#8012)

*Replace this paragraph with a description of what this PR is changing or adding, and why. Consider including before/after screenshots.*
`zIndex` on marker is currently a double. This introduces inconsistency between its behaviours on android and ios since ios truncates it to an int. This PR aims to smooth out that difference by accepting an int param instead through the marker API in dart

*List which issues are fixed by this PR. You must list at least one issue.*
Fixes flutter/flutter#155897
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
autosubmit Merge PR when tree becomes green via auto submit App p: google_maps_flutter
Projects
None yet
Development

Successfully merging this pull request may close these issues.

[google_maps_flutter] zIndex is silently truncated on iOS
5 participants