<!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>









    <script>
        require(['echarts'/*, 'map/js/china' */], function (echarts) {
            var option;
            // $.getJSON('./data/nutrients.json', function (data) {});

            option = {
                title: {
                    text: '浏览器占比变化',
                    subtext: '纯属虚构',
                    top: 10,
                    left: 10
                },
                tooltip: {
                    trigger: 'item',
                    backgroundColor: 'rgba(0,0,250,0.2)'
                },
                legend: {
                    type: 'scroll',
                    bottom: 10,
                    data: (function () {
                        var list = [];
                        for (var i = 1; i <= 28; i++) {
                            list.push(i + 2000 + '');
                        }
                        return list;
                    })()
                },
                visualMap: {
                    top: 'middle',
                    right: 10,
                    color: ['red', 'yellow'],
                    calculable: true
                },
                radar: {
                    indicator: [
                        { text: 'IE8-', max: 400 },
                        { text: 'IE9+', max: 400 },
                        { text: 'Safari', max: 400 },
                        { text: 'Firefox', max: 400 },
                        { text: 'Chrome', max: 400 }
                    ]
                },
                series: (function () {
                    var series = [];
                    for (var i = 1; i <= 28; i++) {
                        series.push({
                            name: '浏览器（数据纯属虚构）',
                            type: 'radar',
                            symbol: 'none',
                            lineStyle: {
                                width: 1
                            },
                            emphasis: {
                                areaStyle: {
                                    color: 'rgba(0,250,0,0.3)'
                                }
                            },
                            data: [
                                {
                                    value: [
                                        (40 - i) * 10,
                                        (38 - i) * 4 + 60,
                                        i * 5 + 10,
                                        i * 9,
                                        i * i / 2
                                    ],
                                    name: i + 2000 + ''
                                }
                            ]
                        });
                    }
                    return series;
                })()
            };

            var chart = testHelper.create(echarts, 'main0', {
                title: [
                    'Test Case Description of main0',
                    '(Muliple lines and **emphasis** are supported in description)'
                ],
                option: option
                // height: 300,
                // buttons: [{text: 'btn-txt', onclick: function () {}}],
                // recordCanvas: true,
            });
            
            setTimeout(function () {
                option.legend.type = 'plain';
                chart.setOption(option);
            }, 3000);

            var option1 = {
                legend: {
                    data: [
                        '邮件营销', '联盟广告', '视频广告', '直接访问', '搜索引擎',
                        '邮件营销1', '联盟广告1', '视频广告1', '直接访问1', '搜索引擎1'
                    ],
                    type: 'scroll'
                },
                xAxis: [{
                    type: 'category',
                    data: ['周一', '周二', '周三', '周四', '周五', '周六', '周日']
                }],
                yAxis: [{
                    type: 'value'
                }],
                series: [
                    {
                        name: '邮件营销',
                        type: 'line',
                        data: [null, null, null, null, null, null, null]
                    },
                    {
                        name: '联盟广告',
                        type: 'line',
                        data: [null, null, null, null, null, null, null]
                    },
                    {
                        name: '视频广告',
                        type: 'line',
                        data: [null, null, null, null, null, null, null]
                    },
                    {
                        name: '直接访问',
                        type: 'line',
                        data: [null, null, null, null, null, null, null]
                    },
                    {
                        name: '搜索引擎',
                        type: 'line',
                        data: [null, null, null, null, null, null, null]
                    },
                    {
                        name: '邮件营销1',
                        type: 'line',
                        data: [null, null, null, null, null, null, null]
                    },
                    {
                        name: '联盟广告1',
                        type: 'line',
                        data: [null, null, null, null, null, null, null]
                    },
                    {
                        name: '视频广告1',
                        type: 'line',
                        data: [null, null, null, null, null, null, null]
                    },
                    {
                        name: '直接访问1',
                        type: 'line',
                        data: [null, null, null, null, null, null, null]
                    },
                    {
                        name: '搜索引擎1',
                        type: 'line',
                        data: [null, null, null, null, null, null, null]
                    }
                ]
                
            };
            var chart1 = testHelper.create(echarts, 'main1', {
                title: [
                    'Test Case Description of main1',
                    'Legend scroll animation'
                ],
                option: option1,
                width: 300,
                // buttons: [{text: 'btn-txt', onclick: function () {}}],
                // recordCanvas: true,
            });
            chart1.setOption(option1);
        });
    </script>


</body>

</html>