08335 / hivui-platform-template
hivui平台项目模板
Newer
Older
hivui-platform-template / project / admin / components / dialog / index.vue
caibinghong on 29 May 2021 add
<template>
    <transition>
    <div class="pl-dialog-wrap" v-show="visible">
        <vue-draggable-resizable
            ref="cmp-VueDraggable"
            class="pl-dialog"
            class-name-handle="pl-dialog-resize"
            :w="w"
            :h="h"
            :z="zindex"
            :minWidth="width"
            :minHeight="height"
            :x="x"
            :y="y"
            @dragging="onDrag"
            @resizing="onResize"
            :parent="true"
            :dragHandle="dragHandle"
            :enableNativeDrag="true"
        >
            <div class="pl-dialog-head" ref="dom-head">
                <div class="title">
                    {{title}}
                </div>
                <i class="icon-close iconfont close" @click="handleCancel"></i>
            </div>
            <div class="pl-dialog-body" ref="dom-body" :style="bdStyle">
                <div class="pl-dialog-content" ref="dom-content">
                    <div v-html="content"></div>
                    <slot v-if="!content"></slot>
                </div>
            </div>
            <div class="pl-dialog-foot" ref="dom-foot" v-if="hasfoot">
                <slot name="footer">
                    <button class="pl-btn pl-btn-round" @click="handleCancel">取消</button>
                    <button class="pl-btn pl-btn-round pl-btn-primary" @click="handleOk">确定</button>
                </slot>
            </div>
        </vue-draggable-resizable>
        <div class="pl-dialog-shadow" v-if="shade"></div>
    </div>
    </transition>
</template>
<script>
//https://mauricius.github.io/vue-draggable-resizable/?path=/info/styling--style-resizing
import VueDraggableResizable from "vue-draggable-resizable";
export default {
    components: {
        VueDraggableResizable
    },
    data() {
        return {
            w: this.width,
            h: this.height,
            x: 0,
            y: 0,
            dragHandle: ".pl-dialog-head",
            zindex: 10000,
            bdStyle:{
                height:null
            },
            visible:false,
            content:null
        };
    },
    props:{
        title:{
            type:String,
            default:'提示'
        },
        width:{
            type:Number,
            default:200
        },
        height:{
            type:Number,
            default:200
        },
        offset:{
            type:String,
            default:''
        },
        hasfoot:{
            type:Boolean,
            default:true
        },
        shade:{
            type:Boolean,
            default:true
        }

    },
    mounted() {
        document.body.appendChild(this.$el);
    },
    updated(){
        this.resizeBody();
    },
    beforeDestroy(){
        this.$el.remove();
    },
    methods: {  
        winResize(){
            let parentW = document.documentElement.offsetWidth,
            parentH = document.documentElement.offsetHeight || 0;
            this.winWidth=parentW;
            this.winHeight=parentH;
        },
        setContent(html){
            this.content = html;
        },
        show(){
            //v-if="visible" 显示会准  v-show会不准
            this.visible=true;
            this.x = (document.documentElement.offsetWidth - this.w)/2;
            this.y = (document.documentElement.offsetHeight - this.h)/2;    
            if(this.offset=='rb'){
                debugger
                this.x = (document.documentElement.offsetWidth - this.w);
                this.y = (document.documentElement.offsetHeight - this.h);    
            }
            this.$nextTick(r=>{
                //因为不会准 所以 重新计算
                let dragable = this.$refs['cmp-VueDraggable'];  
                dragable.resetBoundsAndMouseState();
                dragable.rawWidth = this.w;
                dragable.rawHeight = this.h;
                dragable.rawLeft = this.x;
                dragable.rawTop = this.y;
                dragable.left = this.x;
                dragable.top = this.y;
                [dragable.parentWidth, dragable.parentHeight] = dragable.getParentSize();
                dragable.rawRight = dragable.parentWidth - dragable.rawWidth - dragable.rawLeft
                dragable.rawBottom = dragable.parentHeight - dragable.rawHeight - dragable.rawTop
            })  
        },
        hide(){
            this.visible=false;
        },
        resizeBody(){
            if(!this.$refs['dom-head'])return;
            const headRect = this.$refs['dom-head'].getBoundingClientRect();
            const footRect = this.$refs['dom-foot'].getBoundingClientRect();
            this.bdStyle.height = (this.h - headRect.height - footRect.height)+'px';
        },
        onResize: function(x, y, width, height) {
            this.x = x;
            this.y = y;
            this.w = width;
            this.h = height;
            this.resizeBody();
        },
        onDrag: function(x, y) {
            this.x = x;
            this.y = y;
        },
        handleOk(){
            let backVal = this.$emit('onOk');
            this.hide();
        },
        handleCancel(){
            this.$emit('onCancel');
            this.hide();
        }        
    }
};
</script>
<style lang="less">
.pl-dialog-wrap {
    position: fixed;
    left: 0;
    top: 0;
    width: 100%;
    height: 100%;
}
.pl-dialog-shadow {
    position: fixed;
    left: 0;
    top: 0;
    width: 100%;
    height: 100%;
    z-index: 10;
    background: rgba(0, 0, 0, 0.3);
}
.pl-dialog {
    background: #fff;
    box-shadow: 0 0 10px rgba(0, 0, 0, 0.1);  
    >.pl-dialog-head {
        padding: 15px 10px;
        border-top: 2px #0066cc solid;
        background: #efefef;
        cursor: move;
        height: 16px;
        overflow: hidden;
        > .close {
            position: absolute;
            right: 8px;
            top: 12px;
            font-size: 24px;
            color:#666;
            cursor: pointer;
            &:hover{
                color:red;   
                transform: rotate(-90);
                -webkit-transition: all 300ms linear;
                -ms-transition: all 300ms linear;
                transition: all 300ms linear;
            }
        }
    }
    >.pl-dialog-body {
        overflow: auto;
        .pl-dialog-content{
            padding: 8px;
        }
    }
    >.pl-dialog-foot{
        height: 35px;
        overflow: hidden;
        padding: 10px;
        text-align: right;
        background-color:#f3f3f3;
        .pl-btn+.pl-btn{
            margin-left: 15px;
        }
    }
    .pl-dialog-resize {
        position: absolute;
        height: 4px;
        width: 4px;
        display: block!important;
    }

    .pl-dialog-resize-tl {
        top: 0px;
        left: 0px;
        cursor: nw-resize;
    }

    .pl-dialog-resize-tm {
        top: 0;
        left: 4px;
        right:4px;
        width:auto;
        cursor: n-resize;
    }

    .pl-dialog-resize-tr {
        top: 0;
        right:0;
        cursor: ne-resize;
    }

    .pl-dialog-resize-ml {
        top: 4px;
        bottom:4px;
        left: 0;
        height: auto;
        cursor: w-resize;
    }

    .pl-dialog-resize-mr {
        top: 4px;
        bottom: 4px;
        right: 0;
        height: auto;
        cursor: e-resize;
    }

    .pl-dialog-resize-bl {
        bottom: 0;
        left: 0;
        cursor: sw-resize;
    }

    .pl-dialog-resize-bm {
        bottom: 0;
        left: 4px;
        right: 4px;
        width:auto;
        cursor: s-resize;
    }

    .pl-dialog-resize-br {
        bottom: 0;
        right: 0;
        cursor: se-resize;
    }
}
</style>