index.js 4.2 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203
  1. import { use } from '../utils';
  2. import Picker from '../picker';
  3. import { pickerProps } from '../picker/shared';
  4. const [sfc, bem] = use('area');
  5. export default sfc({
  6. props: {
  7. ...pickerProps,
  8. value: String,
  9. areaList: {
  10. type: Object,
  11. default: () => ({})
  12. },
  13. columnsNum: {
  14. type: [String, Number],
  15. default: 3
  16. }
  17. },
  18. data() {
  19. return {
  20. code: this.value,
  21. columns: [{ values: [] }, { values: [] }, { values: [] }]
  22. };
  23. },
  24. computed: {
  25. province() {
  26. return this.areaList.province_list || {};
  27. },
  28. city() {
  29. return this.areaList.city_list || {};
  30. },
  31. county() {
  32. return this.areaList.county_list || {};
  33. },
  34. displayColumns() {
  35. return this.columns.slice(0, +this.columnsNum);
  36. }
  37. },
  38. watch: {
  39. value() {
  40. this.code = this.value;
  41. this.setValues();
  42. },
  43. areaList: {
  44. deep: true,
  45. handler() {
  46. this.setValues();
  47. }
  48. }
  49. },
  50. mounted() {
  51. this.setValues();
  52. },
  53. methods: {
  54. // get list by code
  55. getList(type, code) {
  56. let result = [];
  57. if (type !== 'province' && !code) {
  58. return result;
  59. }
  60. const list = this[type];
  61. result = Object.keys(list).map(listCode => ({
  62. code: listCode,
  63. name: list[listCode]
  64. }));
  65. if (code) {
  66. // oversea code
  67. if (code[0] === '9' && type === 'city') {
  68. code = '9';
  69. }
  70. result = result.filter(item => item.code.indexOf(code) === 0);
  71. }
  72. return result;
  73. },
  74. // get index by code
  75. getIndex(type, code) {
  76. let compareNum = type === 'province' ? 2 : type === 'city' ? 4 : 6;
  77. const list = this.getList(type, code.slice(0, compareNum - 2));
  78. // oversea code
  79. if (code[0] === '9' && type === 'province') {
  80. compareNum = 1;
  81. }
  82. code = code.slice(0, compareNum);
  83. for (let i = 0; i < list.length; i++) {
  84. if (list[i].code.slice(0, compareNum) === code) {
  85. return i;
  86. }
  87. }
  88. return 0;
  89. },
  90. onChange(picker, values, index) {
  91. this.code = values[index].code;
  92. this.setValues();
  93. this.$emit('change', picker, picker.getValues(), index);
  94. },
  95. setValues() {
  96. let code = this.code || Object.keys(this.county)[0] || '';
  97. const { picker } = this.$refs;
  98. const province = this.getList('province');
  99. const city = this.getList('city', code.slice(0, 2));
  100. if (!picker) {
  101. return;
  102. }
  103. picker.setColumnValues(0, province);
  104. picker.setColumnValues(1, city);
  105. if (city.length && code.slice(2, 4) === '00') {
  106. [{ code }] = city;
  107. }
  108. picker.setColumnValues(2, this.getList('county', code.slice(0, 4)));
  109. picker.setIndexes([
  110. this.getIndex('province', code),
  111. this.getIndex('city', code),
  112. this.getIndex('county', code)
  113. ]);
  114. },
  115. getValues() {
  116. return this.$refs.picker ? this.$refs.picker.getValues().filter(value => !!value) : [];
  117. },
  118. getArea() {
  119. const values = this.getValues();
  120. const area = {
  121. code: '',
  122. country: '',
  123. province: '',
  124. city: '',
  125. county: ''
  126. };
  127. if (!values.length) {
  128. return area;
  129. }
  130. const names = values.map(item => item.name);
  131. area.code = values[values.length - 1].code;
  132. if (area.code[0] === '9') {
  133. area.country = names[1] || '';
  134. area.province = names[2] || '';
  135. } else {
  136. area.province = names[0] || '';
  137. area.city = names[1] || '';
  138. area.county = names[2] || '';
  139. }
  140. return area;
  141. },
  142. reset() {
  143. this.code = '';
  144. this.setValues();
  145. }
  146. },
  147. render(h) {
  148. const on = {
  149. ...this.$listeners,
  150. change: this.onChange
  151. };
  152. return (
  153. <Picker
  154. ref="picker"
  155. class={bem()}
  156. showToolbar
  157. valueKey="name"
  158. title={this.title}
  159. loading={this.loading}
  160. columns={this.displayColumns}
  161. itemHeight={this.itemHeight}
  162. visibleItemCount={this.visibleItemCount}
  163. cancelButtonText={this.cancelButtonText}
  164. confirmButtonText={this.confirmButtonText}
  165. {...{ on }}
  166. />
  167. );
  168. }
  169. });