Merge pull request #44 from AlexisNP/bugfix/empty-search-categories

Fixed empty categories
This commit is contained in:
AlexisNP
2024-11-22 17:54:37 +01:00
committed by GitHub

View File

@@ -13,12 +13,13 @@ import { useMagicKeys, useScroll, useStorage, whenever } from "@vueuse/core"
import { computed, ref, watch } from "vue" import { computed, ref, watch } from "vue"
import { searchUnifier, type SearchMode } from "../SearchMode" import { searchUnifier, type SearchMode } from "../SearchMode"
import { PhClockClockwise, PhClockCounterClockwise, PhMagnifyingGlass } from "@phosphor-icons/vue" import { PhCaretDown, PhClockClockwise, PhClockCounterClockwise, PhMagnifyingGlass } from "@phosphor-icons/vue"
import { import {
ComboboxAnchor, ComboboxAnchor,
ComboboxInput, ComboboxInput,
ComboboxPortal, ComboboxPortal,
ComboboxRoot, ComboboxRoot,
ComboboxTrigger,
VisuallyHidden VisuallyHidden
} from "radix-vue" } from "radix-vue"
@@ -113,7 +114,7 @@ const searchResults = computed<(Character | CalendarEvent)[]>(() => {
} }
hitCategories = selectedCategories.value.every((selectedCat) => { hitCategories = selectedCategories.value.every((selectedCat) => {
return allCategories.includes(selectedCat as Category) return allCategories.findIndex((c) => c.name === selectedCat.name) !== -1
}) })
return (hitTitle || hitDesc) && hitCategories return (hitTitle || hitDesc) && hitCategories
@@ -203,28 +204,54 @@ watch([currentPage, selectedEntity], () => {
}) })
// Compute categories based on current selectedEntity // Compute categories based on current selectedEntity
const currentCategories = computed(() => { const { data: resCategories } = await useFetch("/api/calendars/categories/query")
return [] const currentCategories = ref<Category[]>(resCategories.value?.data as Category[])
})
const selectedCategories = ref<(Category)[]>([]) const selectedCategories = ref<(Category)[]>([])
const categoryFilterOpened = ref<boolean>(false) const categoryFilterOpened = ref<boolean>(false)
const searchCategory = ref<string>("") const searchCategory = ref<string>("")
const filteredCategories = computed(() => const filteredCategories = computed(() => {
currentCategories.value.filter((i) => !selectedCategories.value.includes(i)) // Display original data
) if (!currentCategories.value) return []
// If current categories are selected, ignore them
if (!searchCategory.value) return currentCategories.value.filter((i) => !selectedCategories.value.includes(i))
// If we also have a query to filter them by, do that
return currentCategories.value.filter((i) => {
return !selectedCategories.value.includes(i) && i.name.toLocaleLowerCase().includes(searchCategory.value.toLocaleLowerCase())
})
})
// Reactivity rules for category searches
const categoryInput = ref(null)
const categoryInputValue = ref<string>("")
const { focused: categoryInputFocused } = useFocus(categoryInput)
watch(categoryInputFocused, (isFocused) => {
categoryFilterOpened.value = isFocused
})
/** /**
* Handles the category selections from the TagInput component * Handles the category selections from the TagInput component
* *
* @param e Radix Change Event * @param e Radix Change Event
*/ */
function handleCategorySelect(e: (Category)) { function handleCategorySelect(e: Category) {
if (typeof e === "string") { searchCategory.value = ""
searchCategory.value = "" selectedCategories.value.push(e)
selectedCategories.value.push(e)
if (filteredCategories.value.length === 0) {
categoryFilterOpened.value = false
} }
}
/**
* Removes a category from selection from the TagInput component
*/
function handleCategoryUnselect(e: Category) {
selectedCategories.value.splice(selectedCategories.value.findIndex(sc => sc.name === e.name), 1)
if (filteredCategories.value.length === 0) { if (filteredCategories.value.length === 0) {
categoryFilterOpened.value = false categoryFilterOpened.value = false
@@ -265,7 +292,7 @@ function handleCategorySelect(e: (Category)) {
</span> </span>
</div> </div>
<div class="flex items-center justify-between"> <div class="flex items-center justify-between gap-8">
<div> <div>
<UiToggleGroup <UiToggleGroup
v-model="selectedEntity" v-model="selectedEntity"
@@ -276,18 +303,18 @@ function handleCategorySelect(e: (Category)) {
<UiToggleGroupItem value="events" aria-label="Uniquement les évènements"> <UiToggleGroupItem value="events" aria-label="Uniquement les évènements">
{{ $t('entity.calendar.event.namePlural') }} {{ $t('entity.calendar.event.namePlural') }}
</UiToggleGroupItem> </UiToggleGroupItem>
<UiToggleGroupItem value="characters" aria-label="Uniquement les personnages"> <!-- Not used for now -->
<!-- <UiToggleGroupItem value="characters" aria-label="Uniquement les personnages">
{{ $t('entity.character.namePlural') }} {{ $t('entity.character.namePlural') }}
</UiToggleGroupItem> </UiToggleGroupItem> -->
</UiToggleGroup> </UiToggleGroup>
</div> </div>
<div class="flex items-center gap-1"> <div class="grow flex justify-end items-center gap-1">
<UiTagsInput class="px-0 gap-0 w-72"> <UiTagsInput class="grow px-0 gap-y-1 w-80">
<div class="flex gap-2 flex-wrap items-center px-3"> <div v-if="selectedCategories.length > 0" class="flex gap-2 flex-wrap items-center px-3">
<UiTagsInputItem v-for="item in selectedCategories" :key="item.id" :value="item.name"> <UiTagsInputItem v-for="item in selectedCategories" :key="item.id" :value="item.name">
<UiTagsInputItemText class="capitalize" /> <UiTagsInputItemText class="capitalize cursor-pointer" @click="handleCategoryUnselect(item)" />
<UiTagsInputItemDelete />
</UiTagsInputItem> </UiTagsInputItem>
</div> </div>
@@ -295,18 +322,23 @@ function handleCategorySelect(e: (Category)) {
v-model="selectedCategories" v-model="selectedCategories"
v-model:open="categoryFilterOpened" v-model:open="categoryFilterOpened"
v-model:searchTerm="searchCategory" v-model:searchTerm="searchCategory"
class="w-full" class="grow flex items-center gap-y-1 pr-2"
> >
<ComboboxAnchor as-child> <ComboboxAnchor as-child>
<ComboboxInput :placeholder="$t('entity.category.namePlural')" as-child> <ComboboxInput :placeholder="$t('entity.category.namePlural')" as-child>
<UiTagsInputInput <UiTagsInputInput
class="w-full px-3" ref="categoryInput"
:class="selectedCategories.length > 0 ? 'mt-2' : ''" v-model="categoryInputValue"
class="min-w-16 px-3"
@keydown.enter.prevent @keydown.enter.prevent
/> />
</ComboboxInput> </ComboboxInput>
</ComboboxAnchor> </ComboboxAnchor>
<ComboboxTrigger>
<PhCaretDown size="16" />
</ComboboxTrigger>
<ComboboxPortal :to="'#searchForm'"> <ComboboxPortal :to="'#searchForm'">
<UiCommandList <UiCommandList
position="popper" position="popper"
@@ -317,11 +349,11 @@ function handleCategorySelect(e: (Category)) {
<UiCommandGroup> <UiCommandGroup>
<UiCommandItem <UiCommandItem
v-for="cat in filteredCategories" v-for="cat in filteredCategories"
:key="cat" :key="cat.name"
:value="cat" :value="cat"
@select.prevent="handleCategorySelect(cat)" @select.prevent="handleCategorySelect(cat)"
> >
{{ capitalize(cat) }} {{ capitalize(cat.name) }}
</UiCommandItem> </UiCommandItem>
</UiCommandGroup> </UiCommandGroup>
</UiCommandList> </UiCommandList>