echarts vue 甘特图实现

Posted smallteeth

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了echarts vue 甘特图实现相关的知识,希望对你有一定的参考价值。

<{extends file="../main.tpl" }>

<{block name="html_header_title" append}>
<title>厂家机型故障分析</title>
<{/block}>

<{block name="html_header_css" append}>
<style>
.yn-main-wrapper__cloumn{
    flex:1;
    display:flex;
    flex-direction: column;
}
.yn-br__graph{
    flex:1;
}
.yn-br__graph:first-child {
    display:flex;
}

.yn-br__graph-left{
    flex:1;
    box-sizing:border-box;
    position:relative;
}
.yn-chart__title {
    position:absolute;
    top:10px;
    z-index:2;
    left:50%;
    transform:translate3D(-50%,0,0);
    display:flex;
}
.yn-chart__title-item {
    display:inline-block;
    margin-right:10px;
    font-size:12px;
    display:flex;
    align-items:center;
}
.yn-chart__title-item > span {
    display:inline-block;
    width:18px;
    height:18px;
    margin-right:10px;
}
.yn-br__graph--body{
    box-sizing:border-box;
}
.yn-line__graph--title,
.yn-br__graph--title {
    margin-bottom:22px;
}
/*排名的表格padding*/
.yn-br__graph--range{
    padding:0px 0px 0px 10px;
    box-sizing:border-box;
}
.wrap-check-select {
    width:240px;
}
.search-form__item{
    margin-right:20px;
    display:flex;
    justify-content:space-between;
    align-items:center;
    margin-bottom:10px;
    
}

.search-form {
    padding-left: 20px;
}
.check-select{
    height:30px;
}
</style>
<{/block}>

<{block name="body_content" }>
<div id="root">
<!--搜索区域 -->
    <div id="forTitle">
        <yn-title
            :title="‘故障趋势分析‘"
        ></yn-title>
    </div>
    <script>
        new Vue({el: ‘#forTitle‘})
    </script>
    <div class="search-form-wrapper" id=‘vue-head‘>
        <div class="search-form angle-border clearfix" >
            <div class="search-form__item">
                <span style="margin-right:10px;">时间范围</span>
                <input class="date-picker-input" type="text" id=‘range-date‘>
            </div>
            <div class="search-form__item">
                <label class=search-form__item__label>分析维度</label>
                <div class="search-form__item__control search-form__item__control--select">
                    <div class=‘el-select-wrapper‘>
                        <img src="/static/images/select-down-arrow.png" class="select-down-arrow" >
                        <el-select v-model="latituduesValue" placeholder="请选择">
                            <el-option
                                v-for="(group,index) in analysisLatitudues"
                                :key="index"
                                :label="group.label"
                                :value="group.value"
                                >
                            </el-option>
                        </el-select>
                    </div>
                </div>
            </div>
            <div class="search-form__item">
                <label class=search-form__item__label>风场</label>
                <div class="search-form__item__control search-form__item__control--select">
                    <div class=‘el-select-wrapper‘>
                        <img src="/static/images/select-down-arrow.png" class="select-down-arrow" >
                        <el-select v-model="farmValue" placeholder="请选择">
                            <el-option
                                v-for="group in options_farm"
                                :key="group.value"
                                :label="group.text"
                                :value="group.value"
                                >
                            </el-option>
                        </el-select>
                    </div>
                </div>
            </div>
            <div class=‘wrap-check-select search-form__item‘>
                <div style="width:60px">机组</div>
                <div id=‘group-model‘ class=‘search-form__item__control‘>
                    <check-select2 :datas="forSaveFantype" @get-select-value2=‘getSelectValue‘></check-select2>
                </div>
            </div>
            <div class="search-form__item" style=‘float:right;‘>
                <button @click="search" class=‘search-btn‘>查询</button>
            </div>
        </div>
    </div>
    <!--main -->
    <div class="yn-main-wrapper" id="app">
        <div class="yn-main-wrapper__cloumn">
            <div  @click.stop="bodyClick"  class="yn-br__graph">
                <div v-loading="loading" class="yn-br__graph-left">
                    <div class="yn-chart__title">
                        <div @click.stop="barClick(item)" style="cursor:pointer" class="yn-chart__title-item" v-for="(item,index) in status" :key="index">
                            <span  :style="backgroundComputed(item)"></span>
                            {{item}}
                        </div>
                    </div>
                    <yn-chart-wrapper style="padding:32px 10px 0px 10px;">
                      <template slot="chartInfo">
                          <!--柱状图为例 -->
                          <div ref="scatter" class="yn__graph--body yn-br__graph--body yn-scroll">
                              
                          </div>
                      </template>
                  	</yn-chart-wrapper>
                </div>
            </div>
        </div>
    </div>
</div>

<{/block}>

<{block name="body_main_js" append}>
<script src="/static/js/component/dateType.js"></script>
<script src="/static/js/component/chart-wrapper.js"></script>
<script src="/static/js/component/select2.js"></script>
<script>
    var INDEX_NAME = ‘能量可利用率(%)‘;
    var allData = {};
    var STARTDATA = ‘<{$startDate}>‘;
    var ENDDATA = ‘<{$endDateD}>‘;
    //头部
    
    var vm = new Vue({
        el: ‘#vue-head‘,
        data: function(){
            return {
                options_farm:[],
                //风场
                farmValue:‘‘,
                //机组
                farmModelValue:‘‘,
                //风场型号
                farmModel:[],
                //风场详细型号
                farmFantype:[],
                // 风场选中机型的list
                farmModelList:{},
                //analysisLatitudues分析维度
                analysisLatitudues:[{label:‘系统‘,value:‘system‘},{label:‘检修‘,value:‘repair‘}],
                //维度的value值
                latituduesValue:"",
                backValue:‘‘,
                //选中机型的value
                groupValue:‘‘,
                province : ‘云南‘
            }
        },
        methods: {
            getSelectValue: function (data) {
                this.groupValue = data.join(‘,‘);
            },
            search: function () {
                var rangeData = $(‘#range-date‘).val();
                var arr = _.split(rangeData, ‘ - ‘, 2);
                var startData = arr[0];
                var endDate = arr[1];
                if(!this.province || !startData || !endDate || !this.farmValue || !this.groupValue || !this.latituduesValue){
                    this.$message(
                        {
                            showClose: true,
                            message: ‘请填写需要筛选的数据!‘,
                            type: ‘warning‘,
                            customClass:‘messageClass‘,
                            iconClass:‘icon-yn-warn‘
                        }
                    )
                    return;
                }
                allData.ajaxObj={
                    province:this.province,
                    startDate: startData,
                    endDate: endDate,
                    farm:this.farmValue,
                    fantype:this.groupValue,
                    //新的属性
                    dimension:this.latituduesValue
                }
                //调用下面vue的初始化表的方法
                vmRoot.shearchEcharts(allData.ajaxObj);
            }
        },
        computed: {
            forSaveFantype : function(){
                var that = this;
                that.farmModel=[];
                that.farmFantype=[];
                that.farmModelList =all_provinceData[this.farmValue];
                _.forIn(that.farmModelList, function(value, key) {
                    that.farmModel.push({key:key,value:key,checked:true});
                    that.farmFantype.push(key);
                });
                that.backValue = that.farmFantype.join(‘,‘);
                that.groupValue = that.backValue;
                return that.farmModel;
            },
        },
        mounted: function () {
            var str = localStorage.getItem(‘basicInfo‘);
            var baseInfoObj = JSON.parse(str); 
            this.options_farm = all_provinceSelect;
            this.farmValue = this.options_farm[0].value;
            this.farmModelList = all_provinceSelect[this.farmValue];
            this.latituduesValue = ‘system‘;
            //初始化时间插件
            laydate.render({
                elem: ‘#range-date‘,
                type: ‘month‘,
                range: true,
                min:baseInfoObj.startDate,
                max:baseInfoObj.endDateD
            });
            var str = STARTDATA + ‘ - ‘ + ENDDATA;
            $(‘#range-date‘).val(str);
        }
    })
    function changeAlgorithm(algorithm) {
        vm.search();
    }
</script>
<script>
    var FANTYPE = ‘<{$basicInfoJson}>‘;
    var FARMNAMES = JSON.parse(FANTYPE);
    var vmRoot = new Vue({
        el: ‘#app‘,
        data:function(){
            return {
                option: {},
                //时序图图标
                myChart:null,
                types: [],
                categories: [],
                status : [],
                startTime:‘‘,
                endTime:‘‘,
                //头部传来的时间
                vmStartTime : ‘‘,
                vmEndTime : ‘‘,
                dataCount:10,
                data:[],
                //对应的名称
                farmnames : {},
                //为不同的状态分配不同的颜色
                colorList : [
                    ‘#ffee58‘,
                    ‘#2196f3‘,
                    ‘#1de9b6‘,
                    ‘#f9a825‘,
                    ‘#e040fb‘,
                    ‘#d32f2f‘,
                    ‘#43a047‘,
                    ‘#26c6da‘,
                    ‘#3d5afe‘,
                    ‘#9ccc65‘,
                    ‘#ff5722‘,
                    ‘#9c27b0‘,
                    ‘#ccff90‘,
                    ‘#7b1fa2‘,
                    ‘#0288d1‘,
                ],
                peerColor: {},
                //控制请求接口显示不显示
                loading : false,
                //请求锁
                searchLock : false,
                //存入数据
                totalData : [],
            }
        },
        methods : {
            shearchEcharts:function (data){
                if(this.searchLock){
                    this.$message(
                        {
                            showClose: true,
                            message: ‘请等数据加载完成!‘,
                            type: ‘warning‘,
                            customClass:‘messageClass‘,
                            iconClass:‘icon-yn-warn‘
                        }
                    )
                    return;
                }
                this.searchLock= true;
                //让设备与显示的名称对应的方法
                this.farmnames = FARMNAMES[vm.province][data.farm];
                var obj = {};
                var arr = [];
                var addDate = [];
                var forSaveFantype = [];
                if(data.fantype.indexOf(‘,‘)>-1){
                    arr = data.fantype.split(‘,‘);
                }else{
                    arr.push(data.fantype)
                }
                arr.forEach(function(item) {
                    forSaveFantype.push({name:‘fantype‘,value : item});
                })
                //为了获得当全部选择相同时间的时候得出当前月的最后一天
                addDate=data.endDate.split(‘-‘);
                this.vmStartTime=data.startDate+‘-01‘;
                this.vmEndTime=data.endDate+"-"+this.getLastDay(addDate[0],addDate[1]);
                obj = {
                    startDate: data.startDate,
                    endDate: data.endDate,
                    province: data.province,
                    dimension: data.dimension,
                    farm: data.farm,
                    forSaveFantype: forSaveFantype
                }
                this.getSeqData(obj);
            },
            //请求完成调用方法为echart传递参数
            initParams: function(data,currentChose){
                var obj = {};
                _.forIn(this.farmnames[vm.farmValue], function(value, key) {
                    _.assign(obj,value);
                });
                var that = this;
                that.data=[];
                that.startTime = new Date(that.vmStartTime);
                that.startTime = that.startTime.getTime()/1000;
                that.endTime = new Date(that.vmEndTime);
                that.endTime = that.endTime.getTime()/1000;
                if(data){
                    for (var i = 0; i < data.length; i++) {
                        var j = 0;
                        that.categories.forEach(function(item,index){
                            if(item == data[i].taskName){
                                j = index;
                            }
                        })
                        var opacity = 1;
                        if(!currentChose){
                            opacity = 1;
                        }else{
                            if(currentChose && currentChose == data[i].status){
                                opacity = 1;
                            }else{
                                opacity = 0.1;
                            }
                        }
                        that.data.push({
                            name: data[i].taskName,
                            value: [
                                j,
                                data[i].startDate,
                                data[i].endDate,
                                data[i].endDate-data[i].startDate
                            ],
                            itemStyle: {
                                normal: {
                                    color: that.peerColor[data[i].status],
                                    opacity : opacity
                                },
                                
                            }
                        });
                    }
                }
                
                //控制图标中元素的大小样式
                this.paramOption();
                if(this.myChart){
                    this.myChart.dispose();
                }
                this.myChart = echarts.init(this.$refs.scatter);
                this.myChart.setOption(this.option);
                that.searchLock= false;
            },
            paramOption: function(data){
                var that = this;
                this.option = {
                    tooltip: {
                        trigger : ‘item‘,
                        show:true,
                        showDelay: 0,
                        hideDelay: 0,
                        transitionDuration:0, 
                        backgroundColor : ‘#061934‘,
                        borderColor : ‘#00f6ff‘,
                        borderRadius : 8,
                        borderWidth: 2,
                        padding: 10,    // [5, 10, 15, 20]
                        formatter: function (params) {
                            return ‘开始时间 : ‘ + that.timestampToTime(params.value[1],true) + ‘<br/>‘ + ‘结束时间 : ‘ + that.timestampToTime(params.value[2],true) + ‘<br/>‘ +‘风机名称 : ‘ + params.name ;
                        }
                    },
                    grid:{
                        x:70,
                        y:5,
                        x2:40,
                        y2:70,
                        borderWidth:1
                    },
                    xAxis: {
                        min : that.startTime,
                        max : that.endTime,
                        scale: true,
                        axisLabel: {
                            formatter: function (val) {
                                return that.timestampToTime(val);
                            },
                            textStyle: {
                                color: ‘#fff‘
                            },
                            // rotate:-20,
                        },
                        axisLine: {
                            lineStyle: {
                                type: ‘solid‘,
                                color: ‘#6286a8‘,//左边线的颜色
                                width:‘1‘//坐标线的宽度
                            }
                        },
                        //去掉刻度线
                        axisTick: {
                            show: false
                        },
                        //x轴上面的线
                        splitLine:{ 
                            show:false
                        },
                    },
                    yAxis: {
                        data: that.categories,
                        axisLabel: {
                            textStyle: {
                                color: ‘#fff‘
                            },
                            // rotate:-20,
                        },
                        axisLine: {
                            lineStyle: {
                                type: ‘solid‘,
                                color: ‘#6286a8‘,//左边线的颜色
                                width:‘1‘//坐标线的宽度
                            },
                            textStyle:{
                                fontSize:15,
                                color:‘#fff‘
                            }
                        },
                        
                        axisTick: {
                            show: false
                        },
                        splitLine:{ 
                            show:false
                        },
                    },
                    series: [{
                        type: ‘custom‘,
                        renderItem: that.renderItem,
                        itemStyle: {
                            normal: {
                                opacity: 0.8
                            }
                        },
                        encode: {
                            x: [1, 2],
                            y: 0
                        },
                        data: that.data
                    }]
                    
                };
            },
            //修改echarts自定义画图规则
            renderItem: function(params, api) {
                var categoryIndex = api.value(0);
                var start = api.coord([api.value(1), categoryIndex]);
                var end = api.coord([api.value(2), categoryIndex]);
                var height = api.size([0, 1])[1] * 0.6;           
                return {
                    type: ‘rect‘,
                    shape: echarts.graphic.clipRectByRect({
                        x: start[0],
                        y: start[1] - height / 2,
                        width: end[0] - start[0],
                        height: height
                    }, {
                        x: params.coordSys.x,
                        y: params.coordSys.y,
                        width: params.coordSys.width,
                        height: params.coordSys.height
                    }),
                    style: api.style()
                };
            },
            //获取序列图数据
            getSeqData: function(obj) {
                var that = this;
                that.loading = true;
                $.ajax({
                    url: "/apps/fault/getSeqData.php",         
                    dataType: "json",   
                    async: true,        
                    type: "post",
                    data: obj, 
                    success: function(data) { //此处data为返回值
                        if(data.error_code){
                            that.$message(
                                {
                                    showClose: true,
                                    message: ‘链接错误请求失败!‘,
                                    type: ‘warning‘,
                                    customClass:‘messageClass‘,
                                    iconClass:‘icon-yn-warn‘
                                }
                            )
                            if(that.myChart){
                                that.myChart.dispose();
                            }
                            that.myChart=null;
                            that.loading = false;
                        }
                        var arr = [];
                        var status = [];
                        var objName = {};
                        if(data){
                            _.forIn(that.farmnames, function(value, key) {
                                _.assign(objName,value);
                            });
                            data.forEach(function(item){
                                item.taskName = objName[item.taskName];
                                arr.push(item.taskName);
                                status.push(item.status);
                                item.startDate = new Date(item.startDate).getTime()/1000;
                                item.endDate = new Date(item.endDate).getTime()/1000;
                            })
                            that.status = _.uniq(status);
                            that.status.forEach(function(item,index){
                                that.peerColor[item] = that.colorList[index];
                            });
                            that.categories = _.uniq(arr);
                            that.totalData = data;
                            that.initParams(data);
                            that.loading = false;
                            
                        }
                    },
                    error: function() {
                        that.searchLock= false;
                        that.loading = false;
                        console.log(‘接口错误‘);
                    }
                })
            },
            timestampToTime : function(timestamp ,flag) {
                var date = new Date(timestamp * 1000);//时间戳为10位需*1000,时间戳为13位的话不需乘1000
                var Y = date.getFullYear() + ‘-‘;
                var M = (date.getMonth()+1 < 10 ? ‘0‘+(date.getMonth()+1) : date.getMonth()+1) + ‘-‘;
                var D = date.getDate() <10 ? ‘0‘+date.getDate() : date.getDate() + ‘ ‘;
                var h = date.getHours() + ‘:‘;
                var m = date.getMinutes() + ‘:‘;
                var s = date.getSeconds();
                if(flag){
                    return Y+M+D+" "+h+m+s;
                }else{
                    return Y+M+D;
                }
            },
            backgroundComputed : function(data) {
                return {backgroundColor : this.peerColor[data]};
            },
            getLastDay : function(year,month)   {   
                var new_year = year;  //取当前的年份   
                var new_month = month++;//取下一个月的第一天,方便计算(最后一天不固定)   
                if(month>12)      //如果当前大于12月,则年份转到下一年   
                {   
                new_month -=12;    //月份减   
                new_year++;      //年份增   
                }   
                var new_date = new Date(new_year,new_month,1);        //取当年当月中的第一天   
                return (new Date(new_date.getTime()-1000*60*60*24)).getDate();//获取当月最后一天日期   
            },
            barClick : function(item) {
                this.initParams(this.totalData,item);
            },
            bodyClick :function(item) {
                this.initParams(this.totalData);
            },
        },
        created: function(){
            
        },
        mounted: function(){
            var that = this;
            this.farmnames = FARMNAMES[vm.province][vm.farmValue];
            this.initParams();
            //一开始默认值请求
            setTimeout(function(){
                vm.search();
            },10)
            window.addEventListener(‘resize‘, function () {
                if(that.myChart){
                    that.myChart.resize();
                }
            });
        }
    })
</script>
<{/block}>

  

以上是关于echarts vue 甘特图实现的主要内容,如果未能解决你的问题,请参考以下文章

vue框架下实现甘特图(dhtmlxGantt)

vue+echarts画甘特图

vue+echarts画甘特图

vue项目使用Echarts制作项目工期甘特图

关于ECharts甘特图的实现

基于 ECharts 封装甘特图并实现自动滚屏