import { Http } from "../Http";
import { gve } from "../gveesdk/gvee";
import { Chart } from "./Chart";
import * as echarts from "echarts";
import { PrintObject } from "../models/PrintObject";
import { AstHelper } from "@gvol-org/geovis-brain-core";
/**
* @class Chart.image
* @since ui.Chart
* @todo image.byClass
* @todo image.histogram
* @todo image.series
*/
export class image extends PrintObject {
static chart: Chart;
constructor() { super() }
/**
* 按照指定分类波段,根据指定的分类数值,统计分类
* @param {Image} image 显示统计的影像
* @param {String} classBand 分类波段的名称
* @param {Feature|FeatureCollection|Geometry} region optional 区域几何范围
* @param {Object} reducer optional 统计分析方法
* @param {Number} scale optional 计算的分辨率,单位为米。
* @param {Object} classInfos 统计分类的波段信息列表, 每一个元素都是一个字典对象。
元素组成:"value": 分类的值,"label": 对应类别的标签
* @param {List<object>} xLabels x轴显示的标签信息列表,每一个元素都是一个字典对象。
元素组成:"value": x轴显示的内容,"label": 对应波段名称
* @tutorial ui.Chart.image
*/
static byClass(
image: gve.Image,
classBand: string,
region?: gve.Feature | gve.FeatureCollection | gve.Geometry,
reducer?: object,
scale?: number,
classInfos?: object,
xLabels?: gve.List<object>
) {
if (scale) {
Http.scale = scale.toString();
}
}
/**
* 获取影像直方图信息,返回直方图信息
* @param {Image} img 用于生成直方图的图像。
* @param {Feature | FeatureCollection | Geometry} regoin 用来裁切的图像
* @param {any} bins 柱状图柱子个数
* @param {number} scale 重采样比例尺。
* @returns {image} image 返回统计信息
* @tutorial ui.Chart.image
* @todo image.histogram
*/
static histogram(img: gve.Image, regoin?: gve.Feature | gve.FeatureCollection | gve.Geometry, bins?: any, scale?: number) {
if (scale) {
Http.scale = scale.toString();
}
var express = img.reduceRegion(
gve.Reducer.histogram(bins),
regoin as gve.Geometry,
scale ?? 300
);
if (express["order"]) {
express['chain'] = AstHelper.relativeChain(express["order"]);
}
// let codeContent = "print(" + express['expressions'] + ");";
// console.log("chart histogram表达式:", codeContent);
// Http.getPrintRequest(codeContent).then(response => {
// image.chart?.cht?.hideLoading();
// console.log("chart histogram参数", response);
// image.chart.cht.hideLoading();
// Http.responseSubject$.next(null);
// if (response&&response.prints.length>0) {
// let res = response.prints[0];
Http.getPrintRequest(express["chain"]).then(response => {
image.chart?.cht?.hideLoading();
console.log("chart histogram参数", response);
image.chart.cht.hideLoading();
Http.responseSubject$.next(null);
if (response && response.data.status == 'success') {
let res = response.data.detail;
if (res) {
let keys = Object.keys(res);//波段
let histData = res[keys[0]];
if (histData) {
let hist = histData.histogram;
let bin_edges = histData.bin_means;
let seriesName;
let title;
let itemStyle={};
if (image.chart.seriesNames&& image.chart.seriesNames.length>0) {
seriesName= image.chart.seriesNames[0];
}
if (image.chart.options) {
title=image.chart.options['title'];
if (image.chart.options["series"]) {
itemStyle=image.chart.options["series"][0]
}
}
let option = image.getHistogramOption(hist,
bin_edges,
title,
seriesName,
itemStyle
);
// image.chart.values = null;
// image.chart.xLabels = null;
image.chart.setOptions(option);
}
}
}
});
image.chart = new Chart();
let myChart = echarts.init(image.chart.el as HTMLElement);
image.chart.cht = myChart;
// image.chart.values = [[]];
image.chart.axis = 0;
// image.chart.xLabels = [];
image.chart.setChartType('bar');
myChart.showLoading({
text: '图表生成中...',
color: '#ccc',
textColor: '#000',
maskColor: 'rgba(255, 255, 255, 0.3)',
zlevel: 0,
});
return image.chart;
}
setOptions(options: any) {
}
/**
* 从影像集合生成图表。绘制当前区域内影像中每个波段的值,通常是一个时间序列。
* @param {imageCollection} imageCollection 影像数据集合
* @param {Feature | FeatureCollection | Geometry} region 区域几何范围
* @param {Reducer} reducer 区域统计算子
* @param {number} scale 重采样比例尺。
* @param {string} xProperty 矢量数据属性名称。
* @returns ui.Chart
* @tutorial ui.Chart.image
* @todo image.series
*/
static series(imageCollection: gve.ImageCollection, region: gve.Feature | gve.FeatureCollection | gve.Geometry, reducer?: gve.Reducer, scale?: number, xProperty?: string) {
if (scale) {
Http.scale = scale.toString();
}
let express = imageCollection.filterBounds(region as gve.Geometry).map(function (img: gve.Image) {
let s1 = img.reduceRegion(reducer ?? gve.Reducer.mean(), region as gve.Geometry, scale ?? 200);
let d = img.get(xProperty ?? "acquired_date");
let f = gve.Feature(region, s1);
f = f.set(xProperty ?? "system:time_start", d);
return f;
});
// let codeContent = "print(" + express['expressions'] + ");";
// console.log("chart series表达式:", codeContent);
// let values: any = [];
// let labels: any = [];
// Http.getPrintRequest(codeContent).then(response => {
// console.log("chart series参数", response);
// image.chart.cht.hideLoading();
// Http.responseSubject$.next(null);
// if (response&&response.prints.length>0) {
// let res = response.prints[0];
if (express["order"]) {
express['chain'] = AstHelper.relativeChain(express["order"]);
}
let values: any = [];
let labels: any = [];
let content = {
type: 'value',
chain: express['chain']
};
if ((window as any).astCallback) {
(window as any).astCallback(content);
return;
}
Http.getPrintRequest(express['chain']).then(response => {
console.log("chart series参数", response);
image.chart.cht.hideLoading();
Http.responseSubject$.next(response);
if (response && response.data.status == 'success') {
let res = response.data.detail;
if (res && res.features) {
let props = ['addProp', 'fuel1', 'system:time_start'];
let properties = res.features.map((item: any) => { return item.properties });
if (properties && properties.length > 0) {
let first = properties[0];
let keys = Object.keys(first);
keys.forEach((element: any) => {
if (!props.includes(element)) {
values.push(properties.map((m: any) => { return m[element] }));
}
});
labels = properties.map((n: any) => { return n[xProperty ?? 'system:time_start'] });
image.chart.values = values;
image.chart.xLabels = labels;
image.chart.seriesNames = keys.filter((k: any) => { return !props.includes(k) });
if (!image.chart.options) {
let title = "";
if (JSON.stringify(reducer).includes('mean')) {
title = '平均值';
}
else if (JSON.stringify(reducer).includes('min')) {
title = '最小值';
}
else if (JSON.stringify(reducer).includes('max')) {
title = '最大值';
}
image.chart.options = {
title: '影像波段' + title,
xAxis: {
name: xProperty ? 'xProperty' : '日期',
type: "category",
data: labels,
},
yAxis: {
name: "波段值",
type: "value"
}
}
}
image.chart.setChartType('line');
}
}
}
});
image.chart = new Chart();
let myChart = echarts.init(image.chart.el as HTMLElement);
image.chart.cht = myChart;
image.chart.values = [values];
image.chart.axis = 0;
image.chart.xLabels = labels;
image.chart.setChartType('line');
myChart.showLoading({
text: '图表生成中...',
color: '#ccc',
textColor: '#000',
maskColor: 'rgba(255, 255, 255, 0.3)',
zlevel: 0,
});
return image.chart;
}
static getHistogramOption(hist: any, bin_edges: any, title: string, yAxisName: any,itemStyle: any={}) {
if (hist && bin_edges) {
let data = [];
for (let index = 0; index < hist.length; index++) {
const element = hist[index];
let min = bin_edges[index];
let max = bin_edges[index + 1];
let arr = [];
arr.push((max + min) / 2);
arr.push(element);
arr.push(min);
arr.push(max);
arr.push(min + "-" + max);
data.push(arr);
}
var option = {
title: title ?? "直方图",
tooltip: {
},
color: ['red'],
grid: {
left: '3%',
right: '3%',
bottom: '3%',
containLabel: true
},
xAxis: {
boundaryGap: '5%',
scale: true,
},
yAxis: {
scale: true
},
series: [{
name: yAxisName ? yAxisName : 'histogram',
type: 'bar',
barWidth: '100%',
encode: { x: 0, y: 1, itemName: 4 },
// barCategoryGap: 0,
label: {
normal: {
show: false,
position: 'insideTop'
}
},
itemStyle:itemStyle,
data: data
}]
};
console.log("gethistogramOption:", JSON.stringify(option));
return option;
}
}
}