Tile Cache
Types
Process-wide GPU/native bookkeeping shared by every TileCache instance: the shared textureUnits pool, bind-slot recycling, and the global per-frame GPU bind budget. Kept here rather than per-instance because texture units are a single scarce GPU resource shared across all layers/sources, and must survive across MapView instances in the same process.
Properties
Tile×time entries currently awaiting a download response, keyed by coordinate hash. See setPending/setPendingKey/isPending; entries here (and in bindList) mark a key as in-flight so isInFlight can veto eviction until the response arrives and it is bound.
Timestamp each _pending entry was marked pending, set/cleared alongside it in setPending/setPendingKey.
Tiles for zoom levels below _persistentLevelCount that are never subject to LRU eviction, kept separate from tiles so low-zoom/overview tiles always stay resident.
Coordinate-hash -> request-timestamp map marking a tile as having an in-flight download requested (set by TilePyramid when a request is issued). Cleared as soon as the tile is bound or otherwise resolved, so a stale entry does not permanently block re-requesting it.
Coordinate hashes of tiles queued for GPU upload, drained by bindTextures. Sources add to this set once a tile's data is ready to bind; isInFlight treats membership as in-flight so eviction leaves the entry alone until it is actually bound (or dropped if the underlying cache entry vanishes first).
Coordinate hash to list-of-hashes lookup; currently unused elsewhere in the codebase.
Coordinate hash -> bound GL texture-unit id, maintained by bindTextures and consumed by rendering to look up which texture holds a given tile.
Tiles bucketed by zoom level; populated by updateTile and pruned by removeTile.
Fraction (0–1) of Runtime.maxMemory currently used by the JVM heap, refreshed by memoryLog each time bindCount changes.
This cache's handle to the native pixel store, namespaced by sourceID so different sources' tiles never collide.
Number of tile×time entries currently awaiting a download response (size of _pending).
GL texture-unit indices queued for deletion; drained a few at a time inside bindTextures (see maxDeletesPerCall) so a large batch of deletes does not stall a single frame.
Number of coordinate hashes currently flagged stale (size of _stale).
The LRU-backed store of non-persistent tiles, keyed by tile-coordinate hash. Capacity comes from defaultCacheCapacity. Eviction is disabled while Timeline.isGloballyPlaying or Timeline.holdFullTimelineResidency holds so a full playback range stays resident, and a removed entry's native/GPU pixels are freed here unless that same play/hold state (or a deliberate viewport-change eviction via forceNativeFreeOnRemove) says otherwise.
Functions
Called from LayerHost.
Evicts every cached tile×time whose tile coordinate (x/y/z, ignoring interval) is not in visibleHashShorts and is not a protected zoom-ancestor of one (protectedAncestorHashShorts) — i.e., belongs to a viewport panned away from. Deliberately runs regardless of play state (unlike evictTimesNotIn): rule 7's "never evict" is about the currently visible tiles' full timeline, not every viewport ever visited during a session. Without this, GPU/native memory for stale viewports never comes back, growing unbounded until downloads stall and rendering has no headroom left to animate.
Drops cached tile×time entries whose interval is outside the active playback keep-set. Call when the global timeline phase advances so long playback does not retain every interval visited so far (native ~1MB + GL texture per tile×time).
Apply onRemove GPU bookkeeping on the GL thread (hashMap + bind-slot recycle).
True when this tile×time can be uploaded (or is already on the GPU). A bare tiles entry or TileList.readyList claim is not enough — those can outlive lost pixels and then permanently skip HTTP while buildReadyPlaybackList never sees a texture.
Generates the shared textureUnits GL texture names once per EGL context. Safe to call repeatedly: a no-op if hasInitialized is already true for the current context, but detects an EGL context switch (e.g. a second MapView/activity) via object identity against textureContext and regenerates + resets the shared bind bookkeeping in that case, since texture names from the old context are meaningless (or worse, colliding) in the new one.
Re-inserts a shell Tile when nativeCache/GPU still has pixels for hash (per hasBindableEncodedPixels) but the entry is missing from tiles/_persistents — e.g. the LRU evicted it — so bindTextures can restore EncodedData.paddedData without another HTTP request. Returns true if the tile is bindable (whether or not a shell needed inserting).
Clears every entry from tiles (does not touch _persistents).
Marks or clears tile as pending in _pending/_pendingTime, keyed by its own Tile.coordHash. See setPendingKey for marking an arbitrary hash without a Tile instance.
Marks or clears the pending flag for an arbitrary hash key, independent of a specific Tile instance. A multi-interval batch request marks only one "representative" tile pending, and that flag clears the moment the HTTP response arrives — well before the other intervals in the batch have been decoded, edge-blended, and queued to bind. Until this per-interval flag is set too, isInFlight sees those other intervals as safe to drop, so a concurrent clearOutsideBounds or evictTimesNotIn sweep can strand one before it is ever bound. placeholder is never read back — only key presence matters to pending/in-flight checks.
Convenience overload of updateTile that stores tile under its own Tile.coord.