Table of Contents

Class SurfaceWorldMarkerRenderer

Namespace
LansMap.Markers.World
public sealed class SurfaceWorldMarkerRenderer : IDisposable, IMarkerStyle
Inheritance
object
SurfaceWorldMarkerRenderer
Implements

Constructors

SurfaceWorldMarkerRenderer(MarkerStore)

Shares an existing store - typically a fullscreen MarkerLayer's - so the same markers render on both the screen path and the tabletop without copying, and a 2D-to-tabletop switch is a pure view swap. The owning layer keeps its dirty-range fast path; this layer re-uploads whole when the store's Version moves. Known cost: in shared mode ANY mutation re-uploads the whole buffer here, so a very large shared store with per-frame marker animation pays a full SetData per frame on this side - fine for switch-and-view usage, wrong for animating hundreds of thousands of shared markers.

public SurfaceWorldMarkerRenderer(MarkerStore sharedStore)

Parameters

sharedStore MarkerStore

SurfaceWorldMarkerRenderer(int)

public SurfaceWorldMarkerRenderer(int initialCapacity)

Parameters

initialCapacity int

Fields

HideOutsideSurface

public bool HideOutsideSurface

Field Value

bool

MaxAltitudeMercator

Upper altitude bound (mercator units), inclusive. See MinAltitudeMercator.

public float MaxAltitudeMercator

Field Value

float

MinAltitudeMercator

Lower altitude bound (mercator units, AltitudeMercator) a marker must meet to be uploaded/drawn by this layer, inclusive. NegativeInfinity, the default, means no lower bound. Per-layer-instance: the shared-store convention pairs this with a MarkerLayer filtered to alt <= 0, filtering this layer to alt > 0 so the ground and floating tiers of one shared store never both draw the same marker.

public float MinAltitudeMercator

Field Value

float

Store

public readonly MarkerStore Store

Field Value

MarkerStore

Properties

ApplyZoomRange

When true, the default, each marker's stored min/max zoom window hides it outside that range. When false the windows stay stored but every marker on this layer is drawn and pickable at any zoom. Combined with the per-marker flag: both must be true to apply.

public bool ApplyZoomRange { get; set; }

Property Value

bool

CustomShapes

Registered shape sources in shape-id order, so index i is shape id FirstCustomShapeId + i. Baked SDF entries belong to this layer; the others are the caller's own textures.

public IReadOnlyList<Texture2D> CustomShapes { get; }

Property Value

IReadOnlyList<Texture2D>

OutlineColor

public Color OutlineColor { get; set; }

Property Value

Color

OutlineWidthPx

public float OutlineWidthPx { get; set; }

Property Value

float

ShapeAtlas

The packed shape atlas, or null before the first RegisterShape(Texture2D, bool).

public Texture2D ShapeAtlas { get; }

Property Value

Texture2D

StemWidthPx

public float StemWidthPx { get; set; }

Property Value

float

StemsEnabled

public bool StemsEnabled { get; set; }

Property Value

bool

Visible

public bool Visible { get; set; }

Property Value

bool

Methods

Dispose()

Performs application-defined tasks associated with freeing, releasing, or resetting unmanaged resources.

public void Dispose()

RegisterCustomShape(Texture2D, bool)

Registers a readable texture as a marker shape on this tier and returns the shape to pass to the store.

public MarkerShape RegisterCustomShape(Texture2D readableTexture, bool asSdf = false)

Parameters

readableTexture Texture2D

CPU-readable texture, for example a sprite rasterized from an imported SVG.

asSdf bool

True bakes the alpha silhouette into a distance field so the shape stays crisp at any size (monochrome, tinted by the marker color). False keeps a full-color sprite.

Returns

MarkerShape

Shape whose numeric value is at or above FirstCustomShapeId.

Remarks

The world-space counterpart to RegisterCustomShape(Texture2D, bool): same atlas packing, same asSdf semantics, same shape-id namespace. Each tier keeps its own registry, so markers drawn on both call this once per tier; registering in the same order on each keeps one stored shape value meaning the same picture on both.

The source texture must be CPU-readable (tick Read/Write Enabled on the texture importer). A tier holds at most 64 custom shapes. Registering one at a time repacks the atlas per call; to register a set, use RegisterCustomShapes(IReadOnlyList<CustomShapeRequest>, List<MarkerShape>), which packs once.

Ownership: with asSdf true this tier bakes a new texture, owns it, and destroys it on Dispose(), while your source stays yours. With asSdf false it packs your texture and never destroys it, so keep it alive for as long as this tier draws that shape.

RegisterCustomShapes(IReadOnlyList<CustomShapeRequest>, List<MarkerShape>)

Registers several shapes at once on this tier, packing the shape atlas exactly once.

public void RegisterCustomShapes(IReadOnlyList<CustomShapeRequest> requests, List<MarkerShape> ids)

Parameters

requests IReadOnlyList<CustomShapeRequest>

Shapes to register, in the order their ids are wanted.

ids List<MarkerShape>

Cleared, then filled with one shape per request, in request order.

Remarks

Same per-shape contract as RegisterCustomShape(Texture2D, bool), and the same cost argument as RegisterCustomShapes(IReadOnlyList<CustomShapeRequest>, List<MarkerShape>): registering n shapes individually packs the atlas n times, this packs once.

A batch is all or nothing. Whether it is refused for exceeding the 64-shape limit or one of its textures turns out not to be readable, this tier is left exactly as it was, so the same batch can be handed back after the bad texture is fixed without the failed attempt having consumed any shape slots.

RegisterShape(Texture2D, bool)

Registers a readable texture as a marker shape on this tier and returns the id to store in MarkerInstanceData.Shape.

public int RegisterShape(Texture2D readableTexture, bool asSdf = false)

Parameters

readableTexture Texture2D

CPU-readable texture, for example a sprite rasterized from an imported SVG.

asSdf bool

True bakes the alpha silhouette into a distance field so the shape stays crisp at any size (monochrome, tinted by the marker color). False keeps a full-color sprite.

Returns

int

Shape id at or above FirstCustomShapeId, as an int.

Remarks

Identical to RegisterCustomShape(Texture2D, bool) except for the return type. Prefer RegisterCustomShape(Texture2D, bool), which hands back the MarkerShape the store methods already take, so no cast is needed at the call site.

Render(MapViewTransform, in SurfaceUvMap, Transform, Renderer)

Submits this frame's draw. Call once per frame after the surface view is final (LateUpdate).

public void Render(MapViewTransform view, in SurfaceUvMap uvMap, Transform plane, Renderer planeRenderer)

Parameters

view MapViewTransform

The surface's own view (pitch 0).

uvMap SurfaceUvMap

UV parameterisation of the table mesh.

plane Transform

The table transform the markers stand on; positions and the billboard size follow it every frame, so a moving table carries its markers rigidly.

planeRenderer Renderer

Renderer whose world bounds anchor the draw's culling bounds; expanded upward by the tallest marker so a camera looking only at airspace above the table still renders it, and - when HideOutsideSurface is off - widened horizontally to cover markers standing outside the table too, since that is the toggle's whole purpose and an under-sized bounds here would cull the entire draw call, not just the off-table markers.

TryPick(Ray, MapViewTransform, in SurfaceUvMap, Transform, float, out int)

Picks the nearest marker along a world-space ray (a camera ray in an AR/VR scene), altitude-aware: a raised billboard is hit at its raised position, not at its ground pixel. Returns false when no marker comes within its pick radius. O(active markers) - fine for a pointer event, not for per-frame batch queries.

public bool TryPick(Ray worldRay, MapViewTransform view, in SurfaceUvMap uvMap, Transform plane, float pickRadiusPx, out int slot)

Parameters

worldRay Ray

Ray in world space (Camera.ScreenPointToRay).

view MapViewTransform

The surface's own view.

uvMap SurfaceUvMap

UV parameterisation of the table mesh.

plane Transform

The table transform markers stand on.

pickRadiusPx float

Extra grab slack in marker pixels, added to each marker's own visual radius.

slot int

Store slot of the hit marker.

Returns

bool

TryPick(Ray, MapViewTransform, in SurfaceUvMap, Transform, float, out int, out float)

Same as TryPick(Ray, MapViewTransform, SurfaceUvMap, Transform, float, out int) plus the along-ray distance of the hit, in world units, for ranking against tabletop prefabs.

public bool TryPick(Ray worldRay, MapViewTransform view, in SurfaceUvMap uvMap, Transform plane, float pickRadiusPx, out int slot, out float along)

Parameters

worldRay Ray
view MapViewTransform
uvMap SurfaceUvMap
plane Transform
pickRadiusPx float
slot int
along float

Returns

bool