One small piece per week

preface

Realization function: accordion with switching animation effect
I share a vue3+typeScript widget every week. I just want to share my thoughts on how to implement it.

Results show

Preview the address

The source address

The development process

HTML part

<div class="accordion">
    <div v-for="(vo,inx) in items" :key="inx">
        <! Accordion title -->
        <div class="item" @click="changeItem(vo,inx)">
            {{vo.title}}
        </div>
        <! -- Accordion content -->
        <div class="content" v-show="active==inx&&vo.show">
            {{vo.content}}
            <! -- You can customize content structure -->
            <div v-if="inx===0">I am custom content 1</div>
            <div v-if="inx===1">I am custom content 2</div>
            <div v-if="inx===2">I am custom content 3</div>
        </div>
    </div>
</div>
Copy the code

Ts part

<script lang="ts">
import {
    defineComponent,
    reactive,
    toRefs
} from 'vue'
export default defineComponent({
    setup() {
        // Define the interface type
        interface ItemObj {
            title: string;
            content: string;
            show: boolean;
        }
        const data = reactive({
            items: [{
                    title: "JavaScript".content: "This is content one.".show: true
                },
                {
                    title: "Java".content: "This is content 2.".show: true
                },
                {
                    title: "C++".content: "This is content 3.".show: true}].active: 0.changeItem: (vo: ItemObj, inx: number) = > {
                // To close and open the accordion contents of the current column, click item repeatedly
                if(inx === data.active) { vo.show = ! vo.show }else {
                    vo.show = true
                }
                data.active = inx
            }
        })
        return {
            ...toRefs(data)
        }
    }
})
</script>
Copy the code

The CSS part

.accordion {
    width: 800px;
    padding: 50px 20px;
    background: #ecf0f3;
    height: 600px;
    .item {
        text-align: center;
        line-height: 80px;
        margin: 0 auto;
        width: 600px;
        height: 80px;
        border-radius: 12px;
        box-shadow: inset 12px 12px 20px #d1d9e6, inset -12px -12px 20px #fff;
        cursor: pointer;
        margin-bottom: 5px;
    }

    @keyframes fadeIn {
        from {
            opacity: 0;
        }

        to {
            opacity: 1; }}.content {
        opacity: 0;
        min-height: 80px;
        width: 600px;
        margin: 0 auto;
        animation-name: fadeIn;
        animation-duration: 1s;
        animation-fill-mode: both; }}Copy the code
Vue3 continues to be updated…