/**
 * @import {PointEffectSource} from "@client/canvas/sources/_module.mjs";
 * @import {PlaceableObject} from "@client/canvas/placeables/_module.mjs";
 * @import {Point} from "@common/_types.mjs";
 * @import {EdgeRestrictionType, EdgeSenseType, EdgeDirection, EdgeDirectionMode} from "@common/constants.mjs";
 * @import PolygonVertex from "./edges/vertex.mjs";
 * @import Level from "@client/documents/level.mjs";
 * @import Document from "@common/abstract/document.mjs";
 */


/**
 * @typedef ClipperPoint
 * @property {number} X
 * @property {number} Y
 */

/* -------------------------------------------- */

/**
 * @typedef {"wall"|"source"|"innerBounds"|"outerBounds"} EdgeType
 */

/**
 * @typedef EdgeThresholdData
 * @property {number} [light]        Minimum distance in pixels from a light source for which this edge blocks light
 * @property {number} [darkness]     Minimum distance in pixels from a light source for which this edge blocks darkness
 * @property {number} [sight]        Minimum distance in pixels from a vision source for which this edge blocks vision
 * @property {number} [sound]        Minimum distance in pixels from a sound source for which this edge blocks sound
 * @property {boolean} [attenuation=true] Whether to attenuate the source radius when passing through the edge
 */

/**
 * @typedef EdgeCreationOptions             Additional options which describe the edge
 * @property {string} [id]                   A string used to uniquely identify this edge
 * @property {Document|PlaceableObject} [object]  A Document/PlaceableObject that is responsible for this edge, if any
 * @property {EdgeType} [type]               The type of edge
 * @property {EdgeSenseType} [light]         How this edge restricts light
 * @property {EdgeSenseType} [darkness]      How this edge restricts darkness
 * @property {EdgeSenseType} [move]          How this edge restricts movement
 * @property {EdgeSenseType} [sight]         How this edge restricts sight
 * @property {EdgeSenseType} [sound]         How this edge restricts sound
 * @property {EdgeDirection} [direction=0]   A direction of effect for the edge
 * @property {EdgeThresholdData|null} [threshold] Configuration of threshold data for this edge
 * @property {number} [priority=0]           A source priority for this edge. Default: `0`.
 */

/* -------------------------------------------- */

// TODO: "universal" type will be deprecated in v14
/**
 * @typedef {EdgeRestrictionType|"universal"} PointSourcePolygonType
 */

/**
 * @typedef PointSourcePolygonConfig
 * @property {PointSourcePolygonType} type  The type of polygon being computed
 * @property {Level} [level]        The Level the polygon is computed in. Defaults to the viewed Level.
 * @property {number} [angle=360]   The angle of emission, if limited
 * @property {number} [density]     The desired density of padding rays, a number per PI
 * @property {number} [radius]      A limited radius of the resulting polygon
 * @property {number} [externalRadius=0]  The external radius
 * @property {number} [rotation]    The direction of facing, required if the angle is limited
 * @property {ElevatedSurfaceExposureOptions} [surfaceExposure]  Additional options passed through to surface
 *                                                               exposure generator
 * @property {boolean} [useThreshold=false] Compute the polygon with threshold wall constraints applied
 * @property {boolean} [debug]      Display debugging visualization and logging for the polygon
 * @property {PointEffectSource} [source] The object (if any) that spawned this polygon.
 * @property {Array<PIXI.Rectangle|PIXI.Circle|PIXI.Polygon>} [boundaryShapes] Limiting polygon boundary shapes
 * @property {boolean} [hasLimitedRadius] Does this polygon have a limited radius?
 * @property {boolean} [hasLimitedAngle] Does this polygon have a limited angle?
 * @property {PIXI.Rectangle} [boundingBox] The computed bounding box for the polygon
 */

/* -------------------------------------------- */

/**
 * @typedef ElevatedSurfaceExposureOptions
 * @property {number} [threshold]  Points with at most this distance (grid units) from the surface are exposed.
 *                                 Default: `0`.
 */

/* -------------------------------------------- */

/**
 * @typedef {{mode: 0|1|2, priority: number}} ClockwiseSweepEdgeConfig
 *   Modes:
 *    - Never (`0`): The edges of this type are never included.
 *    - Maybe (`1`): The edges of this type are tested for inclusion.
 *    - Always (`2`): The edges of this type are always included.
 */

/**
 * @typedef _ClockwiseSweepPolygonConfig
 * @property {EdgeDirectionMode} [edgeDirectionMode] Customize how edge direction of one-way edges is applied
 * @property {number} [priority=0]    Edges with priority less than this priority are ignored
 * @property {Partial<Record<EdgeType, boolean|Partial<ClockwiseSweepEdgeConfig>>>} [edgeTypes]
 *   Edge types configured as `false` is equivalent to those edges never being included.
 *   Edge types configured as `true` are included conditionally depending on the type of polygon and the type of edge.
 */

/**
 * @typedef {PointSourcePolygonConfig & _ClockwiseSweepPolygonConfig} ClockwiseSweepPolygonConfig
 */

/* -------------------------------------------- */

/**
 * @typedef RayIntersection
 * @property {number} x     The x-coordinate of intersection
 * @property {number} y     The y-coordinate of intersection
 * @property {number} t0    The proximity to the Ray origin, as a ratio of distance
 * @property {number} t1    The proximity to the Ray destination, as a ratio of distance
 */

/* -------------------------------------------- */

/**
 * @typedef QuadtreeObject
 * @property {PIXI.Rectangle} r
 * @property {*} t
 * @property {Set<Quadtree>} [n]
 */

/* -------------------------------------------- */

/**
 * @typedef {Map<number,PolygonVertex>} VertexMap
 */

/**
 * @typedef {Set<Edge>} EdgeSet
 */

/**
 * @typedef {Ray} PolygonRay
 * @property {CollisionResult} result
 */
