shentao / vue-multiselect

Universal select/multiselect/tagging component for Vue.js
https://vue-multiselect.js.org/
MIT License
6.71k stars 988 forks source link

Is it possible to call a computed property on select event? #1177

Open BorisAng opened 4 years ago

BorisAng commented 4 years ago

We have 4 dropdowns and the following computed property, which calculates which items from the dropdowns have been selected. The property is then used when emitting events in order to perform some API calls.

bidsSelectedFilters () {
  let selFilters = {}
  let mappedBTypeValue
  let mappedBitStatusValue

  if (this.bTypeValue !== null) {
    mappedBTypeValue = this.bTypeValue.map((member) => member.uc_code)
    for (let i = 0; i < mappedBTypeValue.length; i++) {
      mappedBTypeValue[i] = { id: mappedBTypeValue[i] }
    }
    selFilters.ucode = mappedBTypeValue
    this.updateBTypeValue(mappedBTypeValue)
  } else {
    selFilters.ucode = []
  }

  if (this.bidStatusValue !== null) {
    mappedBitStatusValue = this.bidStatusValue.map((member) => member.js_ref)
    for (let i = 0; i < mappedBitStatusValue.length; i++) {
      mappedBitStatusValue[i] = { id: mappedBitStatusValue[i] }
    }
    selFilters.status = mappedBitStatusValue
    this.updateBidStatusValue(mappedBitStatusValue)
  } else {
    selFilters.status = []
  }

  if (this.groupValue !== null) {
    let gpNameObj = { id: this.groupValue.gp_ref }
    selFilters.group = gpNameObj
    this.updateGroupValue(gpNameObj)
  } else {
    selFilters.group = {}
  }

  if (this.personValue !== null) {
    let pxdRefObj = { id: this.personValue.pxd_ref }
    selFilters.person = pxdRefObj
    this.updatePersonValue(pxdRefObj)
  } else {
    selFilters.person = {}
  }
  return selFilters
}

Now, when we pass the property to the dropdown's select event like so @select="bidsSelectedFilters" we get the following error

[Vue warn]: Error in v-on handler: "TypeError: handler.apply is not a function"

The error makes us think that we cannot pass computed properties to the events, however, we are not sure. Any help will be appreciated!

acidbiscuit commented 4 years ago

Only functions should be passed as event handlers in templates (@ or v-on). Computed property is used to access the value for which we define a getter (your code above).

Suggested way would be to define a method, for example, onSeletFilter and pass it as @select event handler. onSeletFilter will receive selected value as an argument that can assigned to update specific defined data property. Such data property then can be included in bidsSelectedFilters computed property. Once data property is updated, bidsSelectedFilters will be re-computed and therefore will always provide correct value to be used in API call, etc.