Skip to content

Instantly share code, notes, and snippets.

@supernovel
Last active August 27, 2021 04:08
Show Gist options
  • Save supernovel/927e7fefb34d49e8958bc2c6433fe63c to your computer and use it in GitHub Desktop.
Save supernovel/927e7fefb34d49e8958bc2c6433fe63c to your computer and use it in GitHub Desktop.
vue-drawer.vue
<template lang="pug">
//refer to https://github.com/segmentio/chrome-sidebar/blob/master/src/frame.js
transition(name='drawer' appear)
aside(
:class='drawerContainerClass'
v-show='opened'
v-click-outside='vcoOption'
)
div(:class='drawerWrapperClass')
div(v-show='isExistHeader' :class='drawerHeaderClass')
slot(name='header')
div(:class='drawerContentClass')
slot(name='content')
//div(class='appContainer') //TODO
slot(name='appContent')
</template>
<script>
import Vue from 'vue/dist/vue.runtime';
import vClickOutside from 'v-click-outside';
Vue.use(vClickOutside);
export default {
props: {
opened: {
type: Boolean,
default: false
},
clickOutsideToClose: {
type: Boolean,
default: false
},
position: {
type: String,
default: 'right'
},
mode: {
type: String,
default: 'float'
}
},
data: function(){
return {
vcoOption: {
handler: this.toggle.bind(this, false),
middleware: this.vcoFilter.bind(this)
}
}
},
computed: {
isExistHeader(){
return !!this.$slots.header;
},
drawerContainerClass(){
return `${this.$style.container} ${this.$style[this.mode]} ${this.$style[this.position]}`
},
drawerWrapperClass(){
return `${this.$style.wrapper}`
},
drawerHeaderClass(){
return `${this.$style.header}`
},
drawerContentClass(){
return `${this.$style.content} ${this.isExistHeader ? '': this.$style.noneHeader}`;
}
},
methods: {
toggle(value){
if(value != null){
this.opened = value;
}else{
this.opened = !this.opened
}
},
vcoFilter(event, el){
return this.clickOutsideToClose && !event.target.classList.contains('vocDrawerExclude');
}
}
}
</script>
<style lang="scss" module>
$content-border-radius: 8px;
$header-height: 50px;
.container {
&.float{
position: fixed;
z-index: 10000;
top: 0px;
box-sizing: border-box;
width: 65%;
max-width: 400px;
height: 100%;
padding: 8px;
margin: 0px;
background-color: transparent;
&.right{
right: 0px;
.wrapper{
box-shadow: -1px 1px 8px rgba(0, 0, 0, 0.15);
}
}
&.left{
left: 0px;
.wrapper{
box-shadow: 1px 1px 8px rgba(0, 0, 0, 0.15);
}
}
.wrapper{
display: flex;
flex-flow: column;
width: 100%;
height: 100%;
background-color: white;
border: none;
border-radius: $content-border-radius;
.header, .content{
display: flex;
width: 100%;
border: none;
background-color: white;
}
.header {
flex: 0 0 $header-height;
border-top-left-radius: $content-border-radius;
border-top-right-radius: $content-border-radius;
}
.content {
flex: 1 1 auto;
border-bottom-left-radius: $content-border-radius;
border-bottom-right-radius: $content-border-radius;
&.noneHeader{
border-top-left-radius: $content-border-radius;
border-top-right-radius: $content-border-radius;
}
}
}
&:global(.drawer-enter-active), &:global(.drawer-leave-active) {
transition: transform 0.45s cubic-bezier(0, 0, 0.3, 1);
}
&:global(.drawer-enter), &:global(.drawer-leave-to) {
&.right{
transform: translateX(100%);
}
&.left{
transform: translateX(-100%);
}
}
&:global(.drawer-enter-to), &:global(.drawer-leave) {
transform: translate3d(0, 0, 0);
}
}
&.attach{
//TODO
}
}
</style>
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment