/**
 * Converts Web Mercator coordinates to geographic coordinates and vice versa.
 *
 * > [!WARNING]
 * >
 * > **Known Limitation**
 * >
 * > Geometry type [Mesh](https://developers.arcgis.com/javascript/latest/references/core/geometry/Mesh/) is not supported.
 *
 * @since 4.0
 * @see [Sample - Coordinate Conversion component - Custom Formats](https://developers.arcgis.com/javascript/latest/sample-code/coordinate-conversion-custom/)
 */
import type SpatialReference from "../SpatialReference.js";
import type { GeometryUnion } from "../types.js";

/**
 * Returns `true` if the `source` spatial reference can be projected to the `target` spatial reference with the [project()](https://developers.arcgis.com/javascript/latest/references/core/geometry/support/webMercatorUtils/#project) function, or
 * if the `source` and `target` are the same [SpatialReference](https://developers.arcgis.com/javascript/latest/references/core/geometry/SpatialReference/).
 *
 * @param source - The input [SpatialReference](https://developers.arcgis.com/javascript/latest/references/core/geometry/SpatialReference/) or an object with
 *                                                                  `spatialReference` property such as [Geometry](https://developers.arcgis.com/javascript/latest/references/core/geometry/Geometry/)
 *                                                                  or [Map](https://developers.arcgis.com/javascript/latest/references/core/Map/).
 * @param target - The target [SpatialReference](https://developers.arcgis.com/javascript/latest/references/core/geometry/SpatialReference/) or an object with
 *                                                                  `spatialReference` property such as [Geometry](https://developers.arcgis.com/javascript/latest/references/core/geometry/Geometry/)
 *                                                                  or [Map](https://developers.arcgis.com/javascript/latest/references/core/Map/).
 * @returns Returns `true` if `source` can be projected to `target`.
 * @see [project()](https://developers.arcgis.com/javascript/latest/references/core/geometry/support/webMercatorUtils/#project)
 */
export function canProject(source: object | SpatialReference | null | undefined, target: object | SpatialReference | null | undefined): boolean;

/**
 * Projects the geometry clientside (if possible). You should test the input geometry in [canProject()](https://developers.arcgis.com/javascript/latest/references/core/geometry/support/webMercatorUtils/#canProject) prior to using this function.
 * If the result of [canProject()](https://developers.arcgis.com/javascript/latest/references/core/geometry/support/webMercatorUtils/#canProject) is `true`, then proceed to project. If [canProject()](https://developers.arcgis.com/javascript/latest/references/core/geometry/support/webMercatorUtils/#canProject) returns `false`, then
 * `project()` won't return useful results. Use [project()](https://developers.arcgis.com/javascript/latest/references/core/rest/geometryService/#project) instead.
 *
 * @param geometry - The input geometry.
 * @param spatialReference - The target [SpatialReference](https://developers.arcgis.com/javascript/latest/references/core/geometry/SpatialReference/) or an object with
 *                                                                  `spatialReference` property such as [Geometry](https://developers.arcgis.com/javascript/latest/references/core/geometry/Geometry/)
 *                                                                  or [Map](https://developers.arcgis.com/javascript/latest/references/core/Map/).
 * @returns Returns the projected geometry if the projection is successful.
 * @see [project()](https://developers.arcgis.com/javascript/latest/references/core/rest/geometryService/#project)
 * @see [ProjectParameters](https://developers.arcgis.com/javascript/latest/references/core/rest/support/ProjectParameters/)
 */
export function project(geometry: GeometryUnion | null | undefined, spatialReference: SpatialReference | null | undefined): GeometryUnion | null | undefined;

/**
 * Translates the given latitude and longitude (decimal degree) values to Web Mercator XY values.
 *
 * @param long - The longitude value to convert.
 * @param lat - The latitude value to convert.
 * @returns Returns the converted values in an array.
 */
export function lngLatToXY(long: number, lat: number): [
    number,
    number
];

/**
 * Translates the given Web Mercator coordinates to Longitude and Latitude values (decimal degrees).
 * By default the returned longitude is normalized so that it is within -180 and +180.
 *
 * @param x - The X coordinate value to convert.
 * @param y - The Y coordinate value to convert.
 * @returns Returns the converted values in an array.
 */
export function xyToLngLat(x: number, y: number): [
    number,
    number
];

/**
 * Converts a geometry from geographic units (wkid: 4326) to Web Mercator units (wkid: 3857).
 *
 * @param geometry - The input geometry to convert.
 * @returns Returns the converted geometry in Web Mercator units.
 */
export function geographicToWebMercator(geometry: GeometryUnion): GeometryUnion;

/**
 * Converts a geometry from Web Mercator units (wkid: 3857) to geographic units (wkid: 4326).
 *
 * @param geometry - The input geometry to convert.
 * @param isLinear - = false - Indicates whether to work with linear values, i.e., do not normalize. By default, this conversion method normalizes xmin and xmax values.
 * If this is not desired, specify this value as `true`. Default value is `false`.
 * @returns Returns the converted geometry in geographic units.
 */
export function webMercatorToGeographic(geometry: GeometryUnion, isLinear?: boolean): GeometryUnion;