提交 ba34aef5 authored 作者: taojinlong's avatar taojinlong

Merge branch 'main' of github.com:dataease/dataease into main

...@@ -123,7 +123,7 @@ public class ChartViewService { ...@@ -123,7 +123,7 @@ public class ChartViewService {
} else if (table.getMode() == 1) {// 抽取 } else if (table.getMode() == 1) {// 抽取
DataTableInfoDTO dataTableInfoDTO = new Gson().fromJson(table.getInfo(), DataTableInfoDTO.class); DataTableInfoDTO dataTableInfoDTO = new Gson().fromJson(table.getInfo(), DataTableInfoDTO.class);
String tableName = dataTableInfoDTO.getTable() + "-" + table.getDataSourceId();// todo hBase table name maybe change String tableName = dataTableInfoDTO.getTable() + "-" + table.getDataSourceId();// todo hBase table name maybe change
data = sparkCalc.getData(tableName, xAxis, yAxis, view.getId().split("-")[0]); data = sparkCalc.getData(tableName, xAxis, yAxis, "tmp_" + view.getId().split("-")[0]);
} }
// 图表组件可再扩展 // 图表组件可再扩展
...@@ -136,7 +136,6 @@ public class ChartViewService { ...@@ -136,7 +136,6 @@ public class ChartViewService {
} }
for (String[] d : data) { for (String[] d : data) {
StringBuilder a = new StringBuilder(); StringBuilder a = new StringBuilder();
BigDecimal b = new BigDecimal("0");
for (int i = 0; i < xAxis.size(); i++) { for (int i = 0; i < xAxis.size(); i++) {
if (i == xAxis.size() - 1) { if (i == xAxis.size() - 1) {
a.append(d[i]); a.append(d[i]);
...@@ -147,7 +146,7 @@ public class ChartViewService { ...@@ -147,7 +146,7 @@ public class ChartViewService {
x.add(a.toString()); x.add(a.toString());
for (int i = xAxis.size(); i < xAxis.size() + yAxis.size(); i++) { for (int i = xAxis.size(); i < xAxis.size() + yAxis.size(); i++) {
int j = i - xAxis.size(); int j = i - xAxis.size();
series.get(j).getData().add(new BigDecimal(d[i])); series.get(j).getData().add(new BigDecimal(StringUtils.isEmpty(d[i]) ? "0" : d[i]));
} }
} }
Map<String, Object> map = new HashMap<>(); Map<String, Object> map = new HashMap<>();
......
...@@ -18,6 +18,7 @@ ...@@ -18,6 +18,7 @@
"@riophae/vue-treeselect": "0.4.0", "@riophae/vue-treeselect": "0.4.0",
"axios": "^0.21.1", "axios": "^0.21.1",
"echarts": "^5.0.2", "echarts": "^5.0.2",
"element-resize-detector": "^1.2.2",
"element-ui": "2.13.0", "element-ui": "2.13.0",
"fit2cloud-ui": "^0.1.12", "fit2cloud-ui": "^0.1.12",
"js-cookie": "2.2.0", "js-cookie": "2.2.0",
......
<template>
<span>
<el-dropdown trigger="click" size="mini" @command="clickItem">
<span class="el-dropdown-link">
<el-tag size="small" class="item-axis">
{{ item.name }}<i class="el-icon-arrow-down el-icon--right" />
</el-tag>
<el-dropdown-menu slot="dropdown">
<el-dropdown-item icon="el-icon-delete" divided :command="beforeClickItem('remove')">
<span>{{ $t('chart.delete') }}</span>
</el-dropdown-item>
<slot />
</el-dropdown-menu>
</span>
</el-dropdown>
</span>
</template>
<script>
export default {
name: 'DragItem',
props: {
item: {
type: Object,
required: true
},
index: {
type: Number,
required: true
}
},
data() {
return {
}
},
mounted() {
},
methods: {
clickItem(param) {
if (!param) {
return
}
switch (param.type) {
case 'rename':
this.showRename()
break
case 'remove':
this.removeItem()
break
default:
break
}
},
beforeClickItem(type) {
return {
type: type
}
},
showRename() {
this.item.index = this.index
this.item.renameType = 'dimension'
this.$emit('onNameEdit', this.item)
},
removeItem() {
this.item.index = this.index
this.$emit('closeItem', this.item)
}
}
}
</script>
<style scoped>
.item-axis {
padding: 1px 6px;
margin: 0 3px 2px 3px;
text-align: left;
height: 24px;
line-height: 22px;
display: inline-block;
border-radius: 4px;
box-sizing: border-box;
white-space: nowrap;
}
.item-axis:hover {
background-color: #fdfdfd;
cursor: pointer;
}
span {
font-size: 12px;
}
</style>
<template> <template>
<div class="bg"> <div id="canvasInfo" class="bg">
<div id="preview-parent" class="canvas-container">
<div
class="canvas"
:style="{
width: changeStyleWithScale(canvasStyleData.width) + 'px',
height: changeStyleWithScale(canvasStyleData.height) + 'px',
}"
>
<ComponentWrapper <ComponentWrapper
v-for="(item, index) in componentData" v-for="(item, index) in componentDataInfo"
:key="index" :key="index"
:config="item" :config="item"
/> />
</div> </div>
</div>
</div>
</template> </template>
<script> <script>
...@@ -23,6 +13,10 @@ import { getStyle } from '@/components/canvas/utils/style' ...@@ -23,6 +13,10 @@ import { getStyle } from '@/components/canvas/utils/style'
import { mapState } from 'vuex' import { mapState } from 'vuex'
import ComponentWrapper from './ComponentWrapper' import ComponentWrapper from './ComponentWrapper'
import { changeStyleWithScale } from '@/components/canvas/utils/translate' import { changeStyleWithScale } from '@/components/canvas/utils/translate'
import { uuid } from 'vue-uuid'
import { deepCopy } from '@/components/canvas/utils/utils'
import eventBus from '@/components/canvas/utils/eventBus'
import elementResizeDetectorMaker from 'element-resize-detector'
export default { export default {
components: { ComponentWrapper }, components: { ComponentWrapper },
...@@ -36,20 +30,84 @@ export default { ...@@ -36,20 +30,84 @@ export default {
default: false default: false
} }
}, },
computed: mapState([ data() {
return {
isShowPreview: false,
panelId: '',
needToChangeHeight: [
'top',
'height',
'fontSize',
'borderWidth'
],
needToChangeWidth: [
'left',
'width'
],
scaleWidth: '100',
scaleHeight: '100',
timer: null,
componentDataShow: []
}
},
computed: {
// 此处单独计算componentData的值 不放入全局mapState中
componentDataInfo() {
return this.componentDataShow
},
...mapState([
'componentData', 'componentData',
'canvasStyleData' 'canvasStyleData'
]), ])
},
mounted() { mounted() {
// 计算组件当前合适宽度 debugger
const _this = this
const erd = elementResizeDetectorMaker()
// 监听div变动事件
erd.listenTo(document.getElementById('canvasInfo'), element => {
_this.$nextTick(() => {
_this.restore()
})
})
// 监听数据变动事件
eventBus.$on('componentDataChange', () => {
_this.restore()
})
}, },
methods: { methods: {
changeStyleWithScale, changeStyleWithScale,
getStyle, getStyle,
restore() {
close() { const canvasHeight = document.getElementById('canvasInfo').offsetHeight
this.$emit('change', false) const canvasWidth = document.getElementById('canvasInfo').offsetWidth
this.scaleWidth = canvasWidth * 100 / parseInt(this.canvasStyleData.width)// 获取宽度比
this.scaleHeight = canvasHeight * 100 / parseInt(this.canvasStyleData.height)// 获取高度比
this.handleScaleChange()
},
resetID(data) {
data.forEach(item => {
item.id = uuid.v1()
})
return data
},
format(value, scale) {
return value * parseInt(scale) / 100
},
handleScaleChange() {
const componentData = deepCopy(this.componentData)
componentData.forEach(component => {
Object.keys(component.style).forEach(key => {
if (this.needToChangeHeight.includes(key)) {
component.style[key] = this.format(component.style[key], this.scaleHeight)
}
if (this.needToChangeWidth.includes(key)) {
component.style[key] = this.format(component.style[key], this.scaleWidth)
}
})
})
this.componentDataShow = componentData
eventBus.$emit('resizing', '')
} }
} }
} }
...@@ -57,12 +115,14 @@ export default { ...@@ -57,12 +115,14 @@ export default {
<style lang="scss" scoped> <style lang="scss" scoped>
.bg { .bg {
min-width: 600px;
min-height: 300px;
width: 100%; width: 100%;
height: 100%; height: 100%;
border: 1px solid #E6E6E6;
.canvas-container { .canvas-container {
width: 100%; width: 100%;
height: 100%; height: 100%;
overflow: auto;
.canvas { .canvas {
position: relative; position: relative;
margin: auto; margin: auto;
......
<template> <template>
<div ref="element" class="bg"> <div id="canvasInfo" class="bg">
<ComponentWrapper <ComponentWrapper
v-for="(item, index) in componentDataInfo" v-for="(item, index) in componentDataInfo"
:key="index" :key="index"
...@@ -10,12 +10,12 @@ ...@@ -10,12 +10,12 @@
<script> <script>
import { getStyle } from '@/components/canvas/utils/style' import { getStyle } from '@/components/canvas/utils/style'
import { mapState } from 'vuex'
import ComponentWrapper from './ComponentWrapper' import ComponentWrapper from './ComponentWrapper'
import { changeStyleWithScale } from '@/components/canvas/utils/translate' import { changeStyleWithScale } from '@/components/canvas/utils/translate'
import { uuid } from 'vue-uuid' import { uuid } from 'vue-uuid'
import { deepCopy } from '@/components/canvas/utils/utils' import { deepCopy } from '@/components/canvas/utils/utils'
import eventBus from '@/components/canvas/utils/eventBus' import eventBus from '@/components/canvas/utils/eventBus'
import elementResizeDetectorMaker from 'element-resize-detector'
import { get } from '@/api/panel/panel' import { get } from '@/api/panel/panel'
export default { export default {
...@@ -47,6 +47,7 @@ export default { ...@@ -47,6 +47,7 @@ export default {
scaleWidth: '100', scaleWidth: '100',
scaleHeight: '100', scaleHeight: '100',
timer: null, timer: null,
componentDataSource: {},
componentData: {}, componentData: {},
canvasStyleData: {} canvasStyleData: {}
...@@ -58,8 +59,17 @@ export default { ...@@ -58,8 +59,17 @@ export default {
} }
}, },
mounted() { mounted() {
const _this = this
// 加载数据 // 加载数据
this.restore() _this.restore()
const erd = elementResizeDetectorMaker()
// 监听div变动事件
erd.listenTo(document.getElementById('canvasInfo'), element => {
_this.$nextTick(() => {
_this.resize()
})
})
window.onresize = () => { window.onresize = () => {
debugger debugger
this.resize() this.resize()
...@@ -82,7 +92,7 @@ export default { ...@@ -82,7 +92,7 @@ export default {
this.panelId = this.$route.path.split('/')[2] this.panelId = this.$route.path.split('/')[2]
// 加载视图数据 // 加载视图数据
get('panel/group/findOne/' + this.panelId).then(response => { get('panel/group/findOne/' + this.panelId).then(response => {
this.componentData = this.resetID(JSON.parse(response.data.panelData)) this.componentDataSource = this.resetID(JSON.parse(response.data.panelData))
this.canvasStyleData = JSON.parse(response.data.panelStyle) this.canvasStyleData = JSON.parse(response.data.panelStyle)
this.resize() this.resize()
}) })
...@@ -98,7 +108,7 @@ export default { ...@@ -98,7 +108,7 @@ export default {
return value * parseInt(scale) / 100 return value * parseInt(scale) / 100
}, },
handleScaleChange() { handleScaleChange() {
const componentData = deepCopy(this.componentData) const componentData = deepCopy(this.componentDataSource)
componentData.forEach(component => { componentData.forEach(component => {
Object.keys(component.style).forEach(key => { Object.keys(component.style).forEach(key => {
if (this.needToChangeHeight.includes(key)) { if (this.needToChangeHeight.includes(key)) {
...@@ -118,6 +128,8 @@ export default { ...@@ -118,6 +128,8 @@ export default {
<style lang="scss" scoped> <style lang="scss" scoped>
.bg { .bg {
min-width: 800px;
min-height: 600px;
width: 100%; width: 100%;
height: 100%; height: 100%;
overflow: auto; overflow: auto;
......
...@@ -9,7 +9,7 @@ ...@@ -9,7 +9,7 @@
<!--<i v-if="asideHidden" class="el-icon-arrow-right"/>--> <!--<i v-if="asideHidden" class="el-icon-arrow-right"/>-->
<!--</div>--> <!--</div>-->
<slot /> <slot />
<de-horizontal-drag-bar /> <de-horizontal-drag-bar v-if="showDragBar" />
</el-aside> </el-aside>
</template> </template>
...@@ -26,6 +26,10 @@ export default { ...@@ -26,6 +26,10 @@ export default {
enableAsideHidden: { enableAsideHidden: {
type: Boolean, type: Boolean,
default: true default: true
},
showDragBar: {
type: Boolean,
default: true
} }
}, },
data() { data() {
......
...@@ -42,6 +42,12 @@ class TimeYearServiceImpl extends WidgetService { ...@@ -42,6 +42,12 @@ class TimeYearServiceImpl extends WidgetService {
beforeToDraw() { beforeToDraw() {
} }
filterFieldMethod(fields) {
return fields.filter(field => {
return field['deType'] === 1
})
}
} }
const timeYearServiceImpl = new TimeYearServiceImpl({ name: 'timeYearWidget' }) const timeYearServiceImpl = new TimeYearServiceImpl({ name: 'timeYearWidget' })
export default timeYearServiceImpl export default timeYearServiceImpl
<?xml version="1.0" standalone="no"?><!DOCTYPE svg PUBLIC "-//W3C//DTD SVG 1.1//EN" "http://www.w3.org/Graphics/SVG/1.1/DTD/svg11.dtd"><svg t="1617857636853" class="icon" viewBox="0 0 1024 1024" version="1.1" xmlns="http://www.w3.org/2000/svg" p-id="859" xmlns:xlink="http://www.w3.org/1999/xlink" width="200" height="200"><defs><style type="text/css"></style></defs><path d="M172.860952 769.462857c55.832381 66.072381 132.291048 92.769524 208.725334 88.064l4.412952-251.562667c-10.288762-4.705524-24.990476-4.705524-35.279238-15.725714L172.860952 769.487238z m239.616-404.041143l-5.90019-169.813333c-55.832381 0-97.01181 15.725714-142.57981 59.733333l76.434286 136.801524c24.990476-15.725714 45.592381-26.721524 72.045714-26.721524z m122.002286 125.781334h357.229714c0-273.554286-199.92381-490.544762-449.828571-490.544762v371.053714c47.030857 4.705524 92.598857 59.733333 92.598857 119.466667z m-5.875809 22.016c-4.412952 26.721524-24.990476 55.02781-45.592381 77.043809l361.642666 386.755048C951.978667 862.232381 1024 698.733714 1024 517.924571H528.579048v-4.705523z m-111.713524 97.475047h-4.412953V997.424762c111.713524-4.705524 219.014095-55.02781 301.348572-125.781333L463.920762 604.40381c-16.164571 6.290286-30.866286 6.290286-47.055238 6.290285z m-224.914286-92.769524c0 55.02781 20.577524 92.769524 51.44381 130.486858l91.136-77.04381c-14.701714-15.701333-24.990476-33.01181-30.866286-59.733333l-111.713524 6.290285z m113.176381-33.011809c0-33.01181 14.701714-55.02781 30.866286-77.04381L172.860952 186.197333C90.526476 245.930667 39.082667 338.70019 24.380952 447.146667l280.771048 37.741714c0 6.290286 0 0 0 0z" p-id="860"></path></svg>
...@@ -693,7 +693,11 @@ export default { ...@@ -693,7 +693,11 @@ export default {
filter_null: '为空', filter_null: '为空',
filter_not_null: '不为空', filter_not_null: '不为空',
filter_include: '包含', filter_include: '包含',
filter_not_include: '不包含' filter_not_include: '不包含',
rose_type: '玫瑰图模式',
radius_mode: '半径',
area_mode: '面积',
rose_radius: '圆角'
}, },
dataset: { dataset: {
datalist: '数据集', datalist: '数据集',
...@@ -770,7 +774,10 @@ export default { ...@@ -770,7 +774,10 @@ export default {
current_update_time: '当前更新时间', current_update_time: '当前更新时间',
param: '参数', param: '参数',
edit_sql: '编辑SQL', edit_sql: '编辑SQL',
showRow: '显示行' showRow: '显示行',
add_excel_table: '添加Excel数据集',
add_custom_table: '添加自助数据集',
upload_file: '上传文件'
}, },
datasource: { datasource: {
create: '新建数据连接', create: '新建数据连接',
......
...@@ -144,3 +144,30 @@ div:focus { ...@@ -144,3 +144,30 @@ div:focus {
border: none !important; border: none !important;
} }
} }
.de-filter-data-table {
.el-table__body-wrapper >table>{
tbody {
.el-table__row {
:hover {
cursor: pointer;
}
td {
border: none !important;
}
}
}
}
}
.de-filter-data-table::before {
height: 0px !important;
}
.custom-component-class {
width: 100%;
div {
width: 100% !important;
}
}
...@@ -42,7 +42,7 @@ $subMenuHover:#1682e6; ...@@ -42,7 +42,7 @@ $subMenuHover:#1682e6;
$sideBarWidth: 210px; $sideBarWidth: 210px;
$topBarHeight: 56px; $topBarHeight: 56px;
$contentHeight: calc(100vh - 56px); $contentHeight: 100vh;
// the :export directive is the magic sauce for webpack // the :export directive is the magic sauce for webpack
// https://www.bluematador.com/blog/how-to-share-variables-between-js-and-sass // https://www.bluematador.com/blog/how-to-share-variables-between-js-and-sass
......
...@@ -15,6 +15,8 @@ export const DEFAULT_SIZE = { ...@@ -15,6 +15,8 @@ export const DEFAULT_SIZE = {
lineArea: false, lineArea: false,
pieInnerRadius: 0, pieInnerRadius: 0,
pieOuterRadius: 60, pieOuterRadius: 60,
pieRoseType: 'radius',
pieRoseRadius: 5,
funnelWidth: 80, funnelWidth: 80,
radarShape: 'polygon' radarShape: 'polygon'
} }
......
...@@ -50,3 +50,18 @@ export function basePieOption(chart_option, chart) { ...@@ -50,3 +50,18 @@ export function basePieOption(chart_option, chart) {
return chart_option return chart_option
} }
export function rosePieOption(chart_option, chart) {
basePieOption(chart_option, chart)
let customAttr = {}
if (chart.customAttr) {
customAttr = JSON.parse(chart.customAttr)
if (customAttr.size) {
chart_option.series[0].roseType = customAttr.size.pieRoseType
chart_option.series[0].itemStyle = {
borderRadius: customAttr.size.pieRoseRadius
}
}
}
return chart_option
}
...@@ -8,7 +8,7 @@ ...@@ -8,7 +8,7 @@
import { BASE_BAR, BASE_LINE, HORIZONTAL_BAR, BASE_PIE, BASE_FUNNEL, BASE_RADAR } from '../chart/chart' import { BASE_BAR, BASE_LINE, HORIZONTAL_BAR, BASE_PIE, BASE_FUNNEL, BASE_RADAR } from '../chart/chart'
import { baseBarOption, stackBarOption, horizontalBarOption, horizontalStackBarOption } from '../chart/bar/bar' import { baseBarOption, stackBarOption, horizontalBarOption, horizontalStackBarOption } from '../chart/bar/bar'
import { baseLineOption, stackLineOption } from '../chart/line/line' import { baseLineOption, stackLineOption } from '../chart/line/line'
import { basePieOption } from '../chart/pie/pie' import { basePieOption, rosePieOption } from '../chart/pie/pie'
import { baseFunnelOption } from '../chart/funnel/funnel' import { baseFunnelOption } from '../chart/funnel/funnel'
import { baseRadarOption } from '../chart/radar/radar' import { baseRadarOption } from '../chart/radar/radar'
import eventBus from '@/components/canvas/utils/eventBus' import eventBus from '@/components/canvas/utils/eventBus'
...@@ -73,6 +73,8 @@ export default { ...@@ -73,6 +73,8 @@ export default {
chart_option = stackLineOption(JSON.parse(JSON.stringify(BASE_LINE)), chart) chart_option = stackLineOption(JSON.parse(JSON.stringify(BASE_LINE)), chart)
} else if (chart.type === 'pie') { } else if (chart.type === 'pie') {
chart_option = basePieOption(JSON.parse(JSON.stringify(BASE_PIE)), chart) chart_option = basePieOption(JSON.parse(JSON.stringify(BASE_PIE)), chart)
} else if (chart.type === 'pie-rose') {
chart_option = rosePieOption(JSON.parse(JSON.stringify(BASE_PIE)), chart)
} else if (chart.type === 'funnel') { } else if (chart.type === 'funnel') {
chart_option = baseFunnelOption(JSON.parse(JSON.stringify(BASE_FUNNEL)), chart) chart_option = baseFunnelOption(JSON.parse(JSON.stringify(BASE_FUNNEL)), chart)
} else if (chart.type === 'radar') { } else if (chart.type === 'radar') {
......
...@@ -57,6 +57,18 @@ ...@@ -57,6 +57,18 @@
<el-form-item :label="$t('chart.pie_outer_radius')" class="form-item form-item-slider"> <el-form-item :label="$t('chart.pie_outer_radius')" class="form-item form-item-slider">
<el-slider v-model="sizeForm.pieOuterRadius" show-input :show-input-controls="false" input-size="mini" :min="0" :max="100" @change="changeBarSizeCase" /> <el-slider v-model="sizeForm.pieOuterRadius" show-input :show-input-controls="false" input-size="mini" :min="0" :max="100" @change="changeBarSizeCase" />
</el-form-item> </el-form-item>
<span v-if="chart.type && chart.type.includes('pie-rose')">
<el-form-item :label="$t('chart.rose_type')" class="form-item">
<el-radio-group v-model="sizeForm.pieRoseType" size="mini" @change="changeBarSizeCase">
<el-radio-button label="radius">{{ $t('chart.radius_mode') }}</el-radio-button>
<el-radio-button label="area">{{ $t('chart.area_mode') }}</el-radio-button>
</el-radio-group>
</el-form-item>
<el-form-item :label="$t('chart.rose_radius')" class="form-item form-item-slider">
<el-slider v-model="sizeForm.pieRoseRadius" show-input :show-input-controls="false" input-size="mini" :min="0" :max="100" @change="changeBarSizeCase" />
</el-form-item>
</span>
</el-form> </el-form>
<el-form v-if="chart.type && chart.type.includes('funnel')" ref="sizeFormPie" :model="sizeForm" label-width="80px" size="mini"> <el-form v-if="chart.type && chart.type.includes('funnel')" ref="sizeFormPie" :model="sizeForm" label-width="80px" size="mini">
......
...@@ -90,8 +90,15 @@ ...@@ -90,8 +90,15 @@
<div style="width: 100%;display: flex;display: -webkit-flex;justify-content: space-between;flex-direction: row;flex-wrap: wrap;"> <div style="width: 100%;display: flex;display: -webkit-flex;justify-content: space-between;flex-direction: row;flex-wrap: wrap;">
<el-radio value="line-stack" label="line-stack"><svg-icon icon-class="line-stack" class="chart-icon" /></el-radio> <el-radio value="line-stack" label="line-stack"><svg-icon icon-class="line-stack" class="chart-icon" /></el-radio>
<el-radio value="pie" label="pie"><svg-icon icon-class="pie" class="chart-icon" /></el-radio> <el-radio value="pie" label="pie"><svg-icon icon-class="pie" class="chart-icon" /></el-radio>
<el-radio value="pie-rose" label="pie-rose"><svg-icon icon-class="pie-rose" class="chart-icon" /></el-radio>
<el-radio value="funnel" label="funnel"><svg-icon icon-class="funnel" class="chart-icon" /></el-radio> <el-radio value="funnel" label="funnel"><svg-icon icon-class="funnel" class="chart-icon" /></el-radio>
<el-radio value="radar" label="radar"><svg-icon icon-class="radar" class="chart-icon" /></el-radio> <el-radio value="radar" label="radar"><svg-icon icon-class="radar" class="chart-icon" /></el-radio>
</div>
<div>
<el-radio value="" label="" disabled class="disabled-none-cursor"><svg-icon icon-class="" class="chart-icon" /></el-radio>
<el-radio value="" label="" disabled class="disabled-none-cursor"><svg-icon icon-class="" class="chart-icon" /></el-radio>
<el-radio value="" label="" disabled class="disabled-none-cursor"><svg-icon icon-class="" class="chart-icon" /></el-radio>
<el-radio value="" label="" disabled class="disabled-none-cursor"><svg-icon icon-class="" class="chart-icon" /></el-radio>
<el-radio value="" label="" disabled class="disabled-none-cursor"><svg-icon icon-class="" class="chart-icon" /></el-radio> <el-radio value="" label="" disabled class="disabled-none-cursor"><svg-icon icon-class="" class="chart-icon" /></el-radio>
</div> </div>
</el-radio-group> </el-radio-group>
...@@ -321,7 +328,7 @@ export default { ...@@ -321,7 +328,7 @@ export default {
const view = JSON.parse(JSON.stringify(this.view)) const view = JSON.parse(JSON.stringify(this.view))
view.id = this.view.id view.id = this.view.id
view.sceneId = this.view.sceneId view.sceneId = this.view.sceneId
view.name = this.table.name view.name = this.view.name ? this.view.name : this.table.name
view.tableId = this.view.tableId view.tableId = this.view.tableId
// view.xaxis.forEach(function(ele) { // view.xaxis.forEach(function(ele) {
// if (!ele.summary || ele.summary === '') { // if (!ele.summary || ele.summary === '') {
......
<template>
<el-col>
<el-row>
<el-row style="height: 26px;">
<span style="line-height: 26px;">
{{ $t('dataset.add_custom_table') }}
</span>
<el-row style="float: right">
<el-button size="mini" @click="cancel">
{{ $t('dataset.cancel') }}
</el-button>
<el-button size="mini" type="primary" :disabled="checkTableList.length < 1" @click="save">
{{ $t('dataset.confirm') }}
</el-button>
</el-row>
</el-row>
<el-divider />
<el-row>
<el-col>
123
</el-col>
<el-col>
456
</el-col>
</el-row>
</el-row>
</el-col>
</template>
<script>
import { post } from '@/api/dataset/dataset'
export default {
name: 'AddCustom',
props: {
param: {
type: Object,
default: null
}
},
data() {
return {
searchTable: '',
options: [],
dataSource: '',
tables: [],
checkTableList: [],
mode: '0',
tableData: []
}
},
watch: {
// dataSource(val) {
// if (val) {
// post('/datasource/getTables', { id: val }).then(response => {
// this.tables = response.data
// this.tableData = JSON.parse(JSON.stringify(this.tables))
// })
// }
// },
// searchTable(val) {
// if (val && val !== '') {
// this.tableData = JSON.parse(JSON.stringify(this.tables.filter(ele => { return ele.includes(val) })))
// } else {
// this.tableData = JSON.parse(JSON.stringify(this.tables))
// }
// }
},
mounted() {
// this.initDataSource()
},
activated() {
// this.initDataSource()
},
methods: {
// initDataSource() {
// listDatasource().then(response => {
// this.options = response.data
// })
// },
save() {
// console.log(this.checkTableList);
// console.log(this.scene);
const sceneId = this.param.id
const dataSourceId = this.dataSource
const tables = []
// const mode = this.mode
this.checkTableList.forEach(function(name) {
tables.push({
name: name,
sceneId: sceneId,
dataSourceId: dataSourceId,
type: 'excel',
mode: 1
})
})
post('/dataset/table/batchAdd', tables).then(response => {
this.$store.dispatch('dataset/setSceneData', new Date().getTime())
this.cancel()
})
},
cancel() {
this.dataReset()
// this.$router.push('/dataset/home')
this.$emit('switchComponent', { name: '' })
},
dataReset() {
this.searchTable = ''
this.options = []
this.dataSource = ''
this.tables = []
this.checkTableList = []
}
}
}
</script>
<style scoped>
.el-divider--horizontal {
margin: 12px 0;
}
.form-item {
margin-bottom: 6px;
}
.el-checkbox {
margin-bottom: 14px;
margin-left: 0;
margin-right: 14px;
}
.el-checkbox.is-bordered + .el-checkbox.is-bordered {
margin-left: 0;
}
span{
font-size: 14px;
}
</style>
<template>
<el-col>
<el-row>
<el-row style="height: 26px;">
<span style="line-height: 26px;">
{{ $t('dataset.add_excel_table') }}
</span>
<el-row style="float: right">
<el-button size="mini" @click="cancel">
{{ $t('dataset.cancel') }}
</el-button>
<el-button size="mini" type="primary" @click="save">
{{ $t('dataset.confirm') }}
</el-button>
</el-row>
</el-row>
<el-divider />
<el-row>
<el-row>
<el-col style="width: 500px;">
<el-form :model="form" :inline="true" size="mini" class="row-style">
<el-form-item>
<el-input v-model="form.name" :placeholder="$t('commons.name')" />
</el-form-item>
<el-form-item>
<el-upload
action="https://jsonplaceholder.typicode.com/posts/"
:multiple="false"
:show-file-list="false"
accept=".xls,.xlsx,.csv"
>
<el-button size="mini" type="primary">{{ $t('dataset.upload_file') }}</el-button>
</el-upload>
</el-form-item>
</el-form>
</el-col>
</el-row>
</el-row>
<el-row>
<el-card class="box-card dataPreview" shadow="never">
<div slot="header" class="clearfix">
<span>{{ $t('dataset.data_preview') }}</span>
</div>
<div class="text item">
<ux-grid
ref="plxTable"
size="mini"
style="width: 100%;"
:height="height"
:checkbox-config="{highlight: true}"
:width-resize="true"
>
<ux-table-column
v-for="field in fields"
:key="field.fieldName"
min-width="200px"
:field="field.fieldName"
:title="field.remarks"
:resizable="true"
/>
</ux-grid>
</div>
</el-card>
</el-row>
</el-row>
</el-col>
</template>
<script>
import { post } from '@/api/dataset/dataset'
export default {
name: 'AddExcel',
props: {
param: {
type: Object,
default: null
}
},
data() {
return {
form: {
name: ''
},
fields: [],
mode: '1',
height: 600
}
},
watch: {
// dataSource(val) {
// if (val) {
// post('/datasource/getTables', { id: val }).then(response => {
// this.tables = response.data
// this.tableData = JSON.parse(JSON.stringify(this.tables))
// })
// }
// },
// searchTable(val) {
// if (val && val !== '') {
// this.tableData = JSON.parse(JSON.stringify(this.tables.filter(ele => { return ele.includes(val) })))
// } else {
// this.tableData = JSON.parse(JSON.stringify(this.tables))
// }
// }
},
mounted() {
// this.initDataSource()
},
activated() {
// this.initDataSource()
},
methods: {
// initDataSource() {
// listDatasource().then(response => {
// this.options = response.data
// })
// },
save() {
// console.log(this.checkTableList);
// console.log(this.scene);
const sceneId = this.param.id
const dataSourceId = this.dataSource
const tables = []
const mode = this.mode
this.checkTableList.forEach(function(name) {
tables.push({
name: name,
sceneId: sceneId,
dataSourceId: dataSourceId,
type: 'excel',
mode: parseInt(mode)
})
})
post('/dataset/table/batchAdd', tables).then(response => {
this.$store.dispatch('dataset/setSceneData', new Date().getTime())
this.cancel()
})
},
cancel() {
this.dataReset()
// this.$router.push('/dataset/home')
this.$emit('switchComponent', { name: '' })
},
dataReset() {
this.searchTable = ''
this.options = []
this.dataSource = ''
this.tables = []
this.checkTableList = []
}
}
}
</script>
<style scoped>
.el-divider--horizontal {
margin: 12px 0;
}
.form-item {
margin-bottom: 6px;
}
.el-checkbox {
margin-bottom: 14px;
margin-left: 0;
margin-right: 14px;
}
.el-checkbox.is-bordered + .el-checkbox.is-bordered {
margin-left: 0;
}
span{
font-size: 14px;
}
.row-style>>>.el-form-item__label{
font-size: 12px;
}
.dataPreview>>>.el-card__header{
padding: 6px 8px;
}
.dataPreview>>>.el-card__body{
padding:10px;
}
</style>
...@@ -536,10 +536,10 @@ export default { ...@@ -536,10 +536,10 @@ export default {
this.addData('AddSQL') this.addData('AddSQL')
break break
case 'excel': case 'excel':
this.$message(param.type) this.addData('AddExcel')
break break
case 'custom': case 'custom':
this.$message(param.type) this.addData('AddCustom')
break break
} }
}, },
......
...@@ -22,10 +22,12 @@ import DataHome from './data/DataHome' ...@@ -22,10 +22,12 @@ import DataHome from './data/DataHome'
import ViewTable from './data/ViewTable' import ViewTable from './data/ViewTable'
import AddDB from './add/AddDB' import AddDB from './add/AddDB'
import AddSQL from './add/AddSQL' import AddSQL from './add/AddSQL'
import AddExcel from './add/AddExcel'
import AddCustom from './add/AddCustom'
export default { export default {
name: 'DataSet', name: 'DataSet',
components: { DeMainContainer, DeContainer, DeAsideContainer, Group, DataHome, ViewTable, AddDB, AddSQL }, components: { DeMainContainer, DeContainer, DeAsideContainer, Group, DataHome, ViewTable, AddDB, AddSQL, AddExcel, AddCustom },
data() { data() {
return { return {
component: DataHome, component: DataHome,
...@@ -46,6 +48,12 @@ export default { ...@@ -46,6 +48,12 @@ export default {
case 'AddSQL': case 'AddSQL':
this.component = AddSQL this.component = AddSQL
break break
case 'AddExcel':
this.component = AddExcel
break
case 'AddCustom':
this.component = AddCustom
break
default: default:
this.component = DataHome this.component = DataHome
break break
......
...@@ -69,11 +69,31 @@ ...@@ -69,11 +69,31 @@
</de-container> </de-container>
<el-dialog <el-dialog
v-if="filterVisible"
title="过滤组件" title="过滤组件"
:visible.sync="filterVisible" :visible.sync="filterVisible"
custom-class="de-filter-dialog" custom-class="de-filter-dialog"
> >
<filter-dialog /> <filter-dialog v-if="filterVisible" :widget-id="currentWidgetId">
<de-drawing-widget
v-if="filterVisible && currentComponent"
:id="'component' + currentComponent.id"
style="width: 100% !important;"
class="component"
:element="currentComponent"
:item="currentComponent"
/>
</filter-dialog>
<!-- <div slot="footer" class="dialog-footer">
<el-button type="text" @click="editPasswordVisible = false">{{ $t('commons.cancel') }}</el-button>
<el-button type="primary" @click="editUserPassword('editPasswordForm')">确认</el-button>
</div> -->
<div style="text-align: end !important;margin: 0 15px !important;">
<span slot="footer">
<el-button @click="cancelFilter">取 消</el-button>
<el-button type="primary" @click="sureFilter">确 定</el-button>
</span>
</div>
</el-dialog> </el-dialog>
</el-container> </el-container>
...@@ -123,7 +143,10 @@ export default { ...@@ -123,7 +143,10 @@ export default {
showIndex: -1, showIndex: -1,
activeName: 'attr', activeName: 'attr',
reSelectAnimateIndex: undefined, reSelectAnimateIndex: undefined,
filterVisible: false filterVisible: false,
currentWidgetId: null,
currentWidget: null,
currentComponent: null
} }
}, },
...@@ -224,11 +247,12 @@ export default { ...@@ -224,11 +247,12 @@ export default {
// 画布 // 画布
restore() { restore() {
// 用保存的数据恢复画布 // 用保存的数据恢复画布
if (localStorage.getItem('canvasData')) { let canvasData = null
this.$store.commit('setComponentData', this.resetID(JSON.parse(localStorage.getItem('canvasData')))) if ((canvasData = localStorage.getItem('canvasData')) !== null && canvasData !== 'null') {
this.$store.commit('setComponentData', this.resetID(JSON.parse(canvasData)))
} }
if (localStorage.getItem('canvasStyle')) { if (canvasData && canvasData !== 'null') {
this.$store.commit('setCanvasStyle', JSON.parse(localStorage.getItem('canvasStyle'))) this.$store.commit('setCanvasStyle', JSON.parse(localStorage.getItem('canvasStyle')))
} }
}, },
...@@ -260,13 +284,17 @@ export default { ...@@ -260,13 +284,17 @@ export default {
} }
}) })
} else { } else {
const wd = ApplicationContext.getService(componentInfo.id) this.currentWidget = ApplicationContext.getService(componentInfo.id)
if (wd.filterDialog) { if (this.currentWidget.filterDialog) {
this.show = false this.show = false
this.openFilterDiolog() this.currentComponent = deepCopy(this.currentWidget)
this.currentComponent.style.top = e.offsetY
this.currentComponent.style.left = e.offsetX
this.currentComponent.id = newComponentId
this.openFilterDiolog(componentInfo.id)
return return
} }
component = deepCopy(wd) component = deepCopy(this.currentWidget)
} }
component.style.top = e.offsetY component.style.top = e.offsetY
...@@ -277,7 +305,6 @@ export default { ...@@ -277,7 +305,6 @@ export default {
}, },
handleDragOver(e) { handleDragOver(e) {
console.log('handleDragOver123')
e.preventDefault() e.preventDefault()
e.dataTransfer.dropEffect = 'copy' e.dataTransfer.dropEffect = 'copy'
}, },
...@@ -300,10 +327,22 @@ export default { ...@@ -300,10 +327,22 @@ export default {
this.$store.commit('hideContextMenu') this.$store.commit('hideContextMenu')
} }
}, },
openFilterDiolog() { openFilterDiolog(widgetId) {
this.currentWidgetId = widgetId
this.filterVisible = true this.filterVisible = true
},
cancelFilter() {
this.filterVisible = false
this.currentWidgetId = null
this.currentWidget = null
this.currentComponent = null
},
sureFilter() {
const component = deepCopy(this.currentComponent)
this.$store.commit('addComponent', { component })
this.$store.commit('recordSnapshot')
this.cancelFilter()
} }
} }
} }
</script> </script>
...@@ -371,7 +410,6 @@ export default { ...@@ -371,7 +410,6 @@ export default {
.leftPanel { .leftPanel {
transform: translate(0); transform: translate(0);
} }
} }
</style> </style>
<template> <template>
<de-container class="de-dialog-container"> <de-container class="de-dialog-container">
<de-aside-container class="ms-aside-container"> <de-aside-container :show-drag-bar="false" class="ms-aside-container">
<el-tabs v-model="activeName" @tab-click="handleClick"> <el-tabs v-model="activeName" class="filter-dialog-tabs">
<el-tab-pane :lazy="true" class="de-tab" label="按表选择" name="dataset">按表选择</el-tab-pane> <el-tab-pane :lazy="true" class="de-tab" label="按表选择" name="dataset">
<div class="component-header filter-common">
<el-breadcrumb separator-class="el-icon-arrow-right">
<el-breadcrumb-item v-for="bread in dataSetBreads" :key="bread.label">
<a v-if="bread.link" :class="{'link-text' : bread.link}" @click="backToLink(bread)"> {{ bread.label }}</a>
<span v-else>{{ bread.label }}</span>
</el-breadcrumb-item>
</el-breadcrumb>
</div>
<div class="component-search filter-common">
<el-input
placeholder="请输入内容"
prefix-icon="el-icon-search"
/>
</div>
<!-- <div class="component-result-content filter-common" @dragstart="handleDragStart" @dragend="handleDragEnd"> -->
<div class="component-result-content filter-common">
<el-tree
v-if="showDomType === 'tree'"
:data="data"
:props="defaultProps"
:render-content="renderNode"
@node-click="handleNodeClick"
/>
<el-table
v-else-if="showDomType === 'db'"
class="de-filter-data-table"
:data="sceneDatas"
:show-header="false"
size="mini"
:highlight-current-row="true"
style="width: 100%"
>
<el-table-column prop="name" label="名称">
<template v-if="showDomType === 'db'" :id="scope.row.id" slot-scope="scope">
<div class="filter-db-row" @click="showFieldDatas(scope.row)">
<i class="el-icon-s-data" />
<span> {{ scope.row.name }}</span>
</div>
</template>
</el-table-column>
</el-table>
<div v-else-if="showDomType === 'field'">
<draggable
v-model="fieldDatas"
:options="{group:{name: 'dimension',pull:'clone'},sort: true}"
animation="300"
:move="onMove"
class="drag-list"
@end="end1"
@start="start1"
>
<transition-group>
<div v-for="item in fieldDatas" :key="item.id" class="filter-db-row">
<i class="el-icon-s-data" />
<span> {{ item.name }}</span>
</div>
</transition-group>
</draggable>
</div>
</div>
</el-tab-pane>
<el-tab-pane :lazy="true" class="de-tab" label="按组件选择" name="assembly">按组件选择</el-tab-pane> <el-tab-pane :lazy="true" class="de-tab" label="按组件选择" name="assembly">按组件选择</el-tab-pane>
</el-tabs> </el-tabs>
</de-aside-container> </de-aside-container>
<!--画布区域-->
<de-main-container class="ms-main-container"> <de-main-container class="ms-main-container">
<div> <div>
<el-row> <el-row>
...@@ -19,7 +82,22 @@ ...@@ -19,7 +82,22 @@
<div class="field-content-text">字段</div> <div class="field-content-text">字段</div>
</div> </div>
<div class="field-content-right">请拖入左侧字段</div> <div class="field-content-right">
<el-row style="display:flex;height: 32px;">
<draggable
v-model="selectField"
group="dimension"
animation="300"
:move="onMove"
style="width:100%;height: 100%;margin:0 10px;border-radius: 4px;overflow-x: auto;display: flex;align-items: center;background-color: white;"
@end="end2"
>
<transition-group class="draggable-group">
<drag-item v-for="(item,index) in selectField" :key="item.id" :item="item" :index="index" @closeItem="closeItem" />
</transition-group>
</draggable>
</el-row>
</div>
</div> </div>
</div> </div>
</el-col> </el-col>
...@@ -42,7 +120,17 @@ ...@@ -42,7 +120,17 @@
</el-row> </el-row>
<el-row> <el-row>
<el-col :span="24"> <el-col :span="24">
<div class="filter-content" /> <div class="filter-content">
<el-card class="box-card">
<div style="margin-bottom: 10px;">
<span> {{ widget.label }}</span>
</div>
<div class="custom-component-class">
<slot />
</div>
</el-card>
</div>
</el-col> </el-col>
</el-row> </el-row>
</div> </div>
...@@ -54,24 +142,165 @@ ...@@ -54,24 +142,165 @@
import DeMainContainer from '@/components/dataease/DeMainContainer' import DeMainContainer from '@/components/dataease/DeMainContainer'
import DeContainer from '@/components/dataease/DeContainer' import DeContainer from '@/components/dataease/DeContainer'
import DeAsideContainer from '@/components/dataease/DeAsideContainer' import DeAsideContainer from '@/components/dataease/DeAsideContainer'
import draggable from 'vuedraggable'
import DragItem from '@/components/DragItem'
import { ApplicationContext } from '@/utils/ApplicationContext'
import { groupTree, loadTable, fieldList } from '@/api/dataset/dataset'
export default { export default {
name: 'FilterDialog', name: 'FilterDialog',
components: { components: {
DeMainContainer, DeMainContainer,
DeContainer, DeContainer,
DeAsideContainer DeAsideContainer,
draggable,
DragItem
},
props: {
widgetId: {
type: String,
default: null
}
}, },
data() { data() {
return { return {
activeName: 'dataset' activeName: 'dataset',
showDomType: 'tree',
dataSetBreads: [
{ label: '数据列表', link: false, type: 'root' }
],
data: [],
sceneDatas: [],
fieldDatas: [],
defaultProps: {
children: 'children',
label: 'label'
},
selectField: [],
widget: null
} }
}, },
created() { created() {
this.widget = ApplicationContext.getService(this.widgetId)
this.loadDataSetTree()
}, },
methods: { methods: {
handleNodeClick(data) {
if (data.type === 'scene') {
this.showSceneTable(data)
}
},
loadDataSetTree() {
groupTree({}).then(res => {
let datas = res.data
if (this.widget && this.widget.filterFieldMethod) {
datas = this.widget.filterFieldMethod(datas)
}
this.data = datas
})
},
renderNode(h, { node, data, store }) {
return (
<div class='custom-tree-node' >
{ data.type === 'scene' ? (
<el-button icon='el-icon-folder' type='text' size='mini' />
) : (
''
)}
<span class='label-span' >{node.label}</span>
</div>
)
},
showSceneTable(node) {
this.showDomType = 'db'
this.setTailLink(node)
this.addTail(node)
this.loadTable(node.id)
},
setTailLink(node) {
const tail = this.dataSetBreads[this.dataSetBreads.length - 1]
tail.type = node.type
tail.link = true
},
addTail(node) {
const tail = { link: false, label: node.label || node.name, type: node.type }
this.dataSetBreads.push(tail)
},
removeTail() {
this.dataSetBreads = this.dataSetBreads.slice(0, this.dataSetBreads.length - 1)
this.dataSetBreads[this.dataSetBreads.length - 1]['link'] = false
},
backToLink(bread) {
if (bread.type === 'db') {
this.showDomType = 'db'
} else {
this.showDomType = 'tree'
}
this.removeTail()
},
loadTable(sceneId) {
loadTable({ sceneId: sceneId, sort: 'type asc,create_time desc,name asc' }).then(res => {
this.sceneDatas = res.data
})
},
loadField(tableId) {
fieldList(tableId).then(res => {
this.fieldDatas = res.data
})
},
showFieldDatas(row) {
this.showDomType = 'field'
this.setTailLink(row)
this.addTail(row)
this.loadField(row.id)
},
test(row) {},
onMove(e, originalEvent) {
this.moveId = e.draggedContext.element.id
return true
},
start1() {
},
end1(e) {
this.refuseMove(e)
this.removeCheckedKey(e)
this.save()
},
save() {
},
end2(e) {
this.refuseMove(e)
},
refuseMove(e) {
const that = this
const xItems = this.fieldDatas.filter(function(m) {
return m.id === that.moveId
})
if (xItems && xItems.length > 1) {
this.fieldDatas.splice(e.newDraggableIndex, 1)
}
},
removeCheckedKey(e) {
const that = this
const xItems = this.selectField.filter(function(m) {
return m.id === that.moveId
})
if (xItems && xItems.length > 1) {
this.selectField.splice(e.newDraggableIndex, 1)
}
},
closeItem(tag) {
const index = tag.index
this.selectField.splice(index, 1)
}
} }
} }
</script> </script>
...@@ -86,9 +315,10 @@ export default { ...@@ -86,9 +315,10 @@ export default {
min-width: 230px !important; min-width: 230px !important;
max-width: 260px !important; max-width: 260px !important;
height: 100%; height: 100%;
min-height: 400px; min-height: 390px;
padding: 5px; padding: 5px;
border: none; border: none;
padding-bottom: 20px !important;
} }
.ms-main-container { .ms-main-container {
...@@ -137,7 +367,7 @@ export default { ...@@ -137,7 +367,7 @@ export default {
display: table-cell; display: table-cell;
vertical-align: middle; vertical-align: middle;
margin: 0px; margin: 0px;
padding: 0 0 0 10px; padding: 0 0 0 0;
height: 100%; height: 100%;
} }
} }
...@@ -161,9 +391,46 @@ export default { ...@@ -161,9 +391,46 @@ export default {
} }
.filter-content { .filter-content {
height: calc(50vh - 150px); height: calc(50vh - 130px);
top: 160px; top: 160px;
background: #99a9bf;
}
.filter-dialog-tabs {
border: 1px solid #E6E6E6;
}
.filter-common {
margin: 10px 10px;
}
.component-header {
margin: 20px 10px !important;
}
.link-text {
font-weight: 450 !important;
color: #409EFF;
}
.filter-db-row {
:hover {
cursor: pointer;
}
i {
color: #409EFF;
}
// background-color: #3685f2;
// color: #fff;
}
.draggable-group {
display: inline-block;
width: 100%;
height: calc(100% - 6px);
}
.box-card {
width: 100%;
height: 100%;
} }
</style> </style>
...@@ -2,25 +2,6 @@ ...@@ -2,25 +2,6 @@
<div class="filter-container" @dragstart="handleDragStart"> <div class="filter-container" @dragstart="handleDragStart">
<!-- <el-card class="filter-card-class">
<div slot="header">
<span>卡片名称</span>
</div>
<div style="position: relative;margin-left: 5px;" @dragstart="handleDragStart">
<div
v-for="(item, index) in componentList"
:key="index"
:data-id="item.id"
draggable
:data-index="index"
>
<span class="iconfont" :class="'icon-' + item.icon" />
<span>{{ item.label }}</span>
</div>
</div>
</el-card> -->
<div v-for="(item, key) in widgetSubjects" :key="key" class="widget-subject"> <div v-for="(item, key) in widgetSubjects" :key="key" class="widget-subject">
<div class="filter-header"> <div class="filter-header">
<div class="filter-header-text"> {{ key }} </div> <div class="filter-header-text"> {{ key }} </div>
......
<template>
<de-container>
<de-aside-container>
<el-tabs v-model="activeName" @tab-click="handleClick">
<el-tab-pane name="PanelList">
<span slot="label"><i class="el-icon-document" />列表</span>
<panel-list />
</el-tab-pane>
<el-tab-pane name="panels_star">
<span slot="label"><i class="el-icon-star-off" />收藏</span>
开发中...
</el-tab-pane>
<el-tab-pane name="panels_share" :lazy="true">
<span slot="label"><i class="el-icon-share" />分享</span>
<share-tree v-if="showShare" />
</el-tab-pane>
</el-tabs>
</de-aside-container>
<de-main-container>
<component :is="component" :param="param" />
</de-main-container>
</de-container>
</template>
<script>
import DeMainContainer from '@/components/dataease/DeMainContainer'
import DeContainer from '@/components/dataease/DeContainer'
import DeAsideContainer from '@/components/dataease/DeAsideContainer'
// import Group from './group/Group'
import PanelList from './list/PanelList'
import PanelViewShow from './list/PanelViewShow'
import ShareTree from './GrantAuth/shareTree'
export default {
name: 'Panel',
components: { DeMainContainer, DeContainer, DeAsideContainer, PanelList, PanelViewShow, ShareTree },
data() {
return {
component: PanelViewShow,
param: {},
activeName: 'PanelList',
showShare: false
}
},
methods: {
handleClick(tab, event) {
// 点击分析面板需要刷新分享内容
if (tab.name === 'panels_share') {
this.refreshShare()
}
},
// switchComponent(c) {
// console.log(c)
// this.param = c.param
// switch (c.name) {
// case 'PanelViewShow':
// this.component = PanelViewShow
// break
// }
// },
refreshShare() {
this.showShare = false
this.$nextTick(() => (this.showShare = true))
}
}
}
</script>
<style scoped>
.ms-aside-container {
height: calc(100vh - 56px);
padding: 15px;
min-width: 260px;
max-width: 460px;
}
.ms-main-container {
height: calc(100vh - 56px);
}
</style>
<template> <template>
<de-container v-loading="$store.getters.loadingMap[$store.getters.currentPath]"> <de-container v-loading="$store.getters.loadingMap[$store.getters.currentPath]" style="background-color: #f7f8fa">
<de-main-container> <de-main-container>
<component :is="component" :param="param" /> <component :is="component" :param="param" />
</de-main-container> </de-main-container>
...@@ -49,7 +49,7 @@ export default { ...@@ -49,7 +49,7 @@ export default {
<style scoped> <style scoped>
.ms-aside-container { .ms-aside-container {
height: calc(100vh - 56px); height: calc(100vh - 56px);
padding: 15px; padding: 0px;
min-width: 260px; min-width: 260px;
max-width: 460px; max-width: 460px;
} }
......
<template>
<el-row style="height: 100%;overflow-y: hidden;width: 100%;">
<el-row style="display: flex;height: 100%">
<el-col class="panel-design">
<!--TODO 仪表盘设计公共设置区域-->
<el-row class="panel-design-head">
<span style="float: left;line-height: 40px; color: gray">
<span>名称:{{ panelInfo.name || '测试仪表板' }}</span>
</span>
<span style="float: right;line-height: 40px;">
<el-tooltip content="预览">
<el-button class="el-icon-view" size="mini" circle />
</el-tooltip>
</span>
</el-row>
<!--TODO 仪表盘预览区域-->
<section>
<Preview />
</section>
</el-col>
</el-row>
</el-row>
</template>
<script>
import ChartEdit from '@/views/chart/view/ChartEdit'
export default {
name: 'ChartViewEdit',
components: { ChartEdit },
data() {
return {
}
},
computed: {
panelInfo() {
return this.$store.state.panel.panelInfo
}
},
mounted() {
},
methods: {
}
}
</script>
<style scoped>
.view-list {
height: 100%;
width: 20%;
min-width: 180px;
max-width: 220px;
border: 1px solid #E6E6E6;
border-left: 0 solid;
overflow-y: auto;
}
.view-list-thumbnails-outline {
height: 100%;
overflow-y: auto;
}
.view-list-thumbnails {
width: 100%;
padding: 0px 15px 15px 0px;
}
.panel-design {
height: 100%;
min-width: 500px;
border-top: 1px solid #E6E6E6;
}
.panel-design-head {
height: 40px;
}
.panel-design-show {
height: 100%;
width: 100%;
border-top: 1px solid #E6E6E6;
}
.padding-lr {
padding: 0 6px;
}
.itxst {
margin: 10px;
text-align: left;
}
.col {
width: 40%;
flex: 1;
padding: 10px;
border: solid 1px #eee;
border-radius: 5px;
float: left;
}
.col + .col {
margin-left: 10px;
}
.item {
padding: 2px 12px;
margin: 3px 3px 0 3px;
border: solid 1px #eee;
background-color: #f1f1f1;
text-align: left;
display: block;
}
.item + .item {
border-top: none;
margin-top: 3px;
}
.item:hover {
background-color: #fdfdfd;
cursor: pointer;
}
.item-axis {
padding: 2px 12px;
margin: 3px 3px 0 3px;
border: solid 1px #eee;
background-color: #f1f1f1;
text-align: left;
}
.item-axis:hover {
background-color: #fdfdfd;
cursor: pointer;
}
.el-form-item {
margin-bottom: 0;
}
.container {
width: 100%;
height: 600px;
border: 1px solid #000;
position: relative;
box-sizing: border-box;
}
span {
font-size: 12px;
}
</style>
...@@ -145,6 +145,7 @@ import GrantAuth from '../GrantAuth' ...@@ -145,6 +145,7 @@ import GrantAuth from '../GrantAuth'
import LinkGenerate from '@/views/link/generate' import LinkGenerate from '@/views/link/generate'
import { uuid } from 'vue-uuid' import { uuid } from 'vue-uuid'
import bus from '@/utils/bus' import bus from '@/utils/bus'
import eventBus from '@/components/canvas/utils/eventBus'
import { loadTable, getScene, addGroup, delGroup, addTable, delTable, groupTree, defaultTree, get } from '@/api/panel/panel' import { loadTable, getScene, addGroup, delGroup, addTable, delTable, groupTree, defaultTree, get } from '@/api/panel/panel'
export default { export default {
...@@ -417,8 +418,6 @@ export default { ...@@ -417,8 +418,6 @@ export default {
nodeClick(data, node) { nodeClick(data, node) {
if (data.nodeType === 'panel') { if (data.nodeType === 'panel') {
this.$store.dispatch('panel/setPanelInfo', data)
this.currGroup = data
// 加载视图数据 // 加载视图数据
this.$nextTick(() => { this.$nextTick(() => {
localStorage.setItem('canvasData', null) localStorage.setItem('canvasData', null)
...@@ -426,6 +425,9 @@ export default { ...@@ -426,6 +425,9 @@ export default {
get('panel/group/findOne/' + data.id).then(response => { get('panel/group/findOne/' + data.id).then(response => {
this.$store.commit('setComponentData', this.resetID(JSON.parse(response.data.panelData))) this.$store.commit('setComponentData', this.resetID(JSON.parse(response.data.panelData)))
this.$store.commit('setCanvasStyle', JSON.parse(response.data.panelStyle)) this.$store.commit('setCanvasStyle', JSON.parse(response.data.panelStyle))
this.$store.dispatch('panel/setPanelInfo', data)
this.currGroup = data
eventBus.$emit('componentDataChange', '')
}) })
}) })
} }
......
...@@ -57,12 +57,13 @@ export default { ...@@ -57,12 +57,13 @@ export default {
<style scoped> <style scoped>
.ms-aside-container { .ms-aside-container {
height: calc(100vh - 56px); height: calc(100vh - 56px);
padding: 15px; padding: 0px;
min-width: 260px; min-width: 260px;
max-width: 460px; max-width: 460px;
} }
.ms-main-container { .ms-main-container {
height: calc(100vh - 56px); height: calc(100vh - 56px);
padding: 0px;
} }
</style> </style>
<template> <template>
<el-row style="height: 100%;overflow-y: hidden;width: 100%;"> <el-row style="height: 100%;width: 100%;">
<el-row style="display: flex;height: 100%"> <el-col v-if="panelInfo.name.length>0" class="panel-design">
<el-col class="panel-design">
<!--TODO 仪表盘设计公共设置区域-->
<el-row class="panel-design-head"> <el-row class="panel-design-head">
<span style="float: left;line-height: 40px; color: gray"> <!--TODO 仪表盘头部区域-->
<span>名称:{{ panelInfo.name || '测试仪表板' }}</span> <span>{{ panelInfo.name || '测试仪表板' }}</span>
</span> <span style="float: right;">
<span style="float: right;line-height: 40px;">
<el-tooltip content="预览"> <el-tooltip content="预览">
<el-button class="el-icon-view" size="mini" circle @click="clickPreview" /> <el-button class="el-icon-view" size="mini" circle @click="clickPreview" />
</el-tooltip> </el-tooltip>
</span> </span>
</el-row> </el-row>
<!--TODO 仪表盘预览区域--> <!--TODO 仪表盘预览区域-->
<section> <el-row class="panel-design-preview">
<Preview /> <Preview />
</section> </el-row>
</el-col> </el-col>
<el-col v-if="panelInfo.name.length===0" style="height: 100%;">
<el-row style="height: 100%;" class="custom-position">
请从左侧选择仪表盘
</el-row> </el-row>
</el-col>
</el-row> </el-row>
</template> </template>
<script> <script>
...@@ -59,7 +59,7 @@ export default { ...@@ -59,7 +59,7 @@ export default {
} }
</script> </script>
<style scoped> <style>
.view-list { .view-list {
height: 100%; height: 100%;
width: 20%; width: 20%;
...@@ -81,18 +81,26 @@ export default { ...@@ -81,18 +81,26 @@ export default {
} }
.panel-design { .panel-design {
min-height: 400px;
height: 100%; height: 100%;
min-width: 500px; min-width: 500px;
overflow-y: auto;
border-top: 1px solid #E6E6E6; border-top: 1px solid #E6E6E6;
} }
.panel-design-head { .panel-design-head {
height: 40px; height: 40px;
background-color: white;
padding: 0 6px;
line-height: 40px;
} }
.panel-design-show { .panel-design-preview {
height: 100%;
width: 100%; width: 100%;
height: calc(100% - 40px);
overflow-x: hidden;
overflow-y: auto;
padding: 5px;
border-top: 1px solid #E6E6E6; border-top: 1px solid #E6E6E6;
} }
...@@ -165,4 +173,14 @@ export default { ...@@ -165,4 +173,14 @@ export default {
span { span {
font-size: 12px; font-size: 12px;
} }
.custom-position {
flex: 1;
display: flex;
align-items: center;
justify-content: space-between;
font-size: 14px;
flex-flow: row nowrap;
color: #9ea6b2;
}
</style> </style>
Markdown 格式
0%
您添加了 0 到此讨论。请谨慎行事。
请先完成此评论的编辑!
注册 或者 后发表评论