<template>
    <div
        class="demo-block"
        :class="[blockClass, { hover: hovering }]"
        @mouseenter="hovering = true"
        @mouseleave="hovering = false"
    >
        <div class="source">
            <slot name="source"></slot>
        </div>
        <div class="meta" ref="meta">
            <div class="description" v-if="$slots.default">
                <slot></slot>
            </div>
            <div class="highlight" v-if="$slots.default">
                <slot name="highlight"></slot>
            </div>
        </div>
        <div
            class="demo-block-control"
            ref="control"
            :class="{ 'is-fixed': fixedControl }"
            @click="isExpanded = !isExpanded"
        >
            <transition name="arrow-slide">
                <i :class="[iconClass, { hovering: hovering }]"></i>
            </transition>
            <transition name="text-slide">
                <span v-show="hovering">{{ controlText }}</span>
            </transition>
        </div>
    </div>
</template>

<script>
import compoLang from '../config/config.json'
import { stripScript, stripStyle, stripTemplate } from '../../document/util'
export default {
    data() {
        return {
            codepen: {
                script: '',
                html: '',
                style: ''
            },
            hovering: false,
            isExpanded: false,
            fixedControl: false,
            scrollParent: null
        }
    },

    computed: {
        lang() {
            return this.$route.path.split('/')[1]
        },

        langConfig() {
            return compoLang['demo-block']
        },

        blockClass() {
            return `demo-${this.lang} demo-${this.$router.currentRoute.path.split('/').pop()}`
        },

        iconClass() {
            return this.isExpanded ? 'el-icon-caret-top' : 'el-icon-caret-bottom'
        },

        controlText() {
            return this.isExpanded ? this.langConfig['hide-text'] : this.langConfig['show-text']
        },

        codeArea() {
            return this.$el.getElementsByClassName('meta')[0]
        },

        codeAreaHeight() {
            if (this.$el.getElementsByClassName('description').length > 0) {
                return (
                    this.$el.getElementsByClassName('description')[0].clientHeight +
                    this.$el.getElementsByClassName('highlight')[0].clientHeight +
                    30
                )
            }
            return this.$el.getElementsByClassName('highlight')[0].clientHeight
        }
    },
    watch: {
        isExpanded(val) {
            this.codeArea.style.height = val ? `${this.codeAreaHeight + 1}px` : '0'
            if (!val) {
                this.fixedControl = false
                this.$refs.control.style.left = '0'
                this.removeScrollHandler()
                return
            }
            setTimeout(() => {
                this.scrollParent = document.querySelector('.page-wrap > .el-scrollbar__wrap')
                this.scrollParent && this.scrollParent.addEventListener('scroll', this.scrollHandler)
                this.scrollHandler()
            }, 200)
        }
    },

    created() {
        const highlight = this.$slots.highlight
        if (highlight && highlight[0]) {
            let code = ''
            let cur = highlight[0]
            if (cur.tag === 'pre' && cur.children && cur.children[0]) {
                cur = cur.children[0]
                if (cur.tag === 'code') {
                    code = cur.children[0].text
                }
            }
            if (code) {
                this.codepen.html = stripTemplate(code)
                this.codepen.script = stripScript(code)
                this.codepen.style = stripStyle(code)
            }
        }
    },
    mounted() {
        this.isExpanded = false
        this.$nextTick(() => {
            let highlight = this.$el.getElementsByClassName('highlight')[0]
            if (this.$el.getElementsByClassName('description').length === 0) {
                highlight.style.width = '100%'
                highlight.borderRight = 'none'
            }
        })
    },
    beforeDestroy() {
        this.removeScrollHandler()
    },

    methods: {
        scrollHandler() {
            const { top, bottom, left } = this.$refs.meta.getBoundingClientRect()
            console.log(bottom, document.documentElement.clientHeight)
            this.fixedControl =
                bottom > document.documentElement.clientHeight && top + 46 <= document.documentElement.clientHeight
            this.$refs.control.style.left = this.fixedControl ? `${left}px` : '0'
        },

        removeScrollHandler() {
            this.scrollParent && this.scrollParent.removeEventListener('scroll', this.scrollHandler)
        }
    }
}
</script>

<style lang="scss">
.demo-block {
    transition: 0.2s;
    @include box_flex($width: 100%, $height: auto, $direction: column, $justify: flex-start, $align: flex-start);
    margin-bottom: 42px;

    p,
    pre {
        margin-left: 0px !important;
        margin-right: 0px !important;
    }

    p,
    pre {
        width: calc(100%) !important;
    }

    .source {
        padding: 24px;
        @include box_flex($width: 100%, $height: auto, $direction: row, $justify: flex-start, $align: flex-start);
    }

    .meta {
        width: 100%;
        @include background_color(bgColor2);
        overflow: hidden;
        transition: height 0.2s;
        @include box_flex($width: 100%, $height: 0, $direction: column, $justify: flex-start, $align: flex-start);
        .description {
            width: calc(100% - 40px);
            padding: 20px;
            box-sizing: border-box;
            border-radius: 3px;
            font-size: 14px;
            line-height: 22px;
            word-break: break-word;
            margin: 15px auto;
            @include font_color(fontColor3);
            @include background_color(bgColor);
            border-radius: 8px;
            p {
                margin: 0;
                line-height: 26px;
                @include font_color(fontColor1);
            }
            code {
                width: 100%;
                height: 100%;
                margin: 0 4px;
                display: inline-block;
                padding: 1px 5px;
                font-size: 12px;
                border-radius: 3px;
            }
        }
    }
    .highlight {
        width: 100%;
        pre {
            margin: 0;
        }
        code.hljs {
            padding: 10px 24px 18px;
            margin: 0;
            border: none;
            max-height: none;
            border-radius: 0;
            @include font_color(fontColor4);
            .hljs-name {
                @include font_color(fontColor1);
            }
            .hljs-tag {
                @include font_color(fontColor1);
            }
            // .hljs-keyword {

            // }
            .hljs-string {
                @include font_color(fontColor1);
            }

            &::before {
                content: none;
            }
        }
    }

    .demo-block-control {
        margin-top: -1px;
        cursor: pointer;
        position: relative;
        @include border_color($direction: bottom, $type: solid, $width: 1px, $color: 'borderColor');
        @include border_color($direction: top, $type: solid, $width: 1px, $color: 'borderColor');
        @include background_color(bgColor);
        @include box_flex($height: auto, $direction: column, $justify: center, $align: center);
        @include font_color(fontColor3);
        &.is-fixed {
            position: fixed;
            bottom: 0;
            width: 906px;
        }
        i {
            font-size: 16px;
            line-height: 44px;
            transition: 0.3s;
            &.hovering {
                transform: translateX(-70px);
            }
        }
        > span {
            position: absolute;
            transform: translateX(-30px);
            font-size: 14px;
            line-height: 44px;
            transition: 0.3s;
            display: inline-block;
        }
        // &:hover {
        //     color: #409eff;
        // }
        & .text-slide-enter,
        & .text-slide-leave-active {
            opacity: 0;
            transform: translateX(10px);
        }
    }
}
</style>
