RegionPicker.vue 4.7 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184
  1. <template>
  2. <uni-popup background-color="#fff" ref="currentValue" type="bottom">
  3. <view class="picker">
  4. <view class="div toolbar">
  5. <text class="button toolbar-item cancel-item" @click="cancel">取消</text>
  6. <view class="div picker-header">请选择地区</view>
  7. <text class="button toolbar-item confirm-item" @click="confirm">确定</text>
  8. </view>
  9. <picker-view class="popup-content" indicator-style="height:80rpx" @change="onValuesChange" :value="areaPicker">
  10. <picker-view-column v-for="(item,index) in buildItems" :key="index">
  11. <view class="popup-item-wrapper" v-for="(v,i) in item.values" :key="i"><text class="popup-item">{{v.area_name}}</text></view>
  12. </picker-view-column>
  13. </picker-view>
  14. </view>
  15. </uni-popup>
  16. </template>
  17. <script>
  18. import { getAreaTree } from '../api/area'
  19. export default {
  20. name: 'RegionPicker',
  21. props: {
  22. modal: {
  23. default: true
  24. },
  25. modalFade: {
  26. default: false
  27. },
  28. lockScroll: {
  29. default: false
  30. },
  31. closeOnClickModal: {
  32. default: true
  33. }
  34. },
  35. data () {
  36. return {
  37. areaPicker: [],
  38. items: false
  39. }
  40. },
  41. created: function () {
  42. getAreaTree().then(res => {
  43. this.items = res.result.area_list
  44. }).catch(function (error) {
  45. uni.showToast({icon:'none',title: error.message})
  46. })
  47. },
  48. computed: {
  49. buildItems: function () {
  50. if (!this.items) {
  51. return []
  52. }
  53. let items = new Array()
  54. this.getDefaultItems(this.items, items)
  55. return items
  56. }
  57. },
  58. methods:{
  59. showPopup(id){
  60. this.$refs[id].open()
  61. },
  62. hidePopup(id){
  63. this.$refs[id].close()
  64. },
  65. getDefaultItems(_item, defaultItems) {
  66. if (_item[0].child && _item[0].child.length > 0) {
  67. let index = 1
  68. if (defaultItems && defaultItems.length == 0) {
  69. defaultItems.push({
  70. flex: 1,
  71. values: _item,
  72. textAlign: 'center'
  73. })
  74. this.areaPicker.push(0)
  75. this.getDefaultItems(_item, defaultItems)
  76. } else if (defaultItems && defaultItems.length > 0) {
  77. defaultItems.push({
  78. flex: 1,
  79. values: _item[0].child,
  80. textAlign: 'center'
  81. })
  82. this.areaPicker.push(0)
  83. this.getDefaultItems(_item[0].child, defaultItems)
  84. }
  85. }
  86. },
  87. onValuesChange(e) {
  88. let value=e.detail.value
  89. let areaPicker=this.areaPicker
  90. for(var i in value){
  91. areaPicker[i]=value[i]
  92. i=parseInt(i)
  93. if(i<(value.length-1)){
  94. if(!this.buildItems[i]['values'].length || !this.buildItems[i]['values'][value[i]]['child'] || !this.buildItems[i]['values'][value[i]]['child'].length){
  95. this.buildItems[i+1]['values']=[]
  96. areaPicker[i+1]=0
  97. }else if(!this.buildItems[i+1]['values'].length || this.buildItems[i]['values'][value[i]]['child'][0]['area_id']!=this.buildItems[i+1]['values'][0]['area_id']){
  98. this.buildItems[i+1]['values']=this.buildItems[i]['values'][value[i]]['child']
  99. areaPicker[i+1]=0
  100. }
  101. }
  102. }
  103. this.areaPicker=areaPicker
  104. this.$forceUpdate()
  105. },
  106. show(){
  107. this.showPopup('currentValue')
  108. },
  109. cancel () {
  110. this.hidePopup('currentValue')
  111. },
  112. confirm() {
  113. this.cancel()
  114. let values = []
  115. for(var i in this.areaPicker){
  116. values[i]=this.buildItems[i]['values'][this.areaPicker[i]]
  117. if(!values[i]){
  118. values[i]={
  119. area_id:0,
  120. area_name:''
  121. }
  122. }
  123. }
  124. this.$emit('onConfirm', values)
  125. }
  126. }
  127. }
  128. </script>
  129. <style lang="scss" scoped>
  130. .picker {
  131. background-color: #ffffff;
  132. }
  133. .toolbar {
  134. height: 2rem;
  135. display: flex;
  136. flex-direction: row;
  137. justify-content: space-between;
  138. align-items: center;
  139. background-color: #f0f2f5;
  140. .toolbar-item {
  141. font-size:$fontSize;
  142. border: none;
  143. border-radius: 0;
  144. background-color: #f0f2f5;
  145. }
  146. .cancel-item {
  147. margin-left: 0.5rem;
  148. color: #4e545d;
  149. }
  150. .confirm-item {
  151. margin-right: 0.5rem;
  152. color: red;
  153. }
  154. .picker-header {
  155. color: #4e545d;
  156. line-height: 2rem;
  157. font-size:$h2;
  158. }
  159. }
  160. .popup-item-wrapper{
  161. display: flex;
  162. justify-content: center;
  163. align-items: center;
  164. }
  165. .popup-item {
  166. font-size: 30rpx;
  167. line-height:80rpx;
  168. text-align: center;
  169. overflow: hidden;
  170. text-overflow: ellipsis;
  171. white-space: nowrap;
  172. }
  173. .popup-content {
  174. padding: 0 40rpx;
  175. height: 300rpx;
  176. }
  177. </style>