mirror of
https://github.com/tenrok/vue-select.git
synced 2026-06-22 10:30:34 +03:00
docs: add reduce caveats
This commit is contained in:
@@ -0,0 +1,20 @@
|
|||||||
|
<template>
|
||||||
|
<v-select
|
||||||
|
v-model="selected"
|
||||||
|
:reduce="(option) => option.id"
|
||||||
|
:options="[
|
||||||
|
{ label: 'One', id: 1 },
|
||||||
|
{ label: 'Two', id: 2 },
|
||||||
|
]"
|
||||||
|
/>
|
||||||
|
</template>
|
||||||
|
|
||||||
|
<script>
|
||||||
|
export default {
|
||||||
|
data() {
|
||||||
|
return {
|
||||||
|
selected: 3,
|
||||||
|
}
|
||||||
|
},
|
||||||
|
}
|
||||||
|
</script>
|
||||||
+92
-59
@@ -2,11 +2,12 @@
|
|||||||
|
|
||||||
### `v-model`
|
### `v-model`
|
||||||
|
|
||||||
The most common use case for vue-select is to have the chosen value synced with a parent component. vue-select
|
The most common use case for vue-select is to have the chosen value synced with a parent component.
|
||||||
takes advantage of the `v-model` syntax to sync values with a parent. The `v-model` syntax works with
|
vue-select takes advantage of the `v-model` syntax to sync values with a parent. The `v-model`
|
||||||
primitives and objects.
|
syntax works with primitives and objects.
|
||||||
|
|
||||||
```html
|
```html
|
||||||
|
|
||||||
<v-select v-model="selected" />
|
<v-select v-model="selected" />
|
||||||
```
|
```
|
||||||
|
|
||||||
@@ -14,25 +15,26 @@ Note that when using the `multiple` prop, the `v-model` value will always be an
|
|||||||
|
|
||||||
### Props and Events
|
### Props and Events
|
||||||
|
|
||||||
Sometimes `v-model` might not fit your use case. For example, when working with [Vuex](https://vuex.vuejs.org),
|
Sometimes `v-model` might not fit your use case. For example, when working
|
||||||
you'll need to trigger a mutation rather than mutating a value directly. In that case, maybe you need
|
with [Vuex](https://vuex.vuejs.org), you'll need to trigger a mutation rather than mutating a value
|
||||||
to bind a pre-selected value, and trigger a mutation when it changes.
|
directly. In that case, maybe you need to bind a pre-selected value, and trigger a mutation when it
|
||||||
|
changes.
|
||||||
|
|
||||||
vue-select exposes the `value` prop and an `input` event to enable this. This combo of props and
|
vue-select exposes the `value` prop and an `input` event to enable this. This combo of props and
|
||||||
events is also how Vue wires up the `v-model` syntax internally.
|
events is also how Vue wires up the `v-model` syntax internally.
|
||||||
|
|
||||||
#### Prop: `value`
|
#### Prop: `value`
|
||||||
|
|
||||||
The `value` prop lets vue-select know what value is currently selected. It will accept strings,
|
The `value` prop lets vue-select know what value is currently selected. It will accept strings,
|
||||||
numbers or objects. If you're using a `multiple` v-select, you'll want to pass an array.
|
numbers or objects. If you're using a `multiple` v-select, you'll want to pass an array.
|
||||||
|
|
||||||
```html
|
```html
|
||||||
|
|
||||||
<v-select :value="selected" />
|
<v-select :value="selected" />
|
||||||
```
|
```
|
||||||
|
|
||||||
::: tip 🤓
|
::: tip 🤓 Anytime you bind the `value` prop directly, you're responsible for updating the bound
|
||||||
Anytime you bind the `value` prop directly, you're responsible for updating the bound variable
|
variable in your code using the `@input` event.
|
||||||
in your code using the `@input` event.
|
|
||||||
:::
|
:::
|
||||||
|
|
||||||
#### Event: `input`
|
#### Event: `input`
|
||||||
@@ -42,50 +44,66 @@ state as it's only parameter.
|
|||||||
|
|
||||||
#### Vuex Support
|
#### Vuex Support
|
||||||
|
|
||||||
The `value` prop and `emit` event are very useful when using a state management tool, like Vuex.
|
The `value` prop and `emit` event are very useful when using a state management tool, like Vuex. You
|
||||||
You can bind the selected value with `:value="$store.myValue"`, and use the `input` event to
|
can bind the selected value with `:value="$store.myValue"`, and use the `input` event to trigger a
|
||||||
trigger a mutation, or dispatch an action – or anything else you might need to do when the selection
|
mutation, or dispatch an action – or anything else you might need to do when the selection changes.
|
||||||
changes.
|
|
||||||
|
|
||||||
```html
|
```html
|
||||||
|
|
||||||
<v-select :value="$store.myValue" @input="setSelected" />
|
<v-select :value="$store.myValue" @input="setSelected" />
|
||||||
```
|
```
|
||||||
|
|
||||||
```js
|
```js
|
||||||
methods: {
|
methods: {
|
||||||
setSelected(value) {
|
setSelected(value)
|
||||||
// trigger a mutation, or dispatch an action
|
{
|
||||||
}
|
// trigger a mutation, or dispatch an action
|
||||||
|
}
|
||||||
}
|
}
|
||||||
```
|
```
|
||||||
|
|
||||||
|
## Single/Multiple
|
||||||
|
|
||||||
|
By default, vue-select supports choosing a single value. If you need multiple values, use the
|
||||||
|
`multiple` boolean prop, much the same way you would on an HTML `<select>` element. When `multiple`
|
||||||
|
is true, `v-model` and `value` must be an array.
|
||||||
|
|
||||||
|
```html
|
||||||
|
|
||||||
|
<v-select multiple v-model="selected" :options="['Canada','United States']" />
|
||||||
|
```
|
||||||
|
|
||||||
|
<v-select multiple :options="['Canada','United States']" />
|
||||||
|
|
||||||
## Transforming Selections
|
## Transforming Selections
|
||||||
|
|
||||||
When the `options` array contains objects, vue-select returns the whole object as dropdown value
|
When the `options` array contains objects, vue-select returns the whole object as dropdown value
|
||||||
upon selection. This approach makes no assumptions about the data you need, and provides a lot of
|
upon selection. This approach makes no assumptions about the data you need, and provides a lot of
|
||||||
flexibility. However, there will be situations where maybe you just need to return a single key
|
flexibility. However, there will be situations where you just need to return a single key from an
|
||||||
from an object.
|
object.
|
||||||
|
|
||||||
### Returning a single key with `reduce`
|
### Returning a single key with `reduce`
|
||||||
|
|
||||||
If you need to return a single key, or transform the selection before it is synced, vue-select
|
If you need to return a single key, or transform the selection before it is synced, vue-select
|
||||||
provides a `reduce` callback that allows you to transform a selected option before it is passed to
|
provides a `reduce` callback that allows you to transform a selected option before it is passed to
|
||||||
the `@input` event. Consider this data structure:
|
the `@input` event. Consider this data structure:
|
||||||
|
|
||||||
```js
|
```js
|
||||||
let options = [{code: 'CA', country: 'Canada'}];
|
let options = [{code: 'CA', country: 'Canada'}];
|
||||||
```
|
```
|
||||||
|
|
||||||
If we want to display the `country`, but return the `code` to `v-model`, we can use the `reduce`
|
If we want to display the `country`, but return the `code` to `v-model`, we can use the `reduce`
|
||||||
prop to receive only the data that's required.
|
prop to receive only the data that's required.
|
||||||
|
|
||||||
```html
|
```html
|
||||||
<v-select :options="options" :reduce="country => country.code" label="country" />
|
|
||||||
|
<v-select :options="options" :reduce="country => country.code" label="country" />
|
||||||
```
|
```
|
||||||
|
|
||||||
### Deep Nested Values
|
### Deep Nested Values
|
||||||
|
|
||||||
The `reduce` property also works well when you have a deeply nested value:
|
The `reduce` property also works well when you have a deeply nested value:
|
||||||
|
|
||||||
```
|
```
|
||||||
{
|
{
|
||||||
country: 'canada',
|
country: 'canada',
|
||||||
@@ -95,30 +113,42 @@ The `reduce` property also works well when you have a deeply nested value:
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
```
|
```
|
||||||
|
|
||||||
```html
|
```html
|
||||||
<v-select :options="options" :reduce="country => country.meta.code" label="country" />
|
|
||||||
|
<v-select :options="options" :reduce="country => country.meta.code" label="country" />
|
||||||
```
|
```
|
||||||
|
|
||||||
<reducer-nested-value />
|
<reducer-nested-value />
|
||||||
|
|
||||||
## Single/Multiple Selection
|
## Caveats with `reduce`
|
||||||
|
|
||||||
By default, vue-select supports choosing a single value. If you need multiple values, use the
|
The most common issue with `reduce` is when the component displays your _reduced_ _value_ instead of
|
||||||
`multiple` boolean prop, much the same way you would on an HTML `<select>` element. When `multiple`
|
it's _label_. This happens when you supply Vue Select a `value` or `v-model` binding with a reduced_
|
||||||
is true, `v-model` and `value` must be an array.
|
value, but the complete option object is not present in the `options` array.
|
||||||
|
|
||||||
|
|
||||||
```html
|
<ReducedWithNoMatchingOption />
|
||||||
<v-select multiple v-model="selected" :options="['Canada','United States']" />
|
|
||||||
```
|
<<< @/.vuepress/components/ReducedWithNoMatchingOption.vue
|
||||||
<v-select multiple :options="['Canada','United States']" />
|
|
||||||
|
In the example above, the component was supplied with an ID that doesn't exist in the `options`
|
||||||
|
array. When `value` changes, Vue Select searches the supplied options, running each one
|
||||||
|
through `reduce` until the corresponding option is found. When that option doesn't exist, Vue Select
|
||||||
|
will end up displaying the `value` supplied.
|
||||||
|
|
||||||
|
::: warning
|
||||||
|
|
||||||
|
When providing Vue Select with a _reduced_ `value` - the object that the value was reduced from must
|
||||||
|
exist in the `options` array.
|
||||||
|
|
||||||
|
:::
|
||||||
|
|
||||||
## Tagging
|
## Tagging
|
||||||
|
|
||||||
To allow input that's not present within the options, set the `taggable` prop to true.
|
To allow input that's not present within the options, set the `taggable` prop to true.
|
||||||
|
|
||||||
```html
|
```html
|
||||||
|
|
||||||
<v-select taggable multiple />
|
<v-select taggable multiple />
|
||||||
```
|
```
|
||||||
|
|
||||||
@@ -127,6 +157,7 @@ To allow input that's not present within the options, set the `taggable` prop to
|
|||||||
If you want added tags to be pushed to the options array, set `push-tags` to true.
|
If you want added tags to be pushed to the options array, set `push-tags` to true.
|
||||||
|
|
||||||
```html
|
```html
|
||||||
|
|
||||||
<v-select taggable multiple push-tags />
|
<v-select taggable multiple push-tags />
|
||||||
```
|
```
|
||||||
|
|
||||||
@@ -136,10 +167,11 @@ If you want added tags to be pushed to the options array, set `push-tags` to tru
|
|||||||
|
|
||||||
When combining `taggable` with `reduce`, you must define the `createOption` prop. The
|
When combining `taggable` with `reduce`, you must define the `createOption` prop. The
|
||||||
`createOption` function is responsible for defining the structure of the objects that Vue Select
|
`createOption` function is responsible for defining the structure of the objects that Vue Select
|
||||||
will create for you when adding a tag. It should return a value that has the same properties as the
|
will create for you when adding a tag. It should return a value that has the same properties as the
|
||||||
rest of your `options`.
|
rest of your `options`.
|
||||||
|
|
||||||
If you don't define `createOption`, Vue Select will construct a simple object following this structure:
|
If you don't define `createOption`, Vue Select will construct a simple object following this
|
||||||
|
structure:
|
||||||
`{[this.label]: searchText}`. If you're using `reduce`, this is probably not what your options look
|
`{[this.label]: searchText}`. If you're using `reduce`, this is probably not what your options look
|
||||||
like, which is why you'll need to set the function yourself.
|
like, which is why you'll need to set the function yourself.
|
||||||
|
|
||||||
@@ -147,28 +179,29 @@ like, which is why you'll need to set the function yourself.
|
|||||||
|
|
||||||
We have a taggable select for adding books to a collection. We're just concerned about getting the
|
We have a taggable select for adding books to a collection. We're just concerned about getting the
|
||||||
book title added, and our server side code will add the author details in a background process. The
|
book title added, and our server side code will add the author details in a background process. The
|
||||||
user has already selected a book.
|
user has already selected a book.
|
||||||
|
|
||||||
```js
|
```js
|
||||||
const options = [
|
const options = [
|
||||||
{
|
{
|
||||||
title: "HTML5",
|
title: "HTML5",
|
||||||
author: {
|
author: {
|
||||||
firstName: "Remy",
|
firstName: "Remy",
|
||||||
lastName: "Sharp"
|
lastName: "Sharp"
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
|
||||||
];
|
];
|
||||||
```
|
```
|
||||||
|
|
||||||
```html
|
```html
|
||||||
|
|
||||||
<v-select
|
<v-select
|
||||||
taggable
|
taggable
|
||||||
multiple
|
multiple
|
||||||
label="title"
|
label="title"
|
||||||
:options="options"
|
:options="options"
|
||||||
:create-option="book => ({ title: book, author: { firstName: '', lastName: '' } })"
|
:create-option="book => ({ title: book, author: { firstName: '', lastName: '' } })"
|
||||||
:reduce="book => `${book.author.firstName} ${book.author.lastName}`"
|
:reduce="book => `${book.author.firstName} ${book.author.lastName}`"
|
||||||
/>
|
/>
|
||||||
```
|
```
|
||||||
|
|
||||||
|
|||||||
Reference in New Issue
Block a user