One small piece per week

preface

Implementation function: Imitate the simple function of element shuttle box
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="shuttle">
    <! -- Left hand list -->
    <div class="shuttle-box">
        <div class="shuttle-box-title">
            <div>A list of</div>
            <div class="index-num">{{itemLeft.length}}</div>
        </div>
        <div class="shuttle-box-list">
            <div class="shuttle-box-item" v-for="(vo,inx) in itemLeft" :key="inx">
                <input type="checkbox" :value="inx" v-model="checkLeft" :disabled="vo.disabled" /> {{vo.label}}
            </div>
        </div>
    </div>
    <! -- Left and right operation button -->
    <div class="shuttle-click">
        <span @click="goLeft">please</span>
        <span @click="goRight">-</span>
    </div>
    <! -- Right list -->
    <div class="shuttle-box">
        <div class="shuttle-box-title">
            <div>List two</div>
            <div class="index-num">{{itemRight.length}}</div>
        </div>
        <div class="shuttle-box-list">
            <div class="shuttle-box-item" v-for="(vo,inx) in itemRight" :key="inx">
                <input type="checkbox" :value="inx" v-model="checkRight" :disabled="vo.disabled" /> {{vo.label}}
            </div>
        </div>
    </div>
</div>
Copy the code

Ts part

<script lang="ts">
import {
    defineComponent,
    reactive,
    toRefs
} from 'vue'

export default defineComponent({
    setup() {

        const data = reactive({
            itemLeft: [{
                label: 'First data from Listing 1'.disabled: true}, {label: 'Second data from Listing 1'.disabled: false,}],itemRight: [{
                label: 'First data from Listing 2'.disabled: false}, {label: 'Second piece of data from Listing 2'.disabled: false,}],checkLeft: [].checkRight: [].goLeft: () = > {
                // Array sort
                data.checkRight.sort(data.sortIndex);
                data.checkRight.forEach((item) = > {
                    // Move the index of itemRight to the left
                    data.itemLeft.push(data.itemRight[item]);
                    / / remove
                    data.itemRight.splice(item, 1);
                });
                / / to empty
                data.checkLeft = [];
                data.checkRight = [];
            },
            goRight: () = > {
                // Array sort
                data.checkLeft.sort(data.sortIndex);
                data.checkLeft.forEach((item) = > {
                    // Move the index of itemLeft to the right
                    data.itemRight.push(data.itemLeft[item]);
                    / / remove
                    data.itemLeft.splice(item, 1);
                });
                / / to empty
                data.checkLeft = [];
                data.checkRight = [];
            },
            // Checkbox is the index of the bound array, so the index order is different, so that the deletion may not find the error, so that the deletion order is from the largest to the smallest
            // This is the sort argument
            sortIndex: (a, b) = > {
                returnb - a; }})return {
            ...toRefs(data),
        }
    }
})
</script>
Copy the code

The CSS part

.shuttle {
    width: 800px;
    padding: 50px 0;
    display: flex;
    justify-content: space-between; // The entire shuttle box.shuttle-box {
        width: 300px;
        height: 500px;
        border: 1px solid #ddd; / / title.shuttle-box-title {
            background: #f5f7fa;
            padding: 0 20px;
            height: 40px;
            line-height: 40px;
            display: flex;
            justify-content: space-between;
            .index-num {
                color: # 909399;
                font-size: 12px;
                font-weight: 400; }} // list.shuttle-box-list {
            padding: 20px; // a list item.shuttle-box-item {
                line-height: 2.0; }}} // Left and right shuttle buttons.shuttle-click {
        padding-top: 60px;
        cursor: pointer;
        span {
            padding: 5px 10px;
            display: inline-block;
            background: #409eff;
            color: #ffffff;
            margin: 0 5px;
            text-align: center; }}}Copy the code
Vue3 continues to be updated…