export function aggregateValueSlices()

in pbi-heat-streams/src/data/aggregateValueSlices.ts [22:83]


export function aggregateValueSlices(
	data: ICategoryDataMap,
	positionDomain: XDomain,
	dateAggregation: DateAggregation,
	numericAggregation: number,
): [
	ICategoryValueMap,
	/**
	 * value domain
	 */
	[number, number],
] {
	let valueMin = 0
	let valueMax = 0
	const isNumericDomain = typeof positionDomain[0] === 'number'

	const categoryIds = Object.keys(data)
	const result = categoryIds.reduce(
		(agg: ICategoryValueMap, current: string) => {
			// sort the category data ascending
			const categoryData = data[current]

			// Bucket out the values by their aggregated position (within day, within year, etc..)
			const valuePositions: { [dateCode: string]: number[] } = {}
			categoryData.forEach(cd => {
				if (cd.value !== undefined && cd.value !== null) {
					const start = isNumericDomain
						? `${cd.position}`
						: sliceStart(cd.position, dateAggregation).toUTCString()

					if (!valuePositions[start]) {
						valuePositions[start] = []
					}
					if (cd.value !== null) {
						if (valueMin === undefined || cd.value < valueMin) {
							valueMin = cd.value
						}
						if (valueMax === undefined || cd.value > valueMax) {
							valueMax = cd.value
						}
					}
					valuePositions[start].push(cd.value)
				}
			})

			const slices = Object.keys(valuePositions).map(vp => {
				const start = isNumericDomain ? parseInt(vp, 10) : new Date(vp)
				const end = getSliceEnd(start, numericAggregation, dateAggregation)
				return {
					start,
					end,
					value: <number>mean(valuePositions[vp]),
				}
			})
			agg[current] = slices
			return agg
		},
		<ICategoryValueMap>{},
	)

	return [result, [valueMin, valueMax]]
}