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

Added memory caching support to FlutterMapNetworkImageProvider #1629

Merged
merged 3 commits into from
Sep 6, 2023
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
22 changes: 9 additions & 13 deletions lib/src/layer/tile_layer/tile_layer.dart
Original file line number Diff line number Diff line change
Expand Up @@ -24,22 +24,18 @@ part 'wms_tile_layer_options.dart';
/// avoid issues.
@immutable
class TileLayer extends StatefulWidget {
/// Defines the structure to create the URLs for the tiles. `{s}` means one of
/// the available subdomains (can be omitted) `{z}` zoom level `{x}` and `{y}`
/// — tile coordinates `{r}` can be used to add "@2x" to the URL to
/// load retina tiles (can be omitted)
/// The URL template is a string that contains placeholders, which, when filled
/// in, create a URL/URI to a specific tile.
///
/// Example:
///
/// https://{s}.tile.openstreetmap.org/{z}/{x}/{y}.png
///
/// Is translated to this:
///
/// https://a.tile.openstreetmap.org/12/2177/1259.png
/// For more information, see <https://docs.fleaflet.dev/layers/tile-layer>.
final String? urlTemplate;

/// Follows the same structure as [urlTemplate]. If specified, this URL is
/// used only if an error occurs when loading the [urlTemplate].
/// Fallback URL template, used if an error occurs when fetching tiles from
/// the [urlTemplate].
///
/// Note that specifying this (non-null) will result in tiles not being cached
/// in memory. This is to avoid issues where the [urlTemplate] is flaky, to
/// prevent different tilesets being displayed at the same time.
///
/// Avoid specifying this when using [AssetTileProvider] or [FileTileProvider],
/// as these providers are less performant and efficient when this is
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,10 @@ import 'package:flutter/painting.dart';
import 'package:http/http.dart';

/// Dedicated [ImageProvider] to fetch tiles from the network
///
/// Supports falling back to a secondary URL, if the primary URL fetch fails.
/// Note that specifying a [fallbackUrl] will prevent this image provider from
/// being cached.
@immutable
class FlutterMapNetworkImageProvider
extends ImageProvider<FlutterMapNetworkImageProvider> {
Expand All @@ -14,15 +18,27 @@ class FlutterMapNetworkImageProvider

/// The URL to fetch the tile from (GET request), in the event the original
/// [url] request fails
///
/// If this is non-null, [operator==] will always return `false` (except if
/// the two objects are [identical]). Therefore, if this is non-null, this
/// image provider will not be cached in memory.
final String? fallbackUrl;

/// The HTTP client to use to make network requests
///
/// Not included in [operator==].
final BaseClient httpClient;

/// The headers to include with the tile fetch request
///
/// Not included in [operator==].
final Map<String, String> headers;

/// Dedicated [ImageProvider] to fetch tiles from the network
/// Create a dedicated [ImageProvider] to fetch tiles from the network
///
/// Supports falling back to a secondary URL, if the primary URL fetch fails.
/// Note that specifying a [fallbackUrl] will prevent this image provider from
/// being cached.
const FlutterMapNetworkImageProvider({
required this.url,
required this.fallbackUrl,
Expand Down Expand Up @@ -75,4 +91,15 @@ class FlutterMapNetworkImageProvider

return decode(await ImmutableBuffer.fromUint8List(bytes));
}

@override
bool operator ==(Object other) =>
identical(this, other) ||
(other is FlutterMapNetworkImageProvider &&
fallbackUrl == null &&
url == other.url);

@override
int get hashCode =>
Object.hashAll([url, if (fallbackUrl != null) fallbackUrl]);
}