Skip to content
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

Port Route Duration Annotations feature to Maps SDK v10 map styling API #2873

Merged
merged 12 commits into from
May 11, 2021

Conversation

avi-c
Copy link
Contributor

@avi-c avi-c commented Mar 17, 2021

Maps v10 replaced the old NSExpression-based style layer API with a new Expressions API.

This necessitates porting over the Route Durations Annotations to the new API.

@avi-c
Copy link
Contributor Author

avi-c commented Mar 17, 2021

Replaces #2870.

@avi-c
Copy link
Contributor Author

avi-c commented Mar 17, 2021

Incorporated some of the feedback that @azarovalex included in #2870

@1ec5 1ec5 requested a review from azarovalex March 18, 2021 16:04
@1ec5 1ec5 added - chore op-ex Refactoring, Tech Debt or any other operational excellence work. topic: cartography release blocker Needs to be resolved before the release. labels Mar 18, 2021
@1ec5 1ec5 added this to the v2.0.0 (RC) milestone Mar 18, 2021
Copy link
Contributor

@1ec5 1ec5 left a comment

Choose a reason for hiding this comment

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

Looks like these are new commits atop release-v2.0 rather than a merge commit. That’s fine, but eventually we’ll need to perform a merge of main into release-v2.0. When we do that, we’ll be able to ignore any conflicts related to route duration annotations as long as this PR has already landed by then.

MapboxNavigation.xcodeproj/project.pbxproj Outdated Show resolved Hide resolved
@avi-c
Copy link
Contributor Author

avi-c commented Mar 19, 2021

@1ec5 - I think all the feedback is addressed. Would it be possible to approve this so we can merge it in?

@avi-c
Copy link
Contributor Author

avi-c commented Apr 1, 2021

@1ec5 - Let me know if there is more to do here or if I can update and merge it in soon.

@@ -155,6 +162,11 @@ open class DayStyle: Style {
NavigationMapView.appearance().trafficUnknownColor = .trafficUnknown
NavigationMapView.appearance().buildingDefaultColor = .defaultBuildingColor
NavigationMapView.appearance().buildingHighlightColor = .defaultBuildingHighlightColor
NavigationMapView.appearance().routeDurationAnnotationColor = .routeDurationAnnotationColor
NavigationMapView.appearance().routeDurationAnnotationSelectedColor = .selectedRouteDurationAnnotationColor
NavigationMapView.appearance().routeDurationAnnotationFontName = "DIN Pro Medium"
Copy link
Contributor

@1ec5 1ec5 Apr 20, 2021

Choose a reason for hiding this comment

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

In general, when styling text on the map that we expect to render server-side, we need to specify a list of fonts including a fallback font. Otherwise, the fontstack could be missing glyphs that are required for rendering the street names, even if the same street names render just fine on the base map: mapbox/mapbox-maps-ios#278.

Since font selection for a symbol layer is so specific to the style specification and unlike UIKit/Core Text font selection, an immediate goal could be to match the fonts in the base style. Consider using the runtime styling API to get the textFont property of the symbol layer used to render roads (so the layer would have a source layer of road) and copying that expression to the layer for the annotations. Typically, a style will use multiple distinct fontstacks for various road label layers, but perhaps we could blithely pick the topmost matching layer or add heuristics to detect and ignore italics and boldface.

That said, maybe the current approach is fine, but there still needs to be a way to specify multiple fallback fonts. The downside is that a developer needs to digest these complex heuristics, especially if they end up opting into client-side fonts for CJK.

Copy link
Contributor Author

Choose a reason for hiding this comment

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

These are good points. I changed the code to allow for a list of font names to be used and not just a single one. This lets the developer choose fonts that may be present in their map style. Also changed the default font of DIN Pro Medium to also include Noto Sans CJK JP Medium and Arial Unicode MS Regular as fallbacks in order to support more glyphs "out of the box" with our default set.
I think that the use of UIAppearance overrides for these map rendered fonts is probably the clearest way we can allow for supporting multiple fonts and fallbacks. I think it's preferable to trying to locate the font settings of a specific layer in the style, which feels more hidden and brittle, even if the source layer name for roads, road is unlikely to change very often in mapbox-streets.

@avi-c avi-c force-pushed the ac-RouteDurationAnnotations branch 2 times, most recently from 65d42c3 to 01669ab Compare April 25, 2021 23:27
CHANGELOG.md Outdated
@@ -99,6 +99,9 @@
* `NavigationMapViewDelegate.navigationMapView(_:alternativeRouteCasingStyleLayerWithIdentifier:source:)` to style the casing of alternative route.
* Fixed an issue where the route line periodically peeked out from behind the user puck even though `NavigationViewController.routeLineTracksTraversal` was enabled. ([#2737](https://github.com/mapbox/mapbox-navigation-ios/pull/2737))
* Created the `UserHaloCourseView` similar to `UserCourseView` for approximate location on iOS 14 during the navigation to represent user location. Allow the switch between `UserHaloCourseView` and `UserCourseView` when precise mode is changed. ([#2664](https://github.com/mapbox/mapbox-navigation-ios/pull/2664))
* Added option to show route duration callouts when previewing route alternatives ([#2734](https://github.com/mapbox/mapbox-navigation-ios/pull/2734)):
* `NavigationMapView.showRouteDurations(along routes:)` to show duration annotation callouts on the map for the provided routes.
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
* `NavigationMapView.showRouteDurations(along routes:)` to show duration annotation callouts on the map for the provided routes.
* `NavigationMapView.showRouteDurations(along:)` to show duration annotation callouts on the map for the provided routes.

Copy link
Contributor Author

Choose a reason for hiding this comment

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

Good idea.

CHANGELOG.md Show resolved Hide resolved
Sources/MapboxNavigation/DayStyle.swift Outdated Show resolved Hide resolved
Sources/MapboxNavigation/NavigationMapView.swift Outdated Show resolved Hide resolved
@objc dynamic public var routeDurationAnnotationColor: UIColor = .routeDurationAnnotationColor
@objc dynamic public var routeDurationAnnotationSelectedTextColor: UIColor = .selectedRouteDurationAnnotationTextColor
@objc dynamic public var routeDurationAnnotationTextColor: UIColor = .routeDurationAnnotationTextColor
@objc dynamic public var routeDurationAnnotationFontName: [String] = ["DIN Pro Medium", "Noto Sans CJK JP Medium", "Arial Unicode MS Regular"]
Copy link
Contributor

Choose a reason for hiding this comment

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

I still think a better default behavior should be to match the style’s existing road label fontstack, even if this UIAppearance option remains as an override. But routeDurationAnnotationFontName is not new, so this can be tail work.

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'm not totally convinced, but I do think you have a good point in that not picking up the map style's font stack removes the ability of the map designer from changing this without help from engineering.

I wrote up #2994 to track this later change.

Sources/MapboxNavigation/NavigationMapView.swift Outdated Show resolved Hide resolved
CHANGELOG.md Outdated
@@ -63,6 +63,8 @@
* Added the `Directions.calculateOffline(options:completionHandler:)` and `Directions.calculateWithCache(options:completionHandler:)` methods, which incorporate routing tiles from the predictive cache when possible to avoid relying on a network connection to calculate the route. `RouteController` now also uses the predictive cache when rerouting. ([#2848](https://github.com/mapbox/mapbox-navigation-ios/pull/2848))
* Fixed an issue where `PassiveLocationDataSource` and `RouteController` did not use the access token and host specified by `PassiveLocationDataSource.directions` and `RouteController.directions`, respectively. Added the `PredictiveCacheOptions.credentials` property for specifying the access token and host used for prefetching resources. ([#2876](https://github.com/mapbox/mapbox-navigation-ios/pull/2876))
* The top banner can now show a wider variety of turn lane configurations, such as combination U-turn/left turn lanes and combination through/slight right turn lanes. ([#2882](https://github.com/mapbox/mapbox-navigation-ios/pull/2882))
* Route Duration Annotations feature now supports a list of fonts to be used. This allows for fallback fonts to be specified and more languages to be supported. ([#2873](https://github.com/mapbox/mapbox-navigation-ios/pull/2873)):
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
* Route Duration Annotations feature now supports a list of fonts to be used. This allows for fallback fonts to be specified and more languages to be supported. ([#2873](https://github.com/mapbox/mapbox-navigation-ios/pull/2873)):
* The duration annotations added by the `NavigationMapView.showRouteDurations(along:)` method are now set in the fonts you specify using the `NavigationMapView.routeDurationAnnotationFontNames` property. Use this property to specify a list of fallback fonts for better language support. ([#2873](https://github.com/mapbox/mapbox-navigation-ios/pull/2873)):

CHANGELOG.md Outdated Show resolved Hide resolved
Sources/MapboxNavigation/DayStyle.swift Outdated Show resolved Hide resolved
Sources/MapboxNavigation/DayStyle.swift Outdated Show resolved Hide resolved
Sources/MapboxNavigation/NavigationMapView.swift Outdated Show resolved Hide resolved
/**
List of Mapbox Maps font names to be used for any symbol layers added by the Navigation SDK.
These are used for features such as Route Duration Annotations that are optionally added during route preview.
See https://docs.mapbox.com/ios/maps/api/6.3.0/customizing-fonts.html for more information about server-side fonts.
Copy link
Contributor

Choose a reason for hiding this comment

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

Where will the (not terribly intuitive) font fallback behavior be documented for map SDK v10? Will it be in the v10 API reference or a guide on docs.mapbox.com?

/cc @mapbox/docs

Copy link
Contributor Author

Choose a reason for hiding this comment

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

That is a very good question. I looked for the font documentation in the v10 beta documentation and it isn't present. I went with the less desired approach of mentioning the v6.3 documentation until the place in the v10 documentation is sorted out.

Perhaps I should write a ticket to update this comment when the docs for Maps v10 are finalized.

Comment on lines +141 to +115
These are used for features such as Route Duration Annotations that are optionally added during route preview.
See https://docs.mapbox.com/ios/maps/api/6.3.0/customizing-fonts.html for more information about server-side fonts.
Copy link
Contributor

Choose a reason for hiding this comment

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

Use Markdown formatting:

Suggested change
These are used for features such as Route Duration Annotations that are optionally added during route preview.
See https://docs.mapbox.com/ios/maps/api/6.3.0/customizing-fonts.html for more information about server-side fonts.
This property affects the font applied to the route duration annotations that the `showRouteDurations(along:)` method adds to the map view. [The map view selects the font](https://docs.mapbox.com/ios/maps/api/6.3.0/customizing-fonts.html) in the same manner as any other symbol layer that you add to the style.

avi-c added 7 commits May 11, 2021 14:15
… instead of a single font name to allow for font fallbacks. Specify a longer list of fonts to include fallbacks for non-English glyphs.
…s set on the Navigation View. In theory they may not be the same, particularly if the developer only wants to label a subset of the routes.
@avi-c avi-c force-pushed the ac-RouteDurationAnnotations branch from 5045ee2 to 1680bfa Compare May 11, 2021 21:31
@avi-c avi-c merged commit 9a7124d into release-v2.0 May 11, 2021
@avi-c avi-c deleted the ac-RouteDurationAnnotations branch May 11, 2021 22:46
Comment on lines +1054 to +1064
let symbolSortKeyString =
"""
["get", "sortOrder"]
"""

if let expressionData = symbolSortKeyString.data(using: .utf8), let expJSONObject = try? JSONSerialization.jsonObject(with: expressionData, options: []) {

mapView.mapboxMap.__map.setStyleLayerPropertyForLayerId(NavigationMapView.routeDurationAnnotationsLayerIdentifier,
property: "symbol-sort-key",
value: expJSONObject)
}
Copy link
Contributor

Choose a reason for hiding this comment

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

I overlooked the possibility of using Expression here: #2996.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
op-ex Refactoring, Tech Debt or any other operational excellence work. release blocker Needs to be resolved before the release. topic: cartography
Projects
None yet
Development

Successfully merging this pull request may close these issues.

Route alternatives should include a callout showing estimated duration of each route
2 participants