Places Search
Places search provider plugins need to extend the LocationProvider
class:
class MyplaceSearchPlugin : LocationProvider(
QueryPluginConfig()
)
In the super constructor call, pass a QueryPluginConfig
object.
Plugin config
Search plugins have the following configuration properties:
storageStrategy
: Describes how the launcher should store a search result in its internal database. This is relevant when a user pins a search result to favorites, or when they assign a tag or custom label. In these situations, the launcher needs to be able to restore the search result from its database. There are two different strategies:StorageStrategy.StoreCopy
(default): The launcher stores all relevant information about this search result in its own internal database. The result can be restored without querying the plugin again. The launcher will try refresh the search result at its own discretion (e.g. when a user long-presses a restored search result to view its details). This strategy is the default and should be used whenever the plugin can't restore a search result immediately. It is best suited for online search plugins.StorageStrategy.StoreReference
: The launcher only stores the ID of the search result, and the plugin that created it. To restore a result, the plugin is queried again. This allows the plugin to update key fields (i.e. the label) immediately. However, plugins that use this strategy must guarantee, that they can restore a search result at any time, in a timely manner. In particular, the plugin must be able to restore a search result without any network requests. This strategy is best suited for on-device search plugins.
Search places
To implement place search, override
suspend fun search(query: LocationQuery, params: SearchParams): List<Location>
query
includes the query parameters:query
: The search termuserLatitude
: The latitude of the user's current locationuserLongitude
: The longitude of the user's current locationradius
: The search radius in meters
params
provides additional parameters for the search:allowNetwork
is a flag that indicates whether the user has enabled online search for this query. Plugins are generally advised to respect this request. This flag exists mainly for privacy reasons: the majority of searches target offline results (like apps, or contacts). Sending every single search request to external servers is overkill and can be a privacy issue. (Besides, it's not very nice to overload servers with unnecessary requests.) To reduce the amount of data that is sent to external servers, users can control, whether a search should include online results or not.lang
is the current language of the launcher. This can differ from the system language, as the user can set a different language per app. This value should be used for any localization in the search results.
search
returns a list of Location
s. The list can be empty if no results were found.
The Location
object
A Location
has the following properties:
id
: A unique and stable identifier for this location. This is used to track usage stats so if two places are identical, they must have the same ID, and if they are different, they need to have different IDs.label
: The name that is shown to the userlatitude
: The latitude of the locationlongitude
: The longitude of the locationicon
: An enum value ofLocationIcon
that determines the icon that is shown for this locationcategory
: A human readable category of the location. For example, "Restaurant", "Hotel", or "Museum". This should be localized with theparams.lang
parameter.address
: The address of the locationwebsiteUrl
: The URL of the location's websitephoneNumber
: The phone number of the locationemailAddress
: The email address of the locationopeningSchedule
: EitherOpeningSchedule.TwentyFourSeven
if the location is open at all timesOpeningSchedule.Hours(openingHours: List<OpeningHours>)
if the location has specific opening hours, with eachOpeningHours
object containing:dayOfWeek
: The day of the week, asDayOfWeek
enum value. If a location is open past midnight,dayOfWeek
should refer to the day when the opening hours start.startTime
: The time the location opens, as aLocalTime
objectduration
: The duration the location is open, as aDuration
object
departures
: If the place is a public transport station, this field contains the next departures from this station. This is a list ofDeparture
objects, each containing:time
: The scheduled departure time asZonedDateTime
delay
: The delay asDuration
. If the departure is on time, this must beDuration.ZERO
. If no real-time data is available, this should benull
.line
: The line name (e.g. "S1", "U2", or "73")lastStop
: The destination of the linetype
: The type of the line, asLineType
enum valuelineColor
: The color of the line, as aColor
userRating
: A user rating of this location, on a scale from 0 to 1. This is multiplied by 5 and shown as a star rating bar in the launcher.userRatingCount
: The number of user ratings that were used to calculate theuserRating
fixMeUrl
: A URL where users can report incorrect data for this location.attribution
: Attribution that should be shown alongside the search result (read the data provider's terms of service to find out if this is required).
Refresh a place
If you have set config.storageStrategy
to StorageStrategy.StoreCopy
, the launcher will periodically try to refresh the stored copy. This happens for example when a user long-presses a place to view its details. To update the place, you can override
suspend fun refresh(item: Location, params: RefreshParams): Location?
The stored place will be replaced with the return value of this method. If the place is no longer available, it should return null
. In this case, the launcher will remove it from its database. If the place is temporarily unavailable, an exception should be thrown.
item
is the version that the launcher has currently storedparams
provides additional parameters:lang
is the current language of the launcher. This can differ from the system language, as the user can set a different language per app. This value should be used to localize the result.lastUpdated
the timestamp (in milliseconds) whenitem
was last updated. This should be used to determine if the item needs to be refreshed again. If you decide not to refresh the item, you should return the originalitem
parameter.
The default implementation returns item
without any changes.
Get a place
If you have set config.storageStrategy
to StorageStrategy.StoreReference
, you must override
suspend fun get(id: String, params: GetParams): Location?
This method is used to lookup a place by its id
. If the place is no longer available, it should return null
. In this case, the launcher will remove it from its database.
id
is the ID of the place that is being requestedparams
provides additional parameters:lang
is the current language of the launcher. This can differ from the system language, as the user can set a different language per app. This value should be used to localize the result.
Plugin state
Some plugins need to be configured before they can be used. For example, users might need to connect an account, or provide an API key.
If your plugin has such requirements, you can override
suspend fun getPluginState(): PluginState
This method can either return PluginState.Ready
, or PluginState.SetupRequired
.
PluginState.Ready
can have a statustext
to describe what the plugin does in its current configuration. For example "Search {username}'s files on {service}". This overrides the plugin's description.PluginState.SetupRequired
needs to have asetupActivity
Intent that starts the setup. You can also provide amessage
to describe what kind of setup needs to be performed. For example "Sign in with {service} to search files on {service}"
IMPORTANT
This method is only meant to provide hints to the launcher's user interface. You should not rely on it as a safeguard for your other plugin methods. There is still a chance that your other plugin methods are called regardless of the return value of this method. Make sure to check your requirements in the other plugin methods as well.