TargetSensor2D Design (6.0)
Purpose
Define a 6.0-friendly grid targeting sensor that:
- Replaces the old
TargetingShapeCast2D*nodes. - Stays as a thin Godot adapter over core targeting services.
- Supports point-based cursor targeting now, with a clear path to area/shape-based detection later without changing the public contract.
Contracts
ITargetSensor (existing)
| |
Responsibilities:
- Convert between world positions and grid coordinates.
- Return a simple IsValid flag indicating whether a usable target exists at/near the given world position.
Non-responsibilities:
- Owning core targeting rules (valid/invalid tiles, paths, costs).
- Owning placement / manipulation workflows.
Those remain in core services (e.g. IGridTargetingService,
IPlacementService, etc.).
Option C Summary (Chosen Approach)
- Now: Implement
TargetSensor2Das a point-based sensor.- World→grid conversion via
CellSize+Origin. - (Later in Phase 2) A single-hit physics check (point or very short
ray) using
CollisionMaskand simple filters.
- World→grid conversion via
- Later: Introduce area-aware detection without changing
ITargetSensorby:- Adding an internal detection mode (
PointvsArea), or - Providing an alternative sensor implementation that still satisfies the same interface.
- Adding an internal detection mode (
TargetingController2D and other consumers continue to depend only
on ITargetSensor.
Phase 1 — Point-Based Sensor (Current)
Behaviour
GetTargetAt(worldPosition):- Map
worldPositiontoCoreVector2IusingCellSizeandOrigin. - Return
(gridPos, true)for now (every mapped tile is treated as potentially valid; core services will later refine this).
- Map
GetWorldPosition(gridPosition):- Map
gridPositionto the tile center in world space.
- Map
Integration
TargetSensor2Dregisters itself into the globalServiceRegistryon_ReadyasITargetSensor.TargetingController2DresolvesITargetSensorfrom the registry and uses it to:- Convert mouse position → grid coordinate.
- Convert grid coordinate → world position for cursor snapping.
Test Boundary
- Core tests (e.g. core targeting/placement tests) define the behaviour of valid/invalid tiles and paths.
- Godot tests for targeting stay as thin wiring smokes:
- Verify the controller resolves
ITargetSensor. - Verify mouse hover drives state and world position through the sensor.
- Do not re-encode full targeting/placement rules.
- Verify the controller resolves
Phase 2 — Physics & Filtering (Planned)
When we need real “object under cursor” detection and collision masks,
TargetSensor2D will grow a physics-backed implementation:
Physics Query
- Use either:
PhysicsDirectSpaceState2D.IntersectPointor a shortRayCast2Dat the tile center for point mode, or- a
ShapeCast2D/IntersectShapefor area mode.
- Respect exported settings:
CollisionMask(layers to include).- Optional
MaxResults/MaxDistance.
- Use either:
Candidate Selection
- From hits, select the best candidate based on:
- Distance to cursor/tile center.
- Collision mask.
- Optional metadata or component filters (e.g. manipulatable flag, specific script, or metadata key).
- From hits, select the best candidate based on:
Grid Mapping & Validation
- Convert candidate hit position →
CoreVector2IusingCellSizeandOrigin. - Optionally consult core services (e.g.
IGridTargetingService.ValidateTargetAtPosition(gridPos, node)). - Return
(gridPos, isValid)to the controller, which then updates state and visual position usingGetWorldPosition.
- Convert candidate hit position →
Throughout this phase, ITargetSensor and
TargetingController2D stay unchanged; only the internal
implementation strategy of the sensor evolves.
Future: Area / Shape-Based Tools
For multi-tile buildings, brushes, or AoE tools, a shape-aware variant can be introduced:
- Either extend
TargetSensor2Dwith an area detection mode that uses a small shape under/around the cursor, or - Introduce a dedicated
ShapeTargetSensor2Dthat still implementsITargetSensorand is wired in via the registry in scenes that need richer detection.
This document intentionally does not specify those tools yet; it only ensures the current design does not block them.
Possible Future: Hit-Selection Helper & Core Tests
If we later introduce probes that can return multiple hits (e.g. Shape-based sensors or richer area tools), it may be useful to factor out a small hit-selection helper into a pure C# utility and test it in a core-style test project. Example responsibilities:
- Choose the closest hit to a reference point (cursor/tile center).
- Apply simple ordering or filtering rules before handing the result back to the sensor.
This is not required for the initial 6.0 rollout and can be added once multi-hit scenarios are formally defined.