修改views\chart\components\views

This commit is contained in:
limengnan 2025-07-01 16:29:15 +08:00
parent 40da16013a
commit e7904b667e
9 changed files with 440 additions and 219 deletions

View File

@ -79,7 +79,8 @@ function createExtremumDiv(id, value, formatterCfg, chart) {
transform: translateX(-50%);
opacity: 1;
transition: opacity 0.2s ease-in-out;
white-space:nowrap;`
white-space:nowrap;
overflow:auto;`
)
div.textContent = valueFormatter(value, formatterCfg)
const span = document.createElement('span')
@ -109,7 +110,7 @@ const noChildrenFieldChart = chart => {
* 线
* @param chart
*/
const supportExtremumChartType = chart => {
export const supportExtremumChartType = chart => {
return ['line', 'area', 'bar', 'bar-group'].includes(chart.type)
}
@ -138,8 +139,8 @@ function removeDivsWithPrefix(parentDivId, prefix) {
export const extremumEvt = (newChart, chart, _options, container) => {
chart.container = container
if (!supportExtremumChartType(chart)) {
clearExtremum(chart)
if (!supportExtremumChartType(chart)) {
return
}
const { label: labelAttr } = parseJson(chart.customAttr)
@ -150,7 +151,9 @@ export const extremumEvt = (newChart, chart, _options, container) => {
i.forEach(item => {
delete item._origin.EXTREME
})
const { minItem, maxItem } = findMinMax(i.filter(item => item._origin.value))
const { minItem, maxItem } = findMinMax(
i.filter(item => item?._origin?.value !== null && item?._origin?.value !== undefined)
)
if (!minItem || !maxItem) {
return
}
@ -223,6 +226,7 @@ export const createExtremumPoint = (chart, ev) => {
divParent.style.zIndex = '1'
divParent.style.opacity = '0'
divParent.style.transition = 'opacity 0.2s ease-in-out'
divParent.style.overflow = 'visible'
// 将父标注加入到图表中
const containerElement = document.getElementById(chart.container)
containerElement.insertBefore(divParent, containerElement.firstChild)

View File

@ -1,7 +1,13 @@
import { Datum } from '@antv/g2plot'
import { find } from 'lodash-es'
import { useI18n } from '@/data-visualization/hooks/web/useI18n'
import { getLocale } from '@/data-visualization/utils/utils'
const { t } = useI18n()
export const isEnLocal = !['zh', 'zh-cn', 'zh-CN', 'tw'].includes(getLocale())
export const formatterItem = {
type: 'auto', // auto,value,percent
unitLanguage: isEnLocal ? 'en' : 'ch',
unit: 1, // 换算单位
suffix: '', // 单位后缀
decimalCount: 2, // 小数位数
@ -10,12 +16,51 @@ export const formatterItem = {
// 单位list
export const unitType = [
{ name: 'unit_none', value: 1 },
{ name: 'unit_thousand', value: 1000 },
{ name: 'unit_ten_thousand', value: 10000 },
{ name: 'unit_million', value: 1000000 },
{ name: 'unit_hundred_million', value: 100000000 }
{ name: t('chart.unit_none'), value: 1 },
{ name: t('chart.unit_thousand'), value: 1000 },
{ name: t('chart.unit_ten_thousand'), value: 10000 },
{ name: t('chart.unit_million'), value: 1000000 },
{ name: t('chart.unit_hundred_million'), value: 100000000 }
]
export const unitEnType = [
{ name: 'None', value: 1 },
{ name: 'Thousand (K)', value: 1000 },
{ name: 'Million (M)', value: 1000000 },
{ name: 'Billion (B)', value: 1000000000 }
]
export function getUnitTypeList(lang) {
if (isEnLocal) {
return unitEnType
}
if (lang === 'ch') {
return unitType
}
return unitEnType
}
export function getUnitTypeValue(lang, value) {
const list = getUnitTypeList(lang)
const item = find(list, l => l.value === value)
if (item) {
return value
}
return 1
}
export function initFormatCfgUnit(cfg) {
if (cfg && cfg.unitLanguage === undefined) {
cfg.unitLanguage = 'ch'
}
if (cfg && isEnLocal) {
cfg.unitLanguage = 'en'
}
onChangeFormatCfgUnitLanguage(cfg, cfg.unitLanguage)
}
export function onChangeFormatCfgUnitLanguage(cfg, lang) {
cfg.unit = getUnitTypeValue(lang, cfg.unit)
}
// 格式化方式
export const formatterType = [
@ -47,17 +92,32 @@ export function valueFormatter(value, formatter) {
}
function transUnit(value, formatter) {
initFormatCfgUnit(formatter)
return value / formatter.unit
}
function transDecimal(value, formatter) {
const resultV = value.toFixed(formatter.decimalCount)
const resultV = retain(value, formatter.decimalCount) as string
if (Object.is(parseFloat(resultV), -0)) {
return resultV.slice(1)
}
return resultV
}
function retain(value, n) {
if (!n) return Math.round(value)
const tran = Math.round(value * Math.pow(10, n)) / Math.pow(10, n)
let tranV = tran.toString()
const newVal = tranV.indexOf('.')
if (newVal < 0) {
tranV += '.'
}
for (let i = tranV.length - tranV.indexOf('.'); i <= n; i++) {
tranV += '0'
}
return tranV
}
function transSeparatorAndSuffix(value, formatter) {
let str = value + ''
if (str.match(/^(\d)(\.\d)?e-(\d)/)) {
@ -74,34 +134,27 @@ function transSeparatorAndSuffix(value, formatter) {
//百分比没有后缀,直接返回
return str
} else {
if (formatter.unit === 1000) {
str += '千'
} else if (formatter.unit === 10000) {
str += '万'
} else if (formatter.unit === 1000000) {
str += '百万'
} else if (formatter.unit === 100000000) {
str += '亿'
const unit = formatter.unit
if (formatter.unitLanguage === 'ch') {
if (unit === 1000) {
str += t('chart.unit_thousand')
} else if (unit === 10000) {
str += t('chart.unit_ten_thousand')
} else if (unit === 1000000) {
str += t('chart.unit_million')
} else if (unit === 100000000) {
str += t('chart.unit_hundred_million')
}
} else {
if (unit === 1000) {
str += 'K'
} else if (unit === 1000000) {
str += 'M'
} else if (unit === 1000000000) {
str += 'B'
}
}
}
return str + formatter.suffix.replace(/(^\s*)|(\s*$)/g, '')
}
export function singleDimensionTooltipFormatter(param: Datum, chart: Chart, prop = 'category') {
let res
const yAxis = chart.yAxis
const obj = { name: param[prop], value: param.value }
for (let i = 0; i < yAxis.length; i++) {
const f = yAxis[i]
if (f.name === param[prop]) {
if (f.formatterCfg) {
res = valueFormatter(param.value, f.formatterCfg)
} else {
res = valueFormatter(param.value, formatterItem)
}
break
}
}
obj.value = res ?? ''
return obj
}

View File

@ -1,4 +1,4 @@
import { isEmpty, isNumber } from 'lodash-es'
import { isNumber } from 'lodash-es'
import { DEFAULT_TITLE_STYLE } from '../editor/util/chart'
import { equalsAny, includesAny } from '../editor/util/StringUtils'
import { FeatureCollection } from '@antv/l7plot/dist/esm/plots/choropleth/types'
@ -12,6 +12,8 @@ import { ElMessage } from 'element-plus-secondary'
import { useI18n } from '@/data-visualization/hooks/web/useI18n'
import { useLinkStoreWithOut } from '@/data-visualization/store/modules/link'
import { useAppStoreWithOut } from '@/data-visualization/store/modules/app'
import { Decimal } from 'decimal.js'
const appStore = useAppStoreWithOut()
const isDataEaseBi = computed(() => appStore.getIsDataEaseBi)
@ -283,17 +285,23 @@ export function handleEmptyDataStrategy<O extends PickOptions>(chart: Chart, opt
}
return options
}
const { yAxis, xAxisExt, extStack } = chart
const { yAxis, xAxisExt, extStack, extBubble } = chart
const multiDimension = yAxis?.length >= 2 || xAxisExt?.length > 0 || extStack?.length > 0
switch (strategy) {
case 'breakLine': {
if (multiDimension) {
// 多维度保持空
if (isChartMix) {
for (let i = 0; i < data.length; i++) {
handleBreakLineMultiDimension(data[i] as Record<string, any>[])
if (data[0]) {
if (xAxisExt?.length > 0 || extStack?.length > 0) {
handleBreakLineMultiDimension(data[0] as Record<string, any>[])
}
}
if (data[1]) {
if (extBubble?.length > 0) {
handleBreakLineMultiDimension(data[1] as Record<string, any>[])
}
}
} else {
if (multiDimension) {
handleBreakLineMultiDimension(data)
}
}
@ -303,22 +311,27 @@ export function handleEmptyDataStrategy<O extends PickOptions>(chart: Chart, opt
}
}
case 'setZero': {
if (isChartMix) {
if (data[0]) {
if (xAxisExt?.length > 0 || extStack?.length > 0) {
handleSetZeroMultiDimension(data[0] as Record<string, any>[])
} else {
handleSetZeroSingleDimension(data[0] as Record<string, any>[])
}
}
if (data[1]) {
if (extBubble?.length > 0) {
handleSetZeroMultiDimension(data[1] as Record<string, any>[], true)
} else {
handleSetZeroSingleDimension(data[1] as Record<string, any>[], true)
}
}
} else {
if (multiDimension) {
// 多维度置0
if (isChartMix) {
for (let i = 0; i < data.length; i++) {
handleSetZeroMultiDimension(data[i] as Record<string, any>[])
}
} else {
handleSetZeroMultiDimension(data)
}
} else {
// 单维度置0
if (isChartMix) {
for (let i = 0; i < data.length; i++) {
handleSetZeroSingleDimension(data[i] as Record<string, any>[])
}
} else {
handleSetZeroSingleDimension(data)
}
}
@ -364,7 +377,7 @@ function handleBreakLineMultiDimension(data) {
})
}
function handleSetZeroMultiDimension(data: Record<string, any>[]) {
function handleSetZeroMultiDimension(data: Record<string, any>[], isExt = false) {
const dimensionInfoMap = new Map()
const subDimensionSet = new Set()
const quotaMap = new Map<string, { id: string }[]>()
@ -372,6 +385,9 @@ function handleSetZeroMultiDimension(data: Record<string, any>[]) {
const item = data[i]
if (item.value === null) {
item.value = 0
if (isExt) {
item.valueExt = 0
}
}
const dimensionInfo = dimensionInfoMap.get(item.field)
if (dimensionInfo) {
@ -388,12 +404,17 @@ function handleSetZeroMultiDimension(data: Record<string, any>[]) {
let subInsertIndex = 0
subDimensionSet.forEach(dimension => {
if (!dimensionInfo.set.has(dimension)) {
data.splice(dimensionInfo.index + insertCount + subInsertIndex, 0, {
const _temp = {
field,
value: 0,
category: dimension,
quotaList: quotaMap.get(dimension as string)
})
} as any
if (isExt) {
_temp.valueExt = 0
}
data.splice(dimensionInfo.index + insertCount + subInsertIndex, 0, _temp)
}
subInsertIndex++
})
@ -402,10 +423,14 @@ function handleSetZeroMultiDimension(data: Record<string, any>[]) {
})
}
function handleSetZeroSingleDimension(data: Record<string, any>[]) {
function handleSetZeroSingleDimension(data: Record<string, any>[], isExt = false) {
data.forEach(item => {
if (item.value === null) {
if (!isExt) {
item.value = 0
} else {
item.valueExt = 0
}
}
})
}
@ -489,7 +514,7 @@ const getExcelDownloadRequest = (data, type?) => {
const tableRow = JSON.parse(JSON.stringify(data.tableRow))
const excelHeader = fields.map(item => item.chartShowName ?? item.name)
const excelTypes = fields.map(item => item.deType)
const excelHeaderKeys = fields.map(item => item.dataeaseName)
const excelHeaderKeys = fields.map(item => item.gisbiName)
let excelData = tableRow.map(item => excelHeaderKeys.map(i => item[i]))
let detailFields = []
if (data.detailFields?.length) {
@ -497,7 +522,7 @@ const getExcelDownloadRequest = (data, type?) => {
return {
name: item.name,
deType: item.deType,
dataeaseName: item.dataeaseName
gisbiName: item.gisbiName
}
})
excelData = tableRow.map(item => {
@ -505,7 +530,7 @@ const getExcelDownloadRequest = (data, type?) => {
if (i === 'detail' && !item[i] && Array.isArray(item['details'])) {
const arr = item['details']
if (arr?.length) {
return arr.map(ele => detailFields.map(field => ele[field.dataeaseName]))
return arr.map(ele => detailFields.map(field => ele[field.gisbiName]))
}
return null
}
@ -522,8 +547,20 @@ const getExcelDownloadRequest = (data, type?) => {
}
}
export const exportExcelDownload = (chart, callBack?) => {
const excelName = chart.title
function getChartExcelTitle(preFix, viewTitle) {
const now = new Date()
const pad = n => n.toString().padStart(2, '0')
const year = now.getFullYear()
const month = pad(now.getMonth() + 1) // 月份从 0 开始
const day = pad(now.getDate())
const hour = pad(now.getHours())
const minute = pad(now.getMinutes())
const second = pad(now.getSeconds())
return `${preFix}_${viewTitle}_${year}${month}${day}_${hour}${minute}${second}`
}
export const exportExcelDownload = (chart, preFix, callBack?) => {
const excelName = getChartExcelTitle(preFix, chart.title)
let request: any = {
proxy: null,
dvId: chart.sceneId,
@ -586,9 +623,11 @@ export const exportExcelDownload = (chart, callBack?) => {
}
export const copyString = (content: string, notify = false) => {
const clipboard = navigator.clipboard || {
let clipboard = navigator.clipboard as Pick<Clipboard, 'writeText'>
if (!clipboard || window.top !== window.self) {
clipboard = {
writeText: data => {
return new Promise(resolve => {
return new Promise<void>(resolve => {
const textareaDom = document.createElement('textarea')
textareaDom.setAttribute('style', 'z-index: -1;position: fixed;opacity: 0;')
textareaDom.value = data
@ -600,6 +639,7 @@ export const copyString = (content: string, notify = false) => {
})
}
}
}
clipboard.writeText(content).then(() => {
if (notify) {
ElMessage.success(t('commons.copy_success'))
@ -779,7 +819,7 @@ export function getColor(chart: Chart) {
}
}
export function setupSeriesColor(chart: ChartObj, data?: any[]): ChartBasicStyle['seriesColor'] {
export function setupSeriesColor(chart: ChartObj): ChartBasicStyle['seriesColor'] {
const result: ChartBasicStyle['seriesColor'] = []
const seriesSet = new Set<string>()
const colors = chart.customAttr.basicStyle.colors
@ -1152,8 +1192,10 @@ export function getLineLabelColorByCondition(conditions, value, fieldId) {
if (fieldConditions.length) {
fieldConditions.some(item => {
if (
(item.term === 'lt' && value <= item.value) ||
(item.term === 'gt' && value >= item.value) ||
(item.term === 'lt' && value < item.value) ||
(item.term === 'le' && value <= item.value) ||
(item.term === 'gt' && value > item.value) ||
(item.term === 'ge' && value >= item.value) ||
(item.term === 'between' && value >= item.min && value <= item.max)
) {
color = item.color
@ -1207,3 +1249,27 @@ export const hexToRgba = (hex, alpha = 1) => {
// 返回 RGBA 格式
return `rgba(${r}, ${g}, ${b}, ${a})`
}
// 安全计算数值字段的总和,使用 Decimal 避免浮点数精度问题
export function safeDecimalSum(data, field) {
// 使用 reduce 累加所有行的指定字段值
return data
.reduce((acc, row) => {
// 将字段值转换为 Decimal 类型并累加到累加器
return acc.plus(new Decimal(row[field] ?? 0))
}, new Decimal(0))
.toNumber() // 最终结果转换为普通数字返回
}
// 安全计算数值字段的平均值,使用 Decimal 避免浮点数精度问题
export function safeDecimalMean(data, field) {
// 如果数据为空,直接返回 0
if (!data.length) return 0
// 计算所有行的指定字段值的总和
const sum = data.reduce((acc, row) => {
// 将字段值转换为 Decimal 类型并累加到累加器
return acc.plus(new Decimal(row[field] ?? 0))
}, new Decimal(0))
// 将总和除以数据行数,得到平均值,并转换为普通数字返回
return sum.dividedBy(data.length).toNumber()
}

View File

@ -28,7 +28,8 @@ import { isDashboard, trackBarStyleCheck } from '@/data-visualization/utils/canv
import { useEmitt } from '@/data-visualization/hooks/web/useEmitt'
import { L7ChartView } from '@/data-visualization/chart/components/js/panel/types/impl/l7'
import { useI18n } from '@/data-visualization/hooks/web/useI18n'
import { ExportImage,Scale } from '@antv/l7'
import { ExportImage, Scale, Fullscreen, Control, Scene, TileLayer } from '@antv/l7'
import { GaodeMap } from '@antv/l7-maps';
const { t } = useI18n()
const dvMainStore = dvMainStoreWithOut()
const { nowPanelTrackInfo, nowPanelJumpInfo, mobileInPc, embeddedCallBack, inMobile } =
@ -111,7 +112,8 @@ const state = reactive({
},
linkageActiveParam: null,
pointParam: null,
data: { fields: [] } //
data: { fields: [] }, //
satelliteVisible: false, //
})
let chartData = shallowRef<Partial<Chart['data']>>({
fields: []
@ -333,35 +335,100 @@ const renderL7Plot = async (chart: ChartObj, chartView: L7PlotChartView<any, any
let mapL7Timer: number
let scaleControl: Scale | null = null //
let fullscreenControl
let satelliteControlInstance = null; //
const renderL7 = async (chart: ChartObj, chartView: L7ChartView<any, any>, callback) => {
mapL7Timer && clearTimeout(mapL7Timer)
mapL7Timer && clearTimeout(mapL7Timer);
mapL7Timer = setTimeout(async () => {
myChart = await chartView.drawChart({
chartObj: myChart,
container: containerId,
chart: chart,
action
})
});
//
if (scaleControl) {
myChart.getScene()?.removeControl(scaleControl)
scaleControl = null
}
//
if (!scaleControl) {
scaleControl = new Scale({
position: 'bottomleft',
imperial: false
})
myChart.getScene()?.addControl(scaleControl)
});
myChart.getScene()?.addControl(scaleControl);
}
myChart?.render()
callback?.()
emit('resetLoading')
}, 500)
}
//
//
if (fullscreenControl) {
} else {
fullscreenControl = new Fullscreen({
position: 'bottomright',
});
myChart.getScene()?.addControl(fullscreenControl, 'bottomright');
}
// ====== 使API ======
let satelliteLayer: any = null;
let isSatelliteVisible = false;
class SatelliteControl extends Control {
protected onAdd() {
const btn = document.createElement('button');
btn.className = 'l7-control-button l7-satellite-control';
btn.innerHTML = '卫星';
// btn.title = '';
btn.style.backgroundColor = '#000';
btn.style.color = '#fff';
btn.style.padding = '2px';
btn.style.borderRadius = '4px';
btn.style.cursor = 'pointer'
btn.style.fontSize = '11px';
const scene = myChart.getScene()
//
scene.on('loaded', () => {
//
satelliteLayer = new window.AMap.TileLayer.Satellite();
btn.onclick = () => {
isSatelliteVisible = !isSatelliteVisible;
if (isSatelliteVisible) {
// 使 scene.addLayer
btn.style.backgroundColor = '#409eff';
scene.map.add(satelliteLayer)
} else {
// 使 scene.removeLayer
btn.style.backgroundColor = '#000';
scene.map.remove(satelliteLayer)
}
};
});
return btn;
}
}
//
//
if (satelliteControlInstance) {
} else {
//
satelliteControlInstance = new SatelliteControl({ position: 'bottomright' });
myChart.getScene()?.addControl(satelliteControlInstance);
}
// ====== ======
myChart?.render();
callback?.();
emit('resetLoading');
}, 500);
};
const pointClickTrans = () => {
if (embeddedCallBack.value === 'yes') {
trackClick('pointClick')
@ -706,15 +773,8 @@ onBeforeUnmount(() => {
<template>
<div class="canvas-area">
<view-track-bar
ref="viewTrack"
:track-menu="trackMenu"
:font-family="fontFamily"
:is-data-v-mobile="dataVMobile"
class="track-bar"
:style="state.trackBarStyle"
@trackClick="trackClick"
/>
<view-track-bar ref="viewTrack" :track-menu="trackMenu" :font-family="fontFamily" :is-data-v-mobile="dataVMobile"
class="track-bar" :style="state.trackBarStyle" @trackClick="trackClick" />
<div v-if="!isError" ref="chartContainer" class="canvas-content" :id="containerId"></div>
<chart-error v-else :err-msg="errMsg" />
</div>
@ -726,12 +786,32 @@ onBeforeUnmount(() => {
width: 100%;
height: 100%;
z-index: 0;
.canvas-content {
width: 100% !important;
height: 100% !important;
:deep(.g2-tooltip) {
position: fixed !important;
}
}
}
</style>
:deep(.l7-button-control) {
background-color: #000000 !important;
}
:deep(.l7-button-control:not(:disabled):hover) {
background-color: #000000d5 !important;
}
:deep(.l7-button-control .l7-iconfont) {
fill: #fff !important;
color: #fff !important;
}
// :deep(.l7-control-container .l7-top) {
// top: auto !important;
// bottom: 133px !important;
// }</style>

View File

@ -16,7 +16,6 @@ import {
} from 'vue'
import { getData } from '@/api/data-visualization/chart'
import chartViewManager from '@/data-visualization/chart/components/js/panel'
import { useAppStoreWithOut } from '@/data-visualization/store/modules/app'
import { dvMainStoreWithOut } from '@/data-visualization/store/modules/data-visualization/dvMain'
import ViewTrackBar from '@/data-visualization/components/visualization/ViewTrackBar.vue'
import { storeToRefs } from 'pinia'
@ -125,6 +124,7 @@ const state = reactive({
imgEnlarge: false,
imgSrc: ''
})
const PAGE_CHARTS = ['table-info', 'table-normal']
//
let chartData = shallowRef<Partial<Chart['data']>>({
fields: []
@ -133,19 +133,20 @@ let chartData = shallowRef<Partial<Chart['data']>>({
const containerId = 'container-' + showPosition.value + '-' + view.value.id + '-' + suffixId.value
const viewTrack = ref(null)
const calcData = (view: Chart, callback, resetPageInfo = true) => {
if (view.customAttr.basicStyle.tablePageStyle === 'general') {
const calcData = (viewInfo: Chart, callback, resetPageInfo = true) => {
if (viewInfo.customAttr.basicStyle.tablePageStyle === 'general') {
if (state.currentPageSize !== 0) {
view.chartExtRequest.pageSize = state.currentPageSize
viewInfo.chartExtRequest.pageSize = state.currentPageSize
state.pageInfo.pageSize = state.currentPageSize
} else {
viewInfo.chartExtRequest.pageSize = state.pageInfo.pageSize
}
} else {
if(view.chartExtRequest != undefined){
delete view.chartExtRequest.pageSize
delete viewInfo.chartExtRequest?.pageSize
}
}
if (view.tableId || view['dataFrom'] === 'template') {
if (viewInfo.tableId || viewInfo['dataFrom'] === 'template') {
isError.value = false
const v = JSON.parse(JSON.stringify(view))
const v = JSON.parse(JSON.stringify(viewInfo))
getData(v)
.then(res => {
if (res.code && res.code !== 0) {
@ -154,7 +155,7 @@ const calcData = (view: Chart, callback, resetPageInfo = true) => {
} else {
chartData.value = res?.data as Partial<Chart['data']>
state.totalItems = res?.totalItems
dvMainStore.setViewDataDetails(view.id, res)
dvMainStore.setViewDataDetails(viewInfo.id, res)
emit('onDrillFilters', res?.drillFilters)
renderChart(res as unknown as Chart, resetPageInfo)
}
@ -225,7 +226,7 @@ const renderChart = (viewInfo: Chart, resetPageInfo: boolean) => {
nextTick(() => debounceRender(resetPageInfo))
}
const debounceRender = debounce(resetPageInfo => {
const debounceRender = debounce(() => {
myChart?.facet?.timer?.stop()
myChart?.facet?.cancelScrollFrame()
myChart?.destroy()
@ -250,19 +251,13 @@ const debounceRender = debounce(resetPageInfo => {
const setupPage = (chart: ChartObj, resetPageInfo?: boolean) => {
const customAttr = chart.customAttr
if (chart.type !== 'table-info' || customAttr.basicStyle.tablePageMode !== 'page') {
if (!PAGE_CHARTS.includes(chart.type) || customAttr.basicStyle.tablePageMode !== 'page') {
state.showPage = false
return
}
const pageInfo = state.pageInfo
state.pageStyle = customAttr.basicStyle.tablePageStyle
if (state.pageStyle === 'general') {
if (state.currentPageSize === 0) {
state.currentPageSize = pageInfo.pageSize
} else {
pageInfo.pageSize = state.currentPageSize
}
} else {
if (state.pageStyle !== 'general') {
pageInfo.pageSize = customAttr.basicStyle.tablePageSize ?? 20
}
if (state.totalItems > state.pageInfo.pageSize || state.pageStyle === 'general') {
@ -274,6 +269,7 @@ const setupPage = (chart: ChartObj, resetPageInfo?: boolean) => {
if (resetPageInfo) {
state.pageInfo.currentPage = 1
}
dvMainStore.setViewPageInfo(chart.id, state.pageInfo)
}
const mouseMove = () => {
@ -295,7 +291,8 @@ const initScroll = () => {
myChart &&
senior?.scrollCfg?.open &&
chartData.value.tableRow?.length &&
(view.value.type === 'table-normal' || (view.value.type === 'table-info' && !state.showPage))
PAGE_CHARTS.includes(props.view.type) &&
!state.showPage
) {
//
myChart.facet.timer?.stop()
@ -339,7 +336,7 @@ const initScroll = () => {
}
const showPage = computed(() => {
if (view.value.type !== 'table-info') {
if (!PAGE_CHARTS.includes(view.value.type)) {
return false
}
return state.showPage
@ -357,6 +354,7 @@ const handleCurrentChange = pageNum => {
const handlePageSizeChange = pageSize => {
if (state.pageStyle === 'general') {
state.currentPageSize = pageSize
emitter.emit('set-page-size', pageSize)
}
let extReq = { pageSize: pageSize }
if (chartExtRequest.value) {
@ -403,10 +401,9 @@ const action = param => {
state.trackBarStyle.top = barStyleTemp.top + 'px'
}
viewTrack.value.trackButtonClick()
viewTrack.value.trackButtonClick(view.value.id)
}
}
const appStore = useAppStoreWithOut()
const trackClick = trackAction => {
const param = state.pointParam
@ -683,12 +680,6 @@ const autoStyle = computed(() => {
}
})
const autoHeightStyle = computed(() => {
return {
height: 20 * scale.value + 8 + 'px'
}
})
const tabStyle = computed(() => [
{ '--de-pager-color': canvasStyleData.value.component.seniorStyleSetting?.pagerColor }
])
@ -745,7 +736,7 @@ const tablePageClass = computed(() => {
v-else
class="table-page-content"
layout="prev, pager, next, sizes, jumper"
v-model:page-size="state.currentPageSize"
v-model:page-size="state.pageInfo.pageSize"
v-model:current-page="state.pageInfo.currentPage"
:pager-count="5"
:total="state.pageInfo.total"

View File

@ -4,7 +4,7 @@ import { ref } from 'vue'
const { t } = useI18n()
const props = defineProps({
defineProps({
errMsg: {
type: String,
required: true,

View File

@ -1,7 +1,6 @@
<script lang="tsx" setup>
import { computed, reactive, watch } from 'vue'
import { computed } from 'vue'
import { useI18n } from '@/data-visualization/hooks/web/useI18n'
import { reverseColor } from '../util/util'
import { ArrowRight } from '@element-plus/icons-vue'
import { dvMainStoreWithOut } from '@/data-visualization/store/modules/data-visualization/dvMain'
const dvMainStore = dvMainStoreWithOut()
@ -27,51 +26,16 @@ const props = defineProps({
const emit = defineEmits(['onDrillJump'])
const state = reactive({
textColor: '#bbbfc4'
})
const textColor = computed(
() => dvMainStore.canvasStyleData.component.seniorStyleSetting.drillLayerColor
)
// watch(
// [() => props.themeStyle?.backgroundColorSelect, () => props.themeStyle?.color],
// () => {
// loadThemeStyle()
// },
// { deep: true }
// )
const drillJump = index => {
if (index < props.drillFilters.length) {
emit('onDrillJump', index)
}
}
const loadThemeStyle = () => {
let themeStyle = null
if (props.themeStyle) {
themeStyle = JSON.parse(JSON.stringify(props.themeStyle))
if (themeStyle && themeStyle.commonBackground) {
const viewBGColor = themeStyle.commonBackground.color
if (viewBGColor !== '#FFFFFF') {
const reverseValue = reverseColor(viewBGColor)
state.textColor = reverseValue
} else {
state.textColor = null
}
}
if (themeStyle && themeStyle.backgroundColorSelect) {
const panelColor = themeStyle.color
if (panelColor !== '#FFFFFF') {
const reverseValue = reverseColor(panelColor)
state.textColor = reverseValue
} else {
state.textColor = null
}
}
}
}
const drillPathVar = computed(() => [{ '--drill-color': textColor.value }])
</script>

View File

@ -0,0 +1,16 @@
<script lang="tsx" setup></script>
<template>
<div class="scroll-shadow-content">tet</div>
</template>
<style lang="less" scoped>
.scroll-shadow-content {
z-index: 1;
position: absolute;
height: 100%;
width: 100%;
background-color: #ece7e7;
opacity: 0.5;
}
</style>

View File

@ -61,12 +61,13 @@ const dvMainStore = dvMainStoreWithOut()
const { emitter } = useEmitt()
const dePreviewPopDialogRef = ref(null)
let innerRefreshTimer = null
let innerSearchCount = 0
const appStore = useAppStoreWithOut()
const appearanceStore = useAppearanceStoreWithOut()
const isDataEaseBi = computed(() => appStore.getIsDataEaseBi)
const isIframe = computed(() => appStore.getIsIframe)
const emit = defineEmits(['onPointClick'])
const emit = defineEmits(['onPointClick', 'onComponentEvent'])
const {
nowPanelJumpInfo,
@ -76,11 +77,15 @@ const {
canvasStyleData,
mobileInPc,
inMobile,
editMode,
hiddenListStatus
editMode
} = storeToRefs(dvMainStore)
const props = defineProps({
//
commonParams: {
type: Object,
required: false
},
active: {
type: Boolean,
default: false
@ -234,6 +239,7 @@ const buildInnerRefreshTimer = (
innerRefreshTimer = setInterval(() => {
clearViewLinkage()
queryData()
innerSearchCount++
}, timerRefreshTime)
}
}
@ -244,14 +250,6 @@ const clearViewLinkage = () => {
useEmitt().emitter.emit('clearPanelLinkage', { viewId: element.value.id })
}
watch(
[() => view.value],
() => {
initTitle()
},
{ deep: true }
)
watch([() => scale.value], () => {
initTitle()
})
@ -374,17 +372,29 @@ const chartClick = param => {
//
const filter = (firstLoad?: boolean) => {
// const { filter } = useFilter(view.value.id, firstLoad)
// return {
// user: wsCache.get('user.uid'),
// filter,
// linkageFilters: element.value.linkageFilters,
// outerParamsFilters: element.value.outerParamsFilters,
// webParamsFilters: element.value.webParamsFilters,
// drill: state.drillClickDimensionList,
// resultCount: resultCount.value,
// resultMode: resultMode.value
// }
const { filter } = useFilter(view.value.id, firstLoad)
const result = {
user: wsCache.get('user.uid'),
filter,
linkageFilters: element.value.linkageFilters,
outerParamsFilters: element.value.outerParamsFilters,
webParamsFilters: element.value.webParamsFilters,
drill: state.drillClickDimensionList,
resultCount: resultCount.value,
resultMode: resultMode.value
}
//
if (route.path === '/preview' && route.query.taskId) {
const sceneId = view.value['sceneId']
const filterJson = window[`de-report-filter-${sceneId}`]
let filterObj = {}
if (filterJson) {
filterObj = JSON.parse(filterJson)
}
filterObj[view.value.id] = result
window[`de-report-filter-${sceneId}`] = JSON.stringify(filterObj)
}
return result
}
const onDrillFilters = param => {
@ -457,9 +467,16 @@ const jumpClick = param => {
if (isDataEaseBi.value) {
embeddedBaseUrl = embeddedStore.baseUrl
}
const jumpInfoParam = `&jumpInfoParam=${encodeURIComponent(
Base64.encode(JSON.stringify(param))
)}`
//
if (jumpInfo.linkType === 'inner') {
if (jumpInfo.targetDvId) {
const editPreviewParams = ['canvas', 'edit-preview'].includes(showPosition.value)
? '&editPreview=true'
: ''
const filterOuterParams = {}
const curFilter = dvMainStore.getLastViewRequestInfo(param.viewId)
const targetViewInfoList = jumpInfo.targetViewInfoList
@ -492,13 +509,11 @@ const jumpClick = param => {
if (publicLinkStatus.value) {
// ID
if (jumpInfo.publicJumpId) {
let url = `${embeddedBaseUrl}#/de-link/${
jumpInfo.publicJumpId
}?fromLink=true&jumpInfoParam=${encodeURIComponent(
Base64.encode(JSON.stringify(param))
)}`
let url = `${embeddedBaseUrl}#/de-link/${jumpInfo.publicJumpId}?fromLink=true&dvType=${jumpInfo.targetDvType}`
if (attachParamsInfo) {
url = url + attachParamsInfo
url = url + attachParamsInfo + jumpInfoParam + editPreviewParams
} else {
url = url + '&ignoreParams=true' + jumpInfoParam + editPreviewParams
}
const currentUrl = window.location.href
localStorage.setItem('beforeJumpUrl', currentUrl)
@ -507,11 +522,11 @@ const jumpClick = param => {
ElMessage.warning(t('visualization.public_link_tips'))
}
} else {
let url = `${embeddedBaseUrl}#/preview?dvId=${
jumpInfo.targetDvId
}&fromLink=true&jumpInfoParam=${encodeURIComponent(Base64.encode(JSON.stringify(param)))}`
let url = `${embeddedBaseUrl}#/preview?dvId=${jumpInfo.targetDvId}&fromLink=true&dvType=${jumpInfo.targetDvType}`
if (attachParamsInfo) {
url = url + attachParamsInfo
url = url + attachParamsInfo + jumpInfoParam + editPreviewParams
} else {
url = url + '&ignoreParams=true' + jumpInfoParam + editPreviewParams
}
const currentUrl = window.location.href
localStorage.setItem('beforeJumpUrl', currentUrl)
@ -567,13 +582,13 @@ const calcData = params => {
methodName: 'calcData',
args: [
params,
res => {
() => {
loading.value = false
}
]
})
} else {
chartComponent?.value?.calcData?.(params, res => {
chartComponent?.value?.calcData?.(params, () => {
loading.value = false
})
}
@ -691,10 +706,19 @@ const changeChartType = () => {
const changeDataset = () => {
checkFieldIsAllowEmpty()
}
const loadPlugin = ref(false)
onMounted(() => {
if (!view.value.isPlugin) {
state.drillClickDimensionList = view.value?.chartExtRequest?.drill ?? []
queryData(!showPosition.value.includes('viewDialog'))
} else {
const searched = dvMainStore.firstLoadMap.includes(element.value.id)
const queryFilter = filter(!searched)
view.value['chartExtRequest'] = queryFilter
chartExtRequest.value = queryFilter
loadPlugin.value = true
}
if (!listenerEnable.value) {
return
@ -829,7 +853,11 @@ onMounted(() => {
// 1. 2.searchCount =0 3.
const loadingFlag = computed(() => {
return (canvasStyleData.value.refreshViewLoading || searchCount.value === 0) && loading.value
return (
(canvasStyleData.value.refreshViewLoading ||
(searchCount.value === 0 && innerSearchCount === 0)) &&
loading.value
)
})
const chartAreaShow = computed(() => {
@ -903,7 +931,7 @@ function onTitleChange() {
}
const toolTip = computed(() => {
return props.themes === 'dark' ? 'ndark' : 'dark'
return props.themes === 'dark' ? 'light' : 'dark'
})
const marginBottom = computed<string | 0>(() => {
@ -1033,6 +1061,14 @@ const titleTooltipWidth = computed(() => {
}
return '500px'
})
const clearG2Tooltip = () => {
const g2TooltipWrapper = document.getElementById('g2-tooltip-wrapper')
if (g2TooltipWrapper) {
for (const ele of g2TooltipWrapper.children) {
ele.style.display = 'none'
}
}
}
</script>
<template>
@ -1123,7 +1159,7 @@ const titleTooltipWidth = computed(() => {
<!--这里去渲染不同图库的图表-->
<div v-if="allEmptyCheck || (chartAreaShow && !showEmpty)" style="flex: 1; overflow: hidden">
<plugin-component
v-if="view.plugin?.isPlugin"
v-if="view.plugin?.isPlugin && loadPlugin"
:jsname="view.plugin.staticMap['index']"
:scale="scale"
:dynamic-area-id="dynamicAreaId"
@ -1170,9 +1206,17 @@ const titleTooltipWidth = computed(() => {
:themes="canvasStyleData.dashboard.themeColor"
ref="chartComponent"
:view="view"
:element="element"
:show-position="showPosition"
:suffixId="suffixId"
:font-family="fontFamily"
:common-params="commonParams"
@touchstart="clearG2Tooltip"
@onChartClick="chartClick"
@onPointClick="onPointClick"
@onDrillFilters="onDrillFilters"
@onJumpClick="jumpClick"
@onComponentEvent="() => emit('onComponentEvent')"
/>
<chart-component-g2-plot
:scale="scale"
@ -1182,6 +1226,7 @@ const titleTooltipWidth = computed(() => {
:element="element"
:suffixId="suffixId"
:font-family="fontFamily"
:active="active"
v-else-if="
showChartView(ChartLibraryType.G2_PLOT, ChartLibraryType.L7_PLOT, ChartLibraryType.L7)
"
@ -1212,6 +1257,7 @@ const titleTooltipWidth = computed(() => {
v-if="(!chartAreaShow || showEmpty) && !allEmptyCheck"
:themes="canvasStyleData.dashboard.themeColor"
:view-icon="view.type"
@touchstart="clearG2Tooltip"
></chart-empty-info>
<drill-path
:disabled="optType === 'enlarge'"
@ -1240,6 +1286,7 @@ const titleTooltipWidth = computed(() => {
overflow: hidden;
}
.title-container {
position: relative;
margin: 0;
width: 100%;