wk-field-select.vue 9.3 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331
  1. <template>
  2. <view class="wk-field wk-field-select">
  3. <view v-if="_label" class="wk-field__label">
  4. <view v-if="field.isNull === 1" class="line" />
  5. {{ _label }}
  6. </view>
  7. <view class="wk-field__body" @click.stop="handleChoose">
  8. <view class="wk-field__body-core">
  9. {{ valueStr }}
  10. </view>
  11. <text class="wk wk-arrow-right icon-right" />
  12. </view>
  13. <view
  14. v-if="showOther"
  15. class="wk-field__body other-input">
  16. <input
  17. ref="core"
  18. v-model="otherVal"
  19. type="text"
  20. :disabled="field.disabled"
  21. :maxlength="getMaxlength"
  22. placeholder="请输入"
  23. placeholder-class="wk-placeholder placeholder"
  24. class="other-input__core"
  25. @input="changeText">
  26. </view>
  27. </view>
  28. </template>
  29. <script>
  30. import { QueryBusinessSetting } from 'API/crm/flow'
  31. import { QueryAllCategory } from 'API/crm/product'
  32. import { QueryReceivablesPlan } from 'API/crm/contract'
  33. import mixins from './mixins'
  34. import { isObject, isArray } from '@/utils/types.js'
  35. import { deepCopy } from '@/utils/lib.js'
  36. export default {
  37. name: 'WkFieldSelect',
  38. mixins: [mixins],
  39. data() {
  40. return {
  41. guid: null,
  42. formValue: [],
  43. keyMap: {
  44. business_type: {valueField: 'flowId', labelField: 'flowName'},
  45. business_status: {valueField: 'settingId', labelField: 'settingName'},
  46. category: {valueField: 'categoryId', labelField: 'name'},
  47. receivables_plan: { valueField: 'receivablesPlanId', labelField: 'num'}
  48. },
  49. dataList: [],
  50. otherVal: null
  51. }
  52. },
  53. computed: {
  54. optionsConfig() {
  55. let obj = this.keyMap[this.field.formType] || {labelField: 'label', valueField: 'value'}
  56. if (this.config && this.config.optionsConfig) {
  57. obj = this.config.optionsConfig
  58. }
  59. return obj
  60. },
  61. labelField() {
  62. return this.optionsConfig.labelField
  63. },
  64. valueField() {
  65. return this.optionsConfig.valueField
  66. },
  67. valueStr() {
  68. const arr = this.formValue || []
  69. if (this.$isEmpty(arr)) return ''
  70. if (!this.labelField) return arr
  71. if (!isArray(arr)) return arr
  72. return arr.map(o => o[this.labelField]).join(',')
  73. },
  74. list() {
  75. if (this.field.setting.length === 0) return []
  76. if (isObject(this.field.setting[0])) {
  77. return this.field.setting
  78. } else {
  79. return this.field.setting.map(o => {
  80. return {
  81. label: o,
  82. value: o
  83. }
  84. })
  85. }
  86. },
  87. showOther() {
  88. // 不是单选或多选类型
  89. if (![
  90. 'checkbox',
  91. 'select'
  92. ].includes(this.field.formType)) return false
  93. // 选中值为空
  94. if (this.$isEmpty(this.formValue)) return false
  95. // 选项中没有其他
  96. if (!this.field.setting.includes('其他')) return false
  97. console.log('formValue: ', this.field, this.formValue)
  98. // 选中值不包含其他
  99. const findIndex = this.formValue.findIndex(o => {
  100. return o[this.labelField] === '其他' ||
  101. !this.field.setting.includes(o[this.valueField])
  102. })
  103. if (findIndex === -1) return false
  104. if (this.formValue[findIndex][this.labelField] !== '其他') {
  105. // 初始有默认值时格式化label和value
  106. const otherObj = {
  107. [this.labelField]: '其他',
  108. [this.valueField]: '其他',
  109. otherVal: this.formValue[findIndex][this.valueField]
  110. }
  111. this.$set(this.formValue, findIndex, otherObj)
  112. } else if (!this.formValue[findIndex].hasOwnProperty('otherVal')) {
  113. // 如果选中值包含其他,给otherVal赋初值
  114. this.$set(this.formValue[findIndex], 'otherVal', null)
  115. this.$set(this.formValue, findIndex, this.formValue[findIndex])
  116. }
  117. return true
  118. },
  119. getMaxlength() {
  120. return this.field.maxlength || 100
  121. }
  122. },
  123. watch: {
  124. showOther: {
  125. handler() {
  126. if (!this.showOther) {
  127. this.otherVal = null
  128. return
  129. }
  130. const findRes = this.formValue.find(o => o.label === '其他')
  131. this.otherVal = findRes.value === '其他' ? (findRes.otherVal || '') : findRes.value
  132. },
  133. immediate: true
  134. },
  135. value: {
  136. handler(val) {
  137. this.formValue = this.value
  138. this.$nextTick(() => {
  139. if (this.showOther) {
  140. const findRes = this.formValue.find(o => o.hasOwnProperty('otherVal'))
  141. if (findRes) {
  142. this.otherVal = findRes.otherVal
  143. }
  144. }
  145. })
  146. },
  147. deep: true,
  148. immediate: true
  149. },
  150. // formValue: {
  151. // handler() {
  152. // this.emitChangeEvt(this.formValue)
  153. // },
  154. // deep: true,
  155. // immediate: true
  156. // }
  157. },
  158. created() {
  159. this.guid = this.$guid()
  160. },
  161. mounted() {
  162. if (this.field.formType === 'category') {
  163. this.getAllCategory()
  164. } else if (this.field.formType === 'receivables_plan') {
  165. this.getPlanList()
  166. } else {
  167. this.emitChangeEvt(this.formValue)
  168. }
  169. },
  170. methods: {
  171. handleChoose() {
  172. if (this.field.disabled) {
  173. if (this.config && this.config.disabledMsg) {
  174. this.$toast(this.config.disabledMsg)
  175. }
  176. return
  177. }
  178. const bridge = getApp().globalData.selectedValBridge
  179. const options = {
  180. guid: this.guid,
  181. maxlength: 1,
  182. title: '选择' + this.field.name,
  183. defaultVal: this.formValue || []
  184. }
  185. if (this.field.formType === 'checkbox') {
  186. options.maxlength = 1 / 0
  187. }
  188. switch (this.field.formType) {
  189. case 'business_type':
  190. bridge.options = {
  191. ...options,
  192. request: QueryBusinessSetting,
  193. config: this.optionsConfig,
  194. }
  195. break
  196. case 'business_status':
  197. bridge.options = {
  198. ...options,
  199. list: this.field.setting,
  200. config: this.optionsConfig
  201. }
  202. break
  203. case 'category':
  204. if (this.dataList.length > 0) {
  205. bridge.options = {
  206. ...options,
  207. list: this.dataList,
  208. config: this.optionsConfig
  209. }
  210. } else {
  211. bridge.options = {
  212. ...options,
  213. request: QueryAllCategory,
  214. config: this.optionsConfig
  215. }
  216. }
  217. break
  218. case 'receivables_plan':
  219. bridge.options = {
  220. ...options,
  221. request: QueryReceivablesPlan,
  222. params: this.config.otherParams,
  223. config: this.optionsConfig
  224. }
  225. break
  226. default:
  227. bridge.options = {
  228. ...options,
  229. list: this.list,
  230. config: this.optionsConfig,
  231. defaultVal: this.formValue || []
  232. }
  233. }
  234. uni.$on('selected-options', this.selectedOptions)
  235. this.$Router.navigateTo('/pages_common/selectList/options')
  236. },
  237. getAllCategory() {
  238. QueryAllCategory().then(res => {
  239. console.log('res', res)
  240. this.dataList = res
  241. if (!this.$isEmpty(this.field.value)) {
  242. const arr = this.field.value || []
  243. let filterRes = res.filter(o => o.categoryId == arr[arr.length - 1])
  244. this.selectedOptions({
  245. data: filterRes,
  246. guid: this.guid
  247. })
  248. }
  249. }).catch()
  250. },
  251. getPlanList() {
  252. console.log('recei plan: ', this.config)
  253. if (this.$isEmpty(this.config.otherParams)) return
  254. QueryReceivablesPlan(this.config.otherParams).then(res => {
  255. this.dataList = res
  256. if (!this.$isEmpty(this.field.value)) {
  257. const arr = this.field.value || []
  258. let filterRes = res.filter(o => o.receivablesPlanId == arr[arr.length - 1])
  259. this.selectedOptions({
  260. data: filterRes,
  261. guid: this.guid
  262. })
  263. }
  264. }).catch()
  265. },
  266. formatValue(oldStr) {
  267. // 禁止输入 emoji
  268. const regStr = /[\ud800-\udbff]|[\udc00-\udfff]/g;
  269. return oldStr.replace(regStr, '');
  270. },
  271. /**
  272. * 修改输入框值
  273. */
  274. changeText() {
  275. let oldStr = String(this.otherVal)
  276. let valueStr = this.formatValue(this.otherVal)
  277. if (this.field.setting.includes(valueStr)) {
  278. valueStr = ''
  279. }
  280. this.otherVal = oldStr
  281. this.$nextTick(function() {
  282. this.otherVal = valueStr
  283. const findIndex = this.formValue.findIndex(o => o.label === '其他')
  284. if (findIndex !== -1) {
  285. this.formValue[findIndex].otherVal = this.otherVal
  286. this.$set(this.formValue, findIndex, this.formValue[findIndex])
  287. }
  288. oldStr = null
  289. valueStr = null
  290. this.emitChangeEvt(this.formValue)
  291. })
  292. },
  293. selectedOptions(data) {
  294. if (this.guid === data.guid) {
  295. let val = data.data
  296. this.formValue = val
  297. this.emitChangeEvt(this.formValue)
  298. }
  299. uni.$off('selected-options')
  300. }
  301. }
  302. }
  303. </script>
  304. <style scoped lang="scss">
  305. @import './wkField.scss';
  306. .other-input {
  307. margin-top: 10rpx;
  308. .other-input__core {
  309. width: 100%;
  310. }
  311. }
  312. </style>