<template> <div class="autocomplete-container" :class="$vuetify.breakpoint.name"> <v-combobox accesskey="s" aria-label="søkefelt" v-model="select" :loading="loading" :items="items" :search-input.sync="search" item-text="label" :menu-props="{maxHeight: $vuetify.breakpoint.name === 'xs' ? 190 : 500, transition: 'fade-transition', allowOverflow: true}" prepend-inner-icon="search" return-object rounded clearable hide-no-data autofocus auto-select-first no-filter hide-details label="Søk..." solo full-width flat outlined placeholder="Søk her" ref="autocomplete" color="primary" :dense="$vuetify.breakpoint.smAndDown" > <template v-slot:append> <v-divider vertical v-if="!$parent.settings.show_radio_buttons"/> <v-menu allowOverflow: true v-if="!$parent.settings.show_radio_buttons"> <template v-slot:activator="{ on, attrs }"> <v-btn min-width="0px" v-bind="attrs" v-on="on" plain depressed color = "primary" text><span v-if="$vuetify.breakpoint.mdAndUp">{{{"bm,nn":"begge ordbøkene", "bm": "bokmålsordboka (bm)", "nn":"nynorskordboka (nn)"}[$parent.lang]}}</span><v-icon>expand_more</v-icon></v-btn> </template> <v-list> <v-list-item v-for="item in [{label:'begge ordbøkene', tag:'bm,nn'},{label:'bokmålsordboka (bm)', tag:'bm'},{label:'nynorskordboka (nn)', tag:'nn'}]" :key="item.tag" active-class="v-list-item--active" :class="$parent.lang == item.tag ? 'v-list-item--active' : ''" @click="$parent.update_lang_form(item.tag)"> <v-list-item-title >{{ item.label }}</v-list-item-title> </v-list-item> </v-list> </v-menu> <v-divider vertical v-if="$parent.settings.show_pos_select"/> <v-menu allowOverflow: true v-if="$parent.settings.show_pos_select"> <template v-slot:activator="{ on, attrs }"> <v-btn min-width="0px" plain depressed v-bind="attrs" v-on="on" color = "primary" text><span v-if="$vuetify.breakpoint.mdAndUp">{{$parent.pos_selected.label}}</span><v-icon>expand_more</v-icon></v-btn> </template> <v-list> <v-list-item active-class="v-list-item--active" :class="$parent.pos_selected.tag == item.tag ? 'v-list-item--active' : ''" v-for="item in $parent.pos" :key="item.tag" @click="$parent.update_pos(item)"> <v-list-item-title >{{ item.label }}</v-list-item-title> </v-list-item> </v-list> </v-menu><v-divider vertical/> <v-dialog max-width="800px" v-model="settings_dialog" hide-overlay :close-on-content-click="false" origin="bottom" > <template v-slot:activator="{ on, attrs }"> <v-btn v-bind="attrs" v-on="on" min-width="0px" class = "search-field-button" plain depressed color = "primary" text><span v-if="$vuetify.breakpoint.mdAndUp"></span><v-icon>more_vert</v-icon></v-btn> </template> <v-card> <v-toolbar dark color="primary"> <v-toolbar-title>Instillinger</v-toolbar-title><v-spacer></v-spacer> <v-toolbar-items> <v-btn dark text @click="settings_dialog = false" > Tilbakestill </v-btn> <v-btn dark text @click="settings_dialog = false" > Lukk </v-btn> </v-toolbar-items> </v-toolbar> <v-container><v-row><v-col> <v-checkbox v-model="$parent.settings.show_pos_select" label="Vis valg av ordklasse" hide-details ></v-checkbox> <v-checkbox v-model="$parent.settings.fulltext_search" label="Fritekstsøk" hide-details ></v-checkbox> <v-checkbox v-model="$parent.settings.show_radio_buttons" label="Vis radioknapper" hide-details ></v-checkbox> </v-col> </v-row> </v-container> </v-card> </v-dialog> </template> <template v-slot:item="data"> <span class="search-hit"> {{data.item.label}} </span> <span v-if="(get_lang()=='bm,nn')"> ({{["bm","nn","bm,nn"][data.item.lang-1] || ["søker...","ingen treff","avansert søk"][data.item.search]}}) </span> </template> <template slot="no-data"> <div></div> </template> </v-combobox> </div> </template> <script> export default { props: { api: Function, }, data: function() { return { loading: false, items: [], search: null, select: null, suggesting: null, settings_dialog: false } }, watch: { search (val) { const time = Date.now() if (! val) { this.items = [] } else { this.run_query(val, time) } }, select(item) { if (item) { this.items = [] if (typeof item != 'string') { this.suggesting = false this.submit(item) } } } }, methods: { get_lang() { return this.$parent.lang }, run_query(q, time) { this.suggesting = true // Search options while waiting for response var search = 0 if (this.items[0]) { if (this.items[0].time < time) { if (/[_*%|]/.test(q)) { search = 2 } // Whitespace necessary in case option already exists in dropdown this.items.splice(0,1, {q: q, label: q +" ", time: time, search: search}) } } else { this.items.push({q: q, label: q, time: time, search: search}) } let self = this self.api.get('suggest?', {params: {q: q, dict: self.get_lang(), n: 80, scope: 'w', dform: 'int', meta: 'n', wc: self.$parent.pos_selected.tag}}) .then(async (response) => { if (self.$refs.autocomplete.searchInput == q & self.suggesting) { let suggestions = response.data.a.w.map(item => ({q: q, match: item[0], label: item[0], time: time, lang: [item[1]]})) if (/[_*%|]/.test(q)) { suggestions.unshift({q: q, label: q, time: time, search: 2}) } if (!suggestions.length) { self.items = [{q: q, label: q, time: time, search: 1}] } else { self.items = suggestions } } self.loading = false }) }, submit(item) { this.$emit('submit', item) let self = this setTimeout(() => { self.$refs.autocomplete.$refs.input.select() this.items = [] this.suggesting = false }, 1) } }, } </script> <style scoped> .search-hit { font-weight: bold; margin-right: 5px; color: var(--v-primary-base); } .autocomplete-container { padding-left: 10px; padding-right: 10px; } .search-field-button { padding: 0px !important; } </style>