Skip to content

Conversation

@EyreFree
Copy link

feat: Add map snapshot functionality

  • Implement map snapshot capability for Android and iOS platforms
  • Add MapSnapshotWrapper for Android
  • Add MapSnapshotter for iOS
  • Update Dart global methods for snapshot support
  • Include comprehensive example with 307 lines of demo code

@gabbopalma gabbopalma self-requested a review September 17, 2025 16:11
Copy link
Collaborator

@gabbopalma gabbopalma left a comment

Choose a reason for hiding this comment

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

Hi! Thank you for your contributions and efforts 😄
We should do some checks on the changes, but nothing major

Could you also run dart format . from from the package root when you're done with all the changes?

Comment on lines +107 to +115
'cameraPosition': {
'target': {
'latitude': cameraPosition.target.latitude,
'longitude': cameraPosition.target.longitude,
},
'zoom': cameraPosition.zoom,
'bearing': cameraPosition.bearing,
'tilt': cameraPosition.tilt,
},
Copy link
Collaborator

Choose a reason for hiding this comment

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

Use cameraPosition.toMap() method, instead of manual formatting

Comment on lines +127 to +152
/// Represents a marker to be added to the map snapshot.
class MapMarker {
final LatLng position;
final Uint8List iconData;
final double iconSize;
final String? label;

const MapMarker({
required this.position,
required this.iconData,
this.iconSize = 32.0,
this.label,
});

Map<String, dynamic> toMap() {
return {
'position': {
'latitude': position.latitude,
'longitude': position.longitude,
},
'iconData': iconData,
'iconSize': iconSize,
'label': label,
};
}
}
Copy link
Collaborator

Choose a reason for hiding this comment

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

Put this code inside a file into maplibre_gl/lib/src path and remove it from global.dart.
Rename this class with a name that better reflects the specific behavior of the map snapshot

Use the LatLng.toJson() method instead of manual mapping the position data

Comment on lines +48 to +51
if (width == null || height == null || styleUrl == null || cameraPositionMap == null) {
result.error("INVALID_ARGUMENTS", "Missing required arguments", null);
return;
}
Copy link
Collaborator

Choose a reason for hiding this comment

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

Also check if styleUrl is empty and, if so, return an error

Suggested change
if (width == null || height == null || styleUrl == null || cameraPositionMap == null) {
result.error("INVALID_ARGUMENTS", "Missing required arguments", null);
return;
}
if (width == null || height == null || styleUrl == null || cameraPositionMap == null) {
result.error("INVALID_ARGUMENTS", "Missing required arguments", null);
return;
}
if (styleUrl.isEmpty()) {
result.error("INVALID_ARGUMENTS", "Style URL cannot be empty", null);
return;
}


setState(() {
_snapshotImage = imageData;
_currentCity = randomCity['name'] as String;
Copy link
Collaborator

Choose a reason for hiding this comment

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

Adjust the casting type of the variable

Suggested change
_currentCity = randomCity['name'] as String;
_currentCity = randomCity['name'] as String?;

Comment on lines +125 to +128
final cameraPosition = CameraPosition(
target: LatLng(randomCity['lat'] as double, randomCity['lng'] as double),
zoom: _currentZoom,
);
Copy link
Collaborator

Choose a reason for hiding this comment

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

Adjust the casting type of the variables

Suggested change
final cameraPosition = CameraPosition(
target: LatLng(randomCity['lat'] as double, randomCity['lng'] as double),
zoom: _currentZoom,
);
final cameraPosition = CameraPosition(
target: LatLng(randomCity['lat']! as double, randomCity['lng']! as double),
zoom: _currentZoom,
);

// Create markers if enabled
List<MapMarker>? markers;
if (_showMarkers) {
final cityName = randomCity['name'] as String;
Copy link
Collaborator

Choose a reason for hiding this comment

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

Adjust the casting type of the variable

Suggested change
final cityName = randomCity['name'] as String;
final cityName = randomCity['name']! as String;


markers = [
MapMarker(
position: LatLng(randomCity['lat'] as double, randomCity['lng'] as double),
Copy link
Collaborator

Choose a reason for hiding this comment

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

Adjust the casting type of the variables

Suggested change
position: LatLng(randomCity['lat'] as double, randomCity['lng'] as double),
position: LatLng(randomCity['lat']! as double, randomCity['lng']! as double),

location: ^5.0.3
maplibre_gl: ^0.22.0
maplibre_gl:
path: ../maplibre_gl
Copy link
Collaborator

Choose a reason for hiding this comment

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

Remove this local dependency. You can use the melos bootstrap command to synchronize all dependencies across packages.
If melos is not activated, activate it first with dart pub global activate melos from the root folder of the maplibre package

Comment on lines +86 to +93
/// Creates a snapshot of a map with the specified parameters.
///
/// [width] and [height] define the dimensions of the snapshot in pixels.
/// [styleUrl] is the URL of the map style to use.
/// [cameraPosition] defines the camera position (center and zoom level) for the snapshot.
/// [markers] is an optional list of markers to add to the snapshot.
///
/// Returns a [Uint8List] containing the PNG image data of the snapshot.
Copy link
Collaborator

Choose a reason for hiding this comment

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

Specific that this method is only available for iOS and Android, and not for Web.

@gabbopalma gabbopalma added enhancement New feature or request android ios dart Pull requests that update Dart code labels Sep 17, 2025
/// [markers] is an optional list of markers to add to the snapshot.
///
/// Returns a [Uint8List] containing the PNG image data of the snapshot.
Future<Uint8List> startMapSnapshot({
Copy link
Contributor

Choose a reason for hiding this comment

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

nitpick: The function should not be named startMapSnapshot as it not only starts the process, but also waits for it to finish and returns the result.

How about takeMapSnapshot or getMapSnapshot?

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

Labels

android dart Pull requests that update Dart code enhancement New feature or request ios

Projects

None yet

Development

Successfully merging this pull request may close these issues.

3 participants