<html>

<head>
  <meta charset="utf-8" />
  <meta name="viewport" content="initial-scale=1, maximum-scale=1,user-scalable=no" />
  <title>ArcGIS JSAPI ESM Template</title>

  <link rel="stylesheet" href="https://js.arcgis.com/4.19/esri/themes/light/main.css" />
</head>

<body>
  <div id="viewDiv">
  </div>
</body>

</html>
html,
body {
	height: 100%;
	width: 100%;
	margin: 0;
	padding: 0;
}

#viewDiv {
	height: 100%;
	width: 100%;
}
import ArcGISMap from "https://js.arcgis.com/4.19/@arcgis/core/Map.js";
import MapView from "https://js.arcgis.com/4.19/@arcgis/core/views/MapView.js";
import FeatureLayer from "https://js.arcgis.com/4.19/@arcgis/core/layers/FeatureLayer.js";
import { whenFalseOnce } from "https://js.arcgis.com/4.19/@arcgis/core/core/watchUtils.js";
import * as colorRendererCreator from "https://js.arcgis.com/4.19/@arcgis/core/smartMapping/renderers/color.js";
import Legend from "https://js.arcgis.com/4.19/@arcgis/core/widgets/Legend.js"

const btn = document.getElementById("btnStart");

const cityLayer = new FeatureLayer({
	portalItem: {
		id: "e39d04981238498792eb33ea26ba1c09"
	}
});

const frsLayer = new FeatureLayer({
	portalItem: {
		id: "cdff193a3e3743a5bc770e2743f215b3"
	}
});

const map = new ArcGISMap({
	basemap: "dark-gray-vector",
	layers: [cityLayer, frsLayer]
});

const view = new MapView({
	container: "viewDiv",
	map,
	center: [-117.98, 33.96],
	zoom: 12
});

const legend = new Legend({ view });
view.ui.add(legend, "top-right");

view.when(async () => {
	// todo bad stuff
	const [ cityLayerView, frsLayerView ] = await Promise.all([
		view.whenLayerView(cityLayer),
		view.whenLayerView(frsLayer),
	]);
	await whenFalseOnce(view, "updating");
	const query = {
		returnGeometry: true
	};
	const cityResults = await cityLayerView.queryFeatures(query);
	const frsResults = await frsLayerView.queryFeatures(query);
	const features = [];
	let temp = [...frsResults.features];
	let temp2 = [];
	for (let feat of cityResults.features) {
		const graphic = feat.clone();
		graphic.attributes.count = 0;
		temp2 = [...temp];
		console.log(temp2.length);
		for (let i = 0; i < temp2.length; i++) {
			const x = temp[i];
			if ((x && graphic.geometry && x.geometry) && graphic.geometry.contains(x.geometry)) {
				graphic.attributes.count++;
				temp.splice(i, 1);
			}
		}
		features.push(graphic);
	}
	map.removeMany([cityLayer, frsLayer]);
	const joinLayer = await createLayer(cityLayer, features, [{
		name: "count",
		alist: "Count",
		type: "integer"
	}]);
	
	const { renderer } = await colorRendererCreator.createContinuousRenderer({
		layer: joinLayer,
		view,
		field: "count",
		them: "above-and-below"
	});
	
	joinLayer.renderer = renderer;
	map.add(joinLayer);
	
});

async function createLayer(layer, source, extraFields) {
	await layer.load();

	// create a Map to hold field info
	const fieldInfosMap = new Map();

	for (const field of [...layer.fields]) {
		fieldInfosMap.set(field.name, {
			fieldName: field.name,
			label: field.alias || field.name
		});
	}

	const fieldInfos = [...new Set(fieldInfosMap.values())];

	const featLayer = new FeatureLayer({
		title: "Spatial Join Layer",
		objectIdField: layer.objectIdField,
		fields: [...new Set([...layer.fields, ...extraFields])],
		geometryType: layer.geometryType,
		source,
		// if schema of two layers is different,
		// popup will have empty fields shown
		popupTemplate: {
			title: "Copy Layer",
			content: [
				{
					type: "fields",
					fieldInfos: [...fieldInfos.values()]
				}
			]
		}
	});
	return featLayer;
}
Run Pen

External CSS

This Pen doesn't use any external CSS resources.

External JavaScript

This Pen doesn't use any external JavaScript resources.