Vue Select — Custom Search and Positioning

Image for post
Image for post
Photo by vision webagency on Unsplash

To make dropdowns easier, we can use the Vue Select plugin to add the dropdown.

It can do much more than the select element.

In this article, we’ll look at how to use the vue-select package to make more complex dropdowns.

Customizing Keydown Behaviour

We can customize keydown behavior to do what we want.

For example, we can write:

<template>
<div>
<v-select no-drop taggable multiple :select-on-key-codes="[188, 13]"/>
</div>
</template>
<script>
export default {
data: () => ({})
};
</script>

to add the selections when we press the comma key in addition to the return key.

188 is the keycode for the comma key and 13 is the return key.

We can append what we want to the selection after a selection is made.

For example, we can write:

<template>
<v-select taggable multiple no-drop :map-keydown="handlers" placeholder="enter an email"/>
</template>
<script>
export default {
methods: {
handlers: (map, vm) => ({
...map,
50: e => {
e.preventDefault();
if (e.key === "@" && vm.search.length > 0) {
vm.search = `${vm.search}@hotmail.com`;
}
}
})
}
};
</script>

We append the @hotmail.com suffix to our selection once we type the @ sign and we typed in something to the input box before that.

Popper.js Integration

Vue Select integrates with Popper.js.

For example, we can write:

<template>
<div style="margin-top: 6em">
<v-select :options="countries" append-to-body :calculate-position="withPopper"/>
</div>
</template>
<script>
import { createPopper } from "@popperjs/core";
export default {
data: () => ({ countries: ["Canada", "United States"], placement: "top" }),
methods: {
withPopper(dropdownList, component, { width }) {
dropdownList.style.width = width;
const popper = createPopper(component.$refs.toggle, dropdownList, {
placement: this.placement,
modifiers: [
{
name: "offset",
options: {
offset: [0, -1]
}
},
{
name: "toggleClass",
enabled: true,
phase: "write",
fn({ state }) {
component.$el.classList.toggle(
"drop-up",
state.placement === "top"
);
}
}
]
});
return () => popper.destroy();
}
}
};
</script>

We added the withPopper method to position the dropdown with the modifiers property to let us change the position.

If state.placement is 'top' , then we set the dropdown to drop up instead.

The this.placement variable sets the placement of the dropdown.

If we set the placement to 'bottom' , then we get the dropdown to display at the bottom as usual.

Filtering with Fuse.js

Fuse.js makes filtering the dropdown entries easier for us.

For example, we can write:

<template>
<v-select :filter="fuseSearch" :options="books" :getOptionLabel="option => option.title">
<template #option="{ author, title }">
{{ title }}
<br>
<cite>{{ author.firstName }} {{ author.lastName }}</cite>
</template>
</v-select>
</template>
<script>
import Fuse from "fuse.js";
export default {
data() {
return {
books: [
{
title: "book",
author: {
firstName: "james",
lastName: "smith"
}
},
{
title: "book 2",
author: {
firstName: "jones",
lastName: "smith"
}
},
{
title: "javascript for dummies",
author: {
firstName: "may",
lastName: "wong"
}
}
]
};
},
methods: {
fuseSearch(options, search) {
const fuse = new Fuse(options, {
keys: ["title", "author.firstName", "author.lastName"],
shouldSort: true
});
return search.length
? fuse.search(search).map(({ item }) => item)
: fuse.list;
}
}
};
</script>

to add the fuseSearch method to let us do the search.

The method has the options array with all the options.

The search parameter is our search query.

The keys have the properties that we want to search by.

shouldSort lets us set whether we sort the items or not.

We then return the results by using the fuse.search method to do the search.

It’ll search all the properties automatically since we specified them in the keys array.

If the query is empty,. then we return the whole list with fuse.list .

Conclusion

We can customize various behaviors with the Vue Select dropdown.

The dropdown position can be changed, and it integrates with various libraries.

Written by

Web developer. Subscribe to my email list now at http://jauyeung.net/subscribe/. Email me at hohanga@gmail.com

Get the Medium app

A button that says 'Download on the App Store', and if clicked it will lead you to the iOS App store
A button that says 'Get it on, Google Play', and if clicked it will lead you to the Google Play store