diff --git a/docs/.vuepress/components/InfiniteScroll.vue b/docs/.vuepress/components/InfiniteScroll.vue new file mode 100644 index 0000000..f3fdd8b --- /dev/null +++ b/docs/.vuepress/components/InfiniteScroll.vue @@ -0,0 +1,72 @@ + + + + + diff --git a/docs/.vuepress/config.js b/docs/.vuepress/config.js index da73379..9cff15a 100644 --- a/docs/.vuepress/config.js +++ b/docs/.vuepress/config.js @@ -120,6 +120,7 @@ module.exports = { ['guide/validation', 'Validation'], ['guide/selectable', 'Limiting Selections'], ['guide/pagination', 'Pagination'], + ['guide/infinite-scroll', 'Infinite Scroll'], ['guide/vuex', 'Vuex'], ['guide/ajax', 'AJAX'], ['guide/loops', 'Using in Loops'], diff --git a/docs/guide/infinite-scroll.md b/docs/guide/infinite-scroll.md new file mode 100644 index 0000000..2444581 --- /dev/null +++ b/docs/guide/infinite-scroll.md @@ -0,0 +1,23 @@ +Vue Select doesn't ship with first party support for infinite scroll, but it's possible to implement +by hooking into the `open`, `close`, and `search` events, along with the `filterable` prop, and the +`list-footer` slot. + +Let's break down the example below, starting with the `data`. + +- `observer` - when the component is mounted, a new `IntersectionObserver` will be set here +- `limit` - the number of options to display 'per page' +- `search` - since we've disabled Vue Selects filtering, we'll need to filter options ourselves + +When Vue Select opens, the `open` event is emitted and `onOpen` will be called. We wait for +`$nextTick()` so that the `$ref` we need will exist, then begin observing it for intersection. + +The observer is set to call `infiniteScroll` when the `
  • ` is completely visible within the list. +Some fancy destructuring is done here to get the first `ObservedEntry`, and specifically the +`isIntersecting` & `target` properties. If the `
  • ` is intersecting, we increase the `limit`, and +ensure that the scroll position remains where it was before the list size changed. Again, it's +important to wait for `$nextTick` here so that the DOM elements have been inserted before setting +the scroll position. + + + +<<< @/.vuepress/components/InfiniteScroll.vue diff --git a/src/components/Select.vue b/src/components/Select.vue index 1b21f69..4f4c623 100644 --- a/src/components/Select.vue +++ b/src/components/Select.vue @@ -619,6 +619,10 @@ */ multiple() { this.clearSelection() + }, + + open(isOpen) { + this.$emit(isOpen ? 'open' : 'close'); } },