]> BookStack Code Mirror - bookstack/blob - resources/js/components/dropdown-search.js
Updated tinymce code block handling to help prevent breaking history states
[bookstack] / resources / js / components / dropdown-search.js
1 import {debounce} from "../services/util";
2
3 class DropdownSearch {
4
5     setup() {
6         this.elem = this.$el;
7         this.searchInput = this.$refs.searchInput;
8         this.loadingElem = this.$refs.loading;
9         this.listContainerElem = this.$refs.listContainer;
10
11         this.localSearchSelector = this.$opts.localSearchSelector;
12         this.url = this.$opts.url;
13
14         this.elem.addEventListener('show', this.onShow.bind(this));
15         this.searchInput.addEventListener('input', this.onSearch.bind(this));
16
17         this.runAjaxSearch = debounce(this.runAjaxSearch, 300, false);
18     }
19
20     onShow() {
21         this.loadList();
22     }
23
24     onSearch() {
25         const input = this.searchInput.value.toLowerCase().trim();
26         if (this.localSearchSelector) {
27             this.runLocalSearch(input);
28         } else {
29             this.toggleLoading(true);
30             this.runAjaxSearch(input);
31         }
32     }
33
34     runAjaxSearch(searchTerm) {
35         this.loadList(searchTerm);
36     }
37
38     runLocalSearch(searchTerm) {
39         const listItems = this.listContainerElem.querySelectorAll(this.localSearchSelector);
40         for (let listItem of listItems) {
41             const match = !searchTerm || listItem.textContent.toLowerCase().includes(searchTerm);
42             listItem.style.display = match ? 'flex' : 'none';
43             listItem.classList.toggle('hidden', !match);
44         }
45     }
46
47     async loadList(searchTerm = '') {
48         this.listContainerElem.innerHTML = '';
49         this.toggleLoading(true);
50
51         try {
52             const resp = await window.$http.get(this.getAjaxUrl(searchTerm));
53             this.listContainerElem.innerHTML = resp.data;
54         } catch (err) {
55             console.error(err);
56         }
57
58         this.toggleLoading(false);
59         if (this.localSearchSelector) {
60             this.onSearch();
61         }
62     }
63
64     getAjaxUrl(searchTerm = null) {
65         if (!searchTerm) {
66             return this.url;
67         }
68
69         const joiner = this.url.includes('?') ? '&' : '?';
70         return `${this.url}${joiner}search=${encodeURIComponent(searchTerm)}`;
71     }
72
73     toggleLoading(show = false) {
74         this.loadingElem.style.display = show ? 'block' : 'none';
75     }
76
77 }
78
79 export default DropdownSearch;