這次的功能優點複雜,組件嵌套了很多次,自己表達能力畢竟有限,分享出來未必能講明白。為了保持內容的連貫性,最終決定寫一下。先看效果: 關鍵點:1、組件嵌套手風琴式摺疊組件,嵌套輸入行,還嵌套輸入行的組合(例子中的邊框) 2、多角度重置實時監測當前值跟預設值是否一致,並提供重置功能。 3、不得不感嘆,V ...
這次的功能優點複雜,組件嵌套了很多次,自己表達能力畢竟有限,分享出來未必能講明白。為了保持內容的連貫性,最終決定寫一下。先看效果:
關鍵點:
1、組件嵌套
手風琴式摺疊組件,嵌套輸入行,還嵌套輸入行的組合(例子中的邊框)
2、多角度重置
實時監測當前值跟預設值是否一致,並提供重置功能。
3、不得不感嘆,VUE強大!
比上次的代碼增加了一個RxInputRowGroup.vue文件,在inputs目錄下。基於slot實現,關鍵看這個代碼就好:
<template> <div class="row-group"> <div class="rx-input-row group-header" :class = "changed ? 'changed' :''"> <div class="label" :class="collapsed? 'collapsed' :''" @click="click" > {{label}} <div v-if="changed" class="reset-button" @click="resetAll" > {{$t('widgets.reset')}} </div> </div> <div v-if="collapsed" class="group-value"> <div v-for="row in inputValue" v-if="row.value" class="value-label" > {{row.value}} <span class="remove-button" @click="remove(row.value)">×</span> </div> </div> </div> <div v-if="!collapsed" class="row-group-body"> <slot></slot> </div> </div> </template> <script> export default { name: 'RxInputRowGroup', props:{ label:{ default:'' }, value:{ default:[] }, }, data () { return { collapsed: true, } }, computed:{ changed(){ for(var i in this.inputValue){ let row = this.inputValue[i] if(row.value !== row.defaultValue){ return true } } return false }, inputValue: { get:function() { return this.value; }, set:function(val) { this.$emit('input', val); }, }, }, methods: { click(){ this.collapsed = !this.collapsed }, resetAll(event){ for(var i in this.inputValue){ this.inputValue[i].value = this.inputValue[i].defaultValue } event.stopPropagation() }, remove(value){ for(var i in this.inputValue){ if(this.inputValue[i].value === value){ this.inputValue[i].value = '' } } } }, } </script> <style> .row-group .group-header .label{ justify-content: space-between; } .row-group-body .rx-input-row .label{ justify-content: center; } .row-group .group-header .label{ position: relative; } .row-group .group-header .label::after{ position: absolute; content: ''; width: 0; height: 0; top: 13px; right: 7px; border-width: 4px; border-style: solid; border-color: #c2c2c2 transparent transparent transparent; } .row-group .group-header .label.collapsed::after{ position: absolute; content: ''; width: 0; height: 0; top: 11px; right: 7px; border-width: 4px; border-style: solid; border-color:transparent transparent transparent #c2c2c2; } .group-value{ display: flex; flex-flow: row; flex-wrap: wrap; } .group-value .value-label{ display: flex; flex-flow: row; padding: 0 4px; height: 24px; align-items: center; justify-content: space-between; background: rgba(255,255,255,0.1); border-radius: 3px; margin: 1px; } .group-value .value-label .remove-button{ margin-left:2px; cursor: pointer; } </style>
調用處代碼:
<template> <CollapsibleItem class="option-item" @itemClick = "itemClick"> <template #heading> {{inputValue.label}} <div v-if="changed" class="reset-button" @click="resetAll">{{$t('widgets.reset')}}</div> </template> <template #body> <RxInputRowGroup v-for="(row, i) in inputValue.rows" v-if="row.isRowGroup" :key="i" :label = "row.label" v-model = "row.rows" > <RxInputRow v-for="(subRow, j) in row.rows" :key="j" :label = "subRow.label" :inputName = "subRow.inputName" :inputProps = "subRow.props" :defaultValue = "subRow.defaultValue" v-model = "subRow.value" > </RxInputRow> </RxInputRowGroup> <RxInputRow v-else="row.isRowGroup" :key="i" :label = "row.label" :inputName = "row.inputName" :inputProps = "row.props" :defaultValue = "row.defaultValue" v-model = "row.value" > </RxInputRow> </template> </CollapsibleItem> </template>
累趴了,睡覺去了。
詳細代碼,請參考Github:https://github.com/vularsoft/studio-ui
若有有問題,請留言交流。