vue 封装 下拉选择框 actionSheet, dropDown ,类似mint-ui中的actionSheet

    xiaoxiao2022-07-05  185

    一,封装蒙层Popup 框---带淡入淡出渐变效果的

    <template>     <transition name="rytpopup-transition">         <div class="rytPopup" v-show="visible" @click="closeRytpopup">             <slot></slot>         </div>     </transition> </template> <!--  slot 意为插槽 里面可以放任何标签 --> <script>  export default {      name:"rytPopup",      props:{          center:{              type: Boolean,              default:false              }             },     data(){         return{             visible:false,              }             },     methods:{         closeRytpopup(){             this.visible = false         },

        },     watch:{         visible(val){            this.$emit('input',val)  //当visible的值发生改变的时候,把val(viaible的值)传给父组件的v-model属性         },           center(val){ //当center的值发生改变的时候,把center的val值传给this.viaible             this.visible = val           }    

        },  } </script> <style scoped>     .rytPopup {       position: fixed;       left: 0;       top: 0;       width: 100%;       height: 100%;       opacity: 0.5;       background-color: #000     }     /*利用vue 的transition 中的过渡实现背景色的opacity 的值在0 和1之间的过渡*/   .rytpopup-transition-enter-active, .rytpopup-transition-leave-active {       transition: opacity .5s;     }     .rytpopup-transition-enter, .rytpopup-transition-leave-to /* .fade-leave-active below version 2.1.8 */      {       opacity: 0;     } </style>

     

    二,封装 dropdown下拉选择框

    <template>   <div>     <!--     蒙层组件,此处是父组件开始 -->     <ryt-popup :center="currentValue" v-model="currentValue">     </ryt-popup>     <!--     蒙层组件,此处是父组件结束 -->     <!-- 下拉选择弹框组建封装 开始 -->     <transition name="ryt-transition">             <div class="ryt-actionsheet" v-show="currentValue">                 <p class="rytTitle parent">{{title}}</p>                 <ul style="border-bottom-right-radius: 12px;border-bottom-left-radius:12px;background-color: #fff">                     <li class="ryt-mint-actionsheet-listitem parent" @click="clickItem(item,index)" v-for="(item,index) in actions">{{item}}</li>                 </ul>                 <button class="ryt-mint-actionsheet-button parent" @click="closeRytDropdown" :style="{color:cancenTextColor}">{{cancelText}}</button>             </div>     </transition>     <!-- 下拉选择弹框组建封装 结束 -->  </div> </template>

    <script>     import rytPopup from './rytPopup.vue';  //popup蒙层框     export default {       name:"rytDropdown",       components:{         rytPopup       },       props:{           title:{               type:String,               default:'请选择您将进行的操作'           },           actions:{               type:[Array,String,Object], //传过来的参数可以为对象,字符串,数组               default:() => []           },           cancelText:{               type:String,               default:'取消'           },           center:{ //接受父组件给子组件的center属性的传值               type:Boolean,               default:false           },           cancenTextColor:{   //取消按钮的文字颜色             type:String,               default:'rgb(255, 130, 0)'           }

          },       data(){           return {               currentValue:false,           }

          },       methods:{           closeRytDropdown(){  //关闭子组件            this.currentValue = false           },           clickItem(item,index){ //选择下拉框选项               this.$emit('clickOption',{                   item:item,                   index:index               })                         this.currentValue = false           }       },       watch: {       currentValue(val) {  //监听currentValue的值传给父组件,父组件没有Input事件为什么还传值给父组件了?解释: v-model 绑定的是input事件          this.$emit('input', val);        },       center(val){  //监听父组件通过props传过来的center的布尔值打开子组件下拉框           this.currentValue = val

          }             },      mounted() {               },

        } </script> <style scoped>       .ryt-actionsheet{          position: fixed;           width: 355px;           border-radius: 12px;           text-align: center;           bottom: 0;           left: 50%;           max-height: 100%;           overflow-y: auto;           transform: translate3d(-50%, 0, 0);           backface-visibility: hidden;           transition: transform .3s ease-out;          }          .rytTitle{               color:#999999;               font-size: 16px;               height:44px;               line-height: 44px;               background-color: #fff;              }          .parent{            position: relative;          }          .parent::after {  /*利用缩放和伪元素解决1px在不同手机有粗有细问题*/           margin:auto auto;           width:355px;           position: absolute;           bottom: 0;           left: 0;           right: 0;           content: "";           box-sizing: border-box;           height: 1px;           border-bottom: 1px solid #e8e8e8;                      transform: scaleY(0.5);           transform-origin: 0 0;         }          .ryt-mint-actionsheet-listitem, .ryt-mint-actionsheet-button{         display: block;         width: 100%;         height: 44px;         line-height: 44px;         font-size: 18px;         color: #333;         }         .ryt-mint-actionsheet-button{          margin-top:11px;          border-radius: 12px;          background-color: #fff;          }          /*弹窗动画*/           .ryt-transition-enter,           .ryt-transition-leave-active {             transform: translate3d(-50%, 100%, 0);           } </style>

     

    三,具体页面中的引用dropdown组件

    <template>   <div class="about marquee">       <!-- 自定义dropDown组件 -->      <ryt-dropdown       v-model="rytDropdown"       :actions="actions"       :center="rytDropdown"       @clickOption="chooseOption"       title="请选择您的提示语"       cancelText="关闭/取消"       cancenTextColor="rgb(255, 130, 0)"       >     </ryt-dropdown>

         <button @click="clickRyt">点击Rytdropdown</button>

      </div> </template>

    <script> import rytDropdown from '../../components/dropDown/rytDropdown.vue';  //下拉框带popup蒙层 export default {    name:'cece',    components: { //注册组件     rytDropdown,   },     data() {     return {      actions: {  //下拉框选项           "1": "半年以内",           "2": "半年至一年",           "3": "一年至上",         },      rytDropdown:false,     };   },   methods: {      //rytdropdown      clickRyt(){         this.rytDropdown = true               },      chooseOption(e){ //选中下拉框中的某一项出发的事件       console.log(e,'chooseOption')      }      },   mounted(){        },   watch:{     }

     } </script>

    <style scoped>

    </style>

    四,大概效果如下

    五,需要掌握知识点 父子组件之间的传值  slot 插槽

    ---------------------------------------------------------------------------------------------------------------------------------------------------------------------

    不够完善,未完待续

    最新回复(0)