import type FeatureReductionBinning from "../support/FeatureReductionBinning.js";
import type FeatureReductionCluster from "../support/FeatureReductionCluster.js";
import type FeatureReductionSelection from "../support/FeatureReductionSelection.js";
import type { FeatureReductionBinningProperties } from "../support/FeatureReductionBinning.js";
import type { FeatureReductionClusterProperties } from "../support/FeatureReductionCluster.js";
import type { FeatureReductionSelectionProperties } from "../support/FeatureReductionSelection.js";

export interface FeatureReductionLayerProperties {
  /**
   * Configures the method for reducing the number of features in the view.
   * By default this property is `null`, which indicates the layer view should draw every feature.
   *
   * There are three types of feature reduction: `selection`, `cluster`, and `binning`.
   *
   * - [Selection](https://developers.arcgis.com/javascript/latest/references/core/layers/support/FeatureReductionSelection/) only applies to points in a [SceneView](https://developers.arcgis.com/javascript/latest/references/core/views/SceneView/)
   * and involves thinning overlapping features so no features
   * intersect on screen. This has been available since version 4.4.
   * - [Cluster](https://developers.arcgis.com/javascript/latest/references/core/layers/support/FeatureReductionCluster/) groups points, lines, or polygons in a [MapView](https://developers.arcgis.com/javascript/latest/references/core/views/MapView/)
   * into _clusters_ defined in screen space. Each cluster is a point geometry whose size is proportional to the number of features within the cluster. This has been available since version 4.14.
   * - [Binning](https://developers.arcgis.com/javascript/latest/references/core/layers/support/FeatureReductionBinning/) spatially groups points, lines, or polygons in a [MapView](https://developers.arcgis.com/javascript/latest/references/core/views/MapView/)
   * into bins, clearly defining the area aggregating features in map space. Each bin is a polygon geometry typically rendered so its color
   * represents the number of features within the bin. This has been available since version 4.24.
   *
   * @since 4.4
   * @see [Sample - Point clustering](https://developers.arcgis.com/javascript/latest/sample-code/featurereduction-cluster/)
   * @see [Sample - Point clustering with visual variables](https://developers.arcgis.com/javascript/latest/sample-code/featurereduction-cluster-visualvariables/)
   * @see [Sample - Filter clustered points](https://developers.arcgis.com/javascript/latest/sample-code/featurereduction-cluster-filter/)
   * @see [Sample - Point styles for cities](https://developers.arcgis.com/javascript/latest/sample-code/visualization-point-styles/)
   * @example
   * // clusters features based on their spatial proximity to other features
   * layer.featureReduction = {
   *   type: "cluster",
   *   clusterRadius: 100
   * };
   * @example
   * // thins features in the view
   * layer.featureReduction = {
   *   type: "selection"
   * };
   * @example
   * // Aggregates features to bins
   * layer.featureReduction = {
   *   type: "binning",
   *   renderer: {
   *     type: "simple",  // autocasts as new SimpleRenderer()
   *     symbol: {
   *       type: "simple-fill",  // autocasts as new SimpleFillSymbol()
   *       outline: {  // autocasts as new SimpleLineSymbol()
   *         width: 0.5,
   *         color: "white"
   *       }
   *     },
   *     visualVariables: [{
   *       type: "color",
   *       field: "aggregateCount",
   *       stops: [
   *         { value: 1, color: "white" },
   *         { value: 1000, color: "blue" }
   *       ]
   *     }]
   *   },
   *   popupTemplate: {
   *     content: "This bin contains <b>{aggregateCount}</b> features.",
   *     fieldInfos: [{
   *       fieldName: "aggregateCount",
   *       format: {
   *         digitSeparator: true,
   *         places: 0
   *       }
   *     }]
   *   }
   * };
   */
  featureReduction?: ((FeatureReductionSelectionProperties & { type: "selection" }) | (FeatureReductionClusterProperties & { type: "cluster" }) | (FeatureReductionBinningProperties & { type: "binning" })) | null;
}

export type FeatureReductionUnion = FeatureReductionSelection | FeatureReductionCluster | FeatureReductionBinning;

/**
 * Mixin for layers that support featureReduction.
 *
 * @since 4.25
 */
export abstract class FeatureReductionLayer {
  constructor(...args: any[]);
  /**
   * Configures the method for reducing the number of features in the view.
   * By default this property is `null`, which indicates the layer view should draw every feature.
   *
   * There are three types of feature reduction: `selection`, `cluster`, and `binning`.
   *
   * - [Selection](https://developers.arcgis.com/javascript/latest/references/core/layers/support/FeatureReductionSelection/) only applies to points in a [SceneView](https://developers.arcgis.com/javascript/latest/references/core/views/SceneView/)
   * and involves thinning overlapping features so no features
   * intersect on screen. This has been available since version 4.4.
   * - [Cluster](https://developers.arcgis.com/javascript/latest/references/core/layers/support/FeatureReductionCluster/) groups points, lines, or polygons in a [MapView](https://developers.arcgis.com/javascript/latest/references/core/views/MapView/)
   * into _clusters_ defined in screen space. Each cluster is a point geometry whose size is proportional to the number of features within the cluster. This has been available since version 4.14.
   * - [Binning](https://developers.arcgis.com/javascript/latest/references/core/layers/support/FeatureReductionBinning/) spatially groups points, lines, or polygons in a [MapView](https://developers.arcgis.com/javascript/latest/references/core/views/MapView/)
   * into bins, clearly defining the area aggregating features in map space. Each bin is a polygon geometry typically rendered so its color
   * represents the number of features within the bin. This has been available since version 4.24.
   *
   * @since 4.4
   * @see [Sample - Point clustering](https://developers.arcgis.com/javascript/latest/sample-code/featurereduction-cluster/)
   * @see [Sample - Point clustering with visual variables](https://developers.arcgis.com/javascript/latest/sample-code/featurereduction-cluster-visualvariables/)
   * @see [Sample - Filter clustered points](https://developers.arcgis.com/javascript/latest/sample-code/featurereduction-cluster-filter/)
   * @see [Sample - Point styles for cities](https://developers.arcgis.com/javascript/latest/sample-code/visualization-point-styles/)
   * @example
   * // clusters features based on their spatial proximity to other features
   * layer.featureReduction = {
   *   type: "cluster",
   *   clusterRadius: 100
   * };
   * @example
   * // thins features in the view
   * layer.featureReduction = {
   *   type: "selection"
   * };
   * @example
   * // Aggregates features to bins
   * layer.featureReduction = {
   *   type: "binning",
   *   renderer: {
   *     type: "simple",  // autocasts as new SimpleRenderer()
   *     symbol: {
   *       type: "simple-fill",  // autocasts as new SimpleFillSymbol()
   *       outline: {  // autocasts as new SimpleLineSymbol()
   *         width: 0.5,
   *         color: "white"
   *       }
   *     },
   *     visualVariables: [{
   *       type: "color",
   *       field: "aggregateCount",
   *       stops: [
   *         { value: 1, color: "white" },
   *         { value: 1000, color: "blue" }
   *       ]
   *     }]
   *   },
   *   popupTemplate: {
   *     content: "This bin contains <b>{aggregateCount}</b> features.",
   *     fieldInfos: [{
   *       fieldName: "aggregateCount",
   *       format: {
   *         digitSeparator: true,
   *         places: 0
   *       }
   *     }]
   *   }
   * };
   */
  get featureReduction(): FeatureReductionUnion | null | undefined;
  set featureReduction(value: ((FeatureReductionSelectionProperties & { type: "selection" }) | (FeatureReductionClusterProperties & { type: "cluster" }) | (FeatureReductionBinningProperties & { type: "binning" })) | null | undefined);
}