@alicloud/cloud-charts
Version:

220 lines (209 loc) • 7.79 kB
JavaScript
"use strict";
var _interopRequireDefault = require("@babel/runtime/helpers/interopRequireDefault");
exports.__esModule = true;
exports["default"] = calculateCatTicks;
exports.timeCat = timeCat;
exports.timePretty = timePretty;
var _extends2 = _interopRequireDefault(require("@babel/runtime/helpers/extends"));
var _util = require("@antv/util");
var _time = require("@antv/scale/esm/util/time");
// 复写G2时间轴标签计算方法
function getYear(date) {
return new Date(date).getFullYear();
}
function createYear(year) {
return new Date(year, 0, 1).getTime();
}
function getMonth(date) {
return new Date(date).getMonth();
}
function diffMonth(min, max) {
var minYear = getYear(min);
var maxYear = getYear(max);
var minMonth = getMonth(min);
var maxMonth = getMonth(max);
return (maxYear - minYear) * 12 + (maxMonth - minMonth) % 12;
}
function creatMonth(year, month) {
return new Date(year, month, 1).getTime();
}
function diffDay(min, max) {
return Math.ceil((max - min) / _time.DAY);
}
function diffHour(min, max) {
return Math.ceil((max - min) / _time.HOUR);
}
function diffMinus(min, max) {
return Math.ceil((max - min) / (60 * 1000));
}
// 如果计算出来的ticks超出最大最小值,保证最大最小值正确,然后根据宽度和数据量均分
// 1. 确认最大最小值正确,默认刻度个数为7个
// 2. 用户自定义高于一切
// 3. 如果计算出来的的刻度数量小于默认刻度个数,则使用计算出来的刻度
function avgTicks(min, max, tickCount, sourceTicks) {
var tickLength = tickCount;
var avg = (max - min) / (tickLength - 1 <= 0 ? 1 : tickLength - 1);
var ticks = [];
if (!(0, _util.isNil)(min) && !(0, _util.isNil)(max)) {
for (var i = min; i <= max; i += avg) {
ticks.push(i);
}
}
return ticks;
}
/**
* 计算 time 的 ticks,对 month, year 进行 pretty 处理
* @param cfg 度量的配置项
* @returns 计算后的 ticks
*/
function timePretty(cfg) {
var _ticks, _ticks2;
var min = cfg.min,
max = cfg.max,
minTickInterval = cfg.minTickInterval,
tickCount = cfg.tickCount;
var tickInterval = cfg.tickInterval;
var ticks = [];
// 指定 tickInterval 后 tickCount 不生效,需要重新计算
if (!tickInterval) {
tickInterval = (max - min) / tickCount;
// 如果设置了最小间距,则使用最小间距
if (minTickInterval && tickInterval < minTickInterval) {
tickInterval = minTickInterval;
}
}
tickInterval = Math.max(Math.floor((max - min) / (Math.pow(2, 12) - 1)), tickInterval);
var minYear = getYear(min);
// 如果间距大于 1 年,则将开始日期从整年开始
if (tickInterval > _time.YEAR) {
var maxYear = getYear(max);
var yearInterval = Math.ceil(tickInterval / _time.YEAR);
for (var i = minYear; i <= maxYear + yearInterval; i = i + yearInterval) {
ticks.push(createYear(i));
}
} else if (tickInterval > _time.MONTH) {
// 大于月时
var monthInterval = Math.ceil(tickInterval / _time.MONTH);
var mmMoth = getMonth(min);
var dMonths = diffMonth(min, max);
for (var _i = 0; _i <= dMonths + monthInterval; _i = _i + monthInterval) {
ticks.push(creatMonth(minYear, _i + mmMoth));
}
} else if (tickInterval > _time.DAY) {
// 大于天
var date = new Date(min);
var year = date.getFullYear();
var month = date.getMonth();
var mday = date.getDate();
var day = Math.ceil(tickInterval / _time.DAY);
var ddays = diffDay(min, max);
for (var _i2 = 0; _i2 < ddays + day; _i2 = _i2 + day) {
ticks.push(new Date(year, month, mday + _i2).getTime());
}
} else if (tickInterval > _time.HOUR) {
// 大于小时
var _date = new Date(min);
var _year = _date.getFullYear();
var _month = _date.getMonth();
var _day = _date.getDate();
var hour = _date.getHours();
var hours = Math.ceil(tickInterval / _time.HOUR);
var dHours = diffHour(min, max);
for (var _i3 = 0; _i3 <= dHours + hours; _i3 = _i3 + hours) {
ticks.push(new Date(_year, _month, _day, hour + _i3).getTime());
}
} else if (tickInterval > _time.MINUTE) {
// 大于分钟
var dMinus = diffMinus(min, max);
var minutes = Math.ceil(tickInterval / _time.MINUTE);
for (var _i4 = 0; _i4 <= dMinus + minutes; _i4 = _i4 + minutes) {
ticks.push(min + _i4 * _time.MINUTE);
}
} else if (tickInterval > _time.SECOND) {
// 小于分钟
var interval = tickInterval;
if (interval < _time.SECOND) {
interval = _time.SECOND;
}
var minSecond = Math.floor(min / _time.SECOND) * _time.SECOND;
var dSeconds = Math.ceil((max - min) / _time.SECOND);
var seconds = Math.ceil(interval / _time.SECOND);
for (var _i5 = 0; _i5 < dSeconds + seconds; _i5 = _i5 + seconds) {
ticks.push(minSecond + _i5 * _time.SECOND);
}
} else {
// 小于秒
var _dSeconds = Math.ceil((max - min) / tickInterval);
for (var _i6 = 0; _i6 < _dSeconds + tickInterval; _i6 = _i6 + 1) {
ticks.push(min + _i6 * tickInterval);
}
}
// 最好是能从算法能解决这个问题,但是如果指定了 tickInterval,计算 ticks,也只能这么算,所以
// 打印警告提示
if (ticks.length >= 512) {
console.warn("Notice: current ticks length(" + ticks.length + ") >= 512, may cause performance issues, even out of memory. Because of the configure \"tickInterval\"(in milliseconds, current is " + tickInterval + ") is too small, increase the value to solve the problem!");
}
// 自己复写filter逻辑,当刻度计算小于6个的时候,且计算出的ticks有超出最大最小值的,只展示首尾
// 1. 数据为1个。就只显示一个
// 2. 数据为2个,则只显示首尾
if (ticks.length < 4 && ticks.length !== 1 && (((_ticks = ticks) === null || _ticks === void 0 ? void 0 : _ticks[0]) < min || ((_ticks2 = ticks) === null || _ticks2 === void 0 ? void 0 : _ticks2[ticks.length - 1]) > max)) {
ticks = [min, max];
}
// 如果只展示了首尾展示,但是用户自定义了tickCount,则展示平均刻度
if (ticks.length === 2 && tickCount > ticks.length) {
ticks = avgTicks(min, max, tickCount, ticks);
}
// 通过配置项开启
// 1. 数据超出3个点,至少保留三个点
// ticks = avgTicks(min, max, tickCount, ticks);
return ticks;
}
/**
* 计算分类 ticks
* @param cfg 度量的配置项
* @returns 计算后的 ticks
*/
function calculateCatTicks(cfg) {
var values = cfg.values,
tickInterval = cfg.tickInterval,
tickCount = cfg.tickCount,
showLast = cfg.showLast;
if ((0, _util.isNumber)(tickInterval)) {
var _ticks3 = (0, _util.filter)(values, function (__, i) {
return i % tickInterval === 0;
});
var lastValue = (0, _util.last)(values);
if (showLast && (0, _util.last)(_ticks3) !== lastValue) {
_ticks3.push(lastValue);
}
return _ticks3;
}
var len = values.length;
var min = cfg.min,
max = cfg.max;
if ((0, _util.isNil)(min)) {
min = 0;
}
if ((0, _util.isNil)(max)) {
max = values.length - 1;
}
if (!(0, _util.isNumber)(tickCount) || tickCount >= len) return values.slice(min, max + 1);
if (tickCount <= 0 || max <= 0) return [];
var interval = tickCount === 1 ? len : Math.floor(len / (tickCount - 1));
var ticks = [];
var idx = min;
for (var i = 0; i < tickCount; i++) {
if (idx >= max) break;
idx = Math.min(min + i * interval, max);
if (i === tickCount - 1 && showLast) ticks.push(values[max]);else ticks.push(values[idx]);
}
return ticks;
}
// 时间分类算法
function timeCat(cfg) {
// 默认保留最后一条
var ticks = calculateCatTicks((0, _extends2["default"])({
showLast: true
}, cfg));
return ticks;
}