<!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="https://d3js.org/d3.v4.min.js"></script>
        <script src="lib/simpleRequire.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>
            window.ANIMATION_DURATION_UPDATE = 1000;
        </script>


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

            var stratify = d3.stratify()
                .parentId(function(d) {
                    return d.id.substring(0, d.id.lastIndexOf("."));
                });

            function toPlainTree(root) {
                return {
                    children: root.children && root.children.map(child => toPlainTree(child)),
                    value: root.value,
                    name: root.id.split('.').pop(),
                    id: root.id
                }
            }

            d3.csv("data/flare.csv", function(error, rawData) {
                if (error) throw error;

                var root = stratify(rawData)
                    .sum(function(d) {
                        return d.value;
                    })
                    .sort(function(a, b) {
                        return b.value - a.value;
                    });
                var maxDepth = 0;

                var seriesDataLinear = root.descendants().map(function (node) {
                    maxDepth = Math.max(maxDepth, node.depth);
                    return [
                        node.value,
                        node.depth,
                        node.id
                    ];
                });

                function renderItem(params, api) {
                    var context = params.context;
                    if (!context.layout) {
                        d3.pack()
                            .size([api.getWidth() - 2, api.getHeight() - 2])
                            .padding(3)(root);

                        context.nodes = {};
                        root.descendants().forEach(function (node, index) {
                            context.nodes[node.id] = {
                                index: index,
                                node: node
                            }
                        });
                    }

                    var nodePath = api.value(2);
                    var node = context.nodes[nodePath].node;
                    var isLeaf = !node.children || !node.children.length;

                    var textFont = api.font({
                        fontSize: 12,
                        fontFamily: 'Arial'
                    });

                    var focus = new Uint32Array(node.descendants().map(function (node) {
                        return context.nodes[node.id].index;
                    }));

                    var nodeName = isLeaf ? nodePath.slice(nodePath.lastIndexOf('.') + 1).split(/(?=[A-Z][^A-Z])/g).join('\n') : '';

                    var z2 = api.value(1) * 2;

                    return {
                        type: 'circle',
                        focus: focus,
                        shape: {
                            cx: node.x,
                            cy: node.y,
                            r: node.r
                        },
                        z2: z2,
                        textContent: {
                            type: 'text',
                            style: {
                                text: nodeName,
                                width: node.r * 1.3,
                                overflow: 'truncate',
                                fontSize: node.r / 3
                            },
                            emphasis: {
                                style: {
                                    overflow: null,
                                    fontSize: Math.max(node.r / 3, 12)
                                }
                            }
                        },
                        textConfig: {
                            position: 'inside'
                        },
                        style: {
                            fill: api.visual('color'),
                            text: nodeName,
                            font: textFont,
                        },
                        emphasis: {
                            style: {
                                font: textFont,
                                shadowBlur: 20,
                                shadowOffsetX: 3,
                                shadowOffsetY: 5,
                                shadowColor: 'rgba(0,0,0,0.3)'
                            }
                        }
                    };
                }

                var circlePackingOption = {
                    tooltip: {},
                    visualMap: {
                        show: false,
                        min: 0,
                        max: maxDepth,
                        dimension: 1,
                        inRange: {
                            color: ['#006edd', '#e0ffff']
                        }
                    },
                    series: {
                        type: 'custom',
                        id: 'main',
                        renderItem: renderItem,
                        coordinateSystem: null,
                        animationDurationUpdate: ANIMATION_DURATION_UPDATE,
                        encode: {
                            tooltip: 0,
                            itemName: 2
                        },
                        universalTransition: {
                            enabled: true
                        },
                        data: seriesDataLinear
                    }
                };

                var treemapOption = {
                    series: {
                        type: 'treemap',
                        id: 'main',
                        data: toPlainTree(root).children,
                        animationDurationUpdate: ANIMATION_DURATION_UPDATE,
                        roam: false,
                        label: {
                            fontSize: 10
                        },
                        breadcrumb: {
                            show: false
                        },
                        universalTransition: {
                            enabled: true
                        },
                        itemStyle: {
                            color: '#ddd',
                            borderWidth: 2
                        }
                    }
                }

                var sunburstOption = {
                    series: {
                        type: 'sunburst',
                        id: 'main',
                        data: toPlainTree(root).children,
                        animationDurationUpdate: ANIMATION_DURATION_UPDATE,
                        roam: false,
                        radius: ['20%', '90%'],
                        label: {
                            show: false
                        },
                        breadcrumb: {
                            show: false
                        },
                        universalTransition: {
                            enabled: true
                        },
                        itemStyle: {
                            borderWidth: 1
                        }
                    }
                }

                var chart = testHelper.create(echarts, 'main0', {
                    title: [
                        'Custom Series: Universal Transition betwee treemap and circle packing '
                    ],
                    recordVideo: true,
                    option: treemapOption,
                    height: 500,
                    buttons: [{
                        text: 'Custom Circle Packing',
                        onclick: function () {
                            chart.setOption(circlePackingOption, true);
                        }
                    }, {
                        text: 'Treemap',
                        onclick: function () {
                            chart.setOption(treemapOption, true);
                        }
                    }, {
                        text: 'Sunburst',
                        onclick: function () {
                            chart.setOption(sunburstOption, true);
                        }
                    }],
                });
            });
        });
        </script>


        <script>
            require([
                'echarts'
            ], function (echarts) {
                var pieData = [
                    { value: 800, name: 'A' },
                    { value: 635, name: 'B' },
                    { value: 580, name: 'C' },
                    { value: 484, name: 'D' },
                    { value: 300, name: 'E' },
                    { value: 200, name: 'F' }
                ];
                const defaultPalette = [
                    // '#51689b', '#ce5c5c', '#fbc357', '#8fbf8f', '#659d84', '#fb8e6a', '#c77288', '#786090', '#91c4c5', '#6890ba'
                    '#5470c6',
                    '#91cc75',
                    '#fac858',
                    '#ee6666',
                    '#73c0de',
                    '#3ba272',
                    '#fc8452',
                    '#9a60b4',
                    '#ea7ccc'
                ];

                const radius = ['30%', '80%'];

                var pieOption = {
                    series: [{
                        type: 'pie',
                        center: ['50%', '50%'],
                        radius: radius,
                        label: {
                            show: false
                        },
                        itemStyle: {
                            borderRadius: 0
                        },
                        universalTransition: {
                            enabled: true,
                            seriesKey: 'first'
                        },
                        animationDurationUpdate: 1000,
                        data: pieData
                    }]
                };


                var parliamentOption = (function () {
                    const sum = pieData.reduce((sum, cur) => {
                        return sum + cur.value;
                    }, 0);

                    const angles = [];
                    const startAngle = -Math.PI / 2;
                    let curAngle = startAngle;
                    pieData.forEach(item => {
                        angles.push(curAngle);
                        curAngle += (item.value / sum) * Math.PI * 2;
                    });
                    angles.push(startAngle + Math.PI * 2);
                    function parliamentLayout(startAngle, endAngle, totalAngle, r0, r1, size) {
                        const rowsCount = Math.ceil((r1 - r0) / size);
                        const points = [];

                        let r = r0;
                        for (let i = 0; i < rowsCount; i++) {
                            // Recalculate size
                            const totalRingSeatsNumber = Math.round((totalAngle * r) / size);
                            const newSize = (totalAngle * r) / totalRingSeatsNumber;
                            for (
                                let k = Math.floor((startAngle * r) / newSize) * newSize;
                                k < Math.floor((endAngle * r) / newSize) * newSize - 1e-6;
                                k += newSize
                            ) {
                                const angle = k / r;
                                const x = Math.cos(angle) * r;
                                const y = Math.sin(angle) * r;
                                points.push([x, y]);
                            }

                            r += size;
                        }

                        return points;
                    }
                    return {
                        series: {
                            type: 'custom',
                            data: pieData,
                            coordinateSystem: undefined,
                            universalTransition: {
                                enabled: true,
                                seriesKey: 'first'
                            },
                            animationDurationUpdate: 1000,
                            renderItem(params, api) {
                                const idx = params.dataIndex;
                                const viewSize = Math.min(api.getWidth(), api.getHeight());
                                const r0 = ((parseFloat(radius[0]) / 100) * viewSize) / 2;
                                const r1 = ((parseFloat(radius[1]) / 100) * viewSize) / 2;
                                const cx = api.getWidth() * 0.5;
                                const cy = api.getHeight() * 0.5;
                                const size = 15;

                                const points = parliamentLayout(
                                    angles[idx],
                                    angles[idx + 1],
                                    Math.PI * 2,
                                    r0,
                                    r1,
                                    size + 3
                                );

                                return {
                                    type: 'group',
                                    children: points.map(pt => {
                                        return {
                                            type: 'circle',
                                            autoBatch: true,
                                            shape: {
                                                cx: cx + pt[0],
                                                cy: cy + pt[1],
                                                r: size / 2
                                            },
                                            style: {
                                                fill: defaultPalette[idx % defaultPalette.length]
                                            }
                                        };
                                    })
                                };
                            }
                        }
                    };
                })();

                var chart = testHelper.create(echarts, 'main1', {
                    title: [
                        'Parliament and pie chart.'
                    ],
                    recordVideo: true,
                    option: pieOption,
                    height: 500,
                    buttons: [{
                        text: 'Parliament chart',
                        onclick: function () {
                            chart.setOption(parliamentOption, true);
                        }
                    }, {
                        text: 'Pie chart',
                        onclick: function () {
                            chart.setOption(pieOption, true);
                        }
                    }],
                });
            });
            </script>

    </body>
</html>

