<!DOCTYPE html>
<!--
Licensed to the Apache Software Foundation (ASF) under one
or more contributor license agreements.  See the NOTICE file
distributed with this work for additional information
regarding copyright ownership.  The ASF licenses this file
to you under the Apache License, Version 2.0 (the
"License"); you may not use this file except in compliance
with the License.  You may obtain a copy of the License at

   http://www.apache.org/licenses/LICENSE-2.0

Unless required by applicable law or agreed to in writing,
software distributed under the License is distributed on an
"AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
KIND, either express or implied.  See the License for the
specific language governing permissions and limitations
under the License.
-->


<html>

<head>
    <meta charset="utf-8">
    <meta name="viewport" content="width=device-width, initial-scale=1" />
    <script src="lib/esl.js"></script>
    <script src="lib/config.js"></script>
    <script src="lib/jquery.min.js"></script>
    <script src="lib/facePrint.js"></script>
    <script src="lib/testHelper.js"></script>
    <!-- <script src="ut/lib/canteen.js"></script> -->
    <link rel="stylesheet" href="lib/reset.css" />
</head>

<body>
    <style>
    </style>



    <div id="main0"></div>

    <div id="main1"></div>

    <div id="main2"></div>

    <div id="main3"></div>









    <script>
        require(['echarts'], function (echarts) {
            var option = {
                tooltip: {
                    formatter: "{a} <br/>{b} : {c}%"
                },
                series: [
                    {
                        name: 'Pressure',
                        type: 'gauge',
                        detail: {formatter: '{value}%', valueAnimation: true},
                        data: [{value: 50, name: 'score'}]
                    }
                ]
            };

            var chart = testHelper.create(echarts, 'main0', {
                title: [
                    'Simple gauge',
                    'Value should be 88 after clicking button'
                ],
                option: option,
                buttons: [{
                    text: 'Change data', onclick: function () {
                        option.series[0].data[0].value = 88;
                        chart.setOption(option, true);
                    }
                }]
            });
        });
    </script>






    <script>
        require(['echarts'], function (echarts) {
            var option = {
                tooltip: {
                    formatter: "{a} <br/>{b} : {c}%"
                },
                dataset: {
                    source: [[10], [30]]
                },
                series: [
                    {
                        name: 'Pressure',
                        type: 'gauge',
                        detail: {formatter: '{value}%'}
                    }
                ]
            };

            var chart = testHelper.create(echarts, 'main1', {
                title: [
                    'Gauge with dataset',
                    'Value should be 44 and 88 after clicking button'
                ],
                option: option,
                buttons: [{
                    text: 'Change data', onclick: function () {
                        chart.setOption({
                            dataset: {
                                source: [[44], [88]]
                            }
                        });
                    }
                }]
            });
        });
    </script>




    <script>
        require(['echarts'], function (echarts) {
            var option = {
                tooltip: {
                    formatter: "{a} <br/>{b} : {c}%"
                },
                series: [
                    {
                        name: 'Pressure',
                        type: 'gauge',
                        data: [{}]
                    }
                ]
            };

            var chart = testHelper.create(echarts, 'main2', {
                title: [
                    'Gauge with no data, should display NaN'
                ],
                option: option
            });
        });
    </script>

    <script>
        require(['echarts'], function (echarts) {
            var option = {
                tooltip: {
                    formatter: '{a} <br/>{b} : {c}%'
                },
                toolbox: {
                    feature: {
                        restore: {},
                        saveAsImage: {}
                    }
                },
                series: [{
                    name: '学生成绩',
                    type: 'gauge',
                    startAngle: 180,
                    endAngle: 0,
                    min: 0,
                    max: 1,
                    splitNumber: 8,
                    axisLine: {
                        lineStyle: {
                            width: 5,
                            color: [
                                [0.25, '#FF6E76'],
                                [0.5, '#FDDD60'],
                                [0.75, '#58D9F9'],
                                [1, '#7CFFB2'],
                            ]
                        }
                    },
                    pointer: {
                        length: '80%',
                        itemStyle: {
                            color: 'auto'
                        }
                    },
                    axisTick: {
                        length: 15,
                        lineStyle: {
                            color: 'auto'
                        }
                    },
                    splitLine: {
                        length: 20,
                        lineStyle: {
                            color: 'auto',
                            width: 5
                        }
                    },
                    axisLabel: {
                        color: '#464646',
                        fontSize: 20,
                        distance: -60,
                        formatter: function(value) {
                            if (value === 0.875) {
                                return '优'
                            } else if (value === 0.625) {
                                return '中'
                            } else if (value === 0.375) {
                                return '良'
                            } else if (value === 0.125) {
                                return '差'
                            }
                        }
                    },
                    title: {
                        offsetCenter: [0, '-50%'],
                        fontSize: 40
                    },
                    detail: {
                        valueAnimation: true,
                        fontSize: 50,
                        offsetCenter: [0, '-30%'],
                        formatter: function(value) {
                            return Math.round(value * 100) + '%';
                        },
                        color: 'auto'
                    },
                    data: [{
                        value: 0.75,
                        name: '成绩评定'
                    }]
                }]
            };

            var chart = testHelper.create(echarts, 'main3', {
                title: [
                    'Value animation should be enabled'
                ],
                option: option
            });
        });
    </script>
</body>

</html>