first steps to advanced search

This commit is contained in:
vabene1111
2025-01-03 23:14:16 +01:00
parent dc58b42f68
commit b8db54d198
9 changed files with 254 additions and 43 deletions

View File

@@ -45,11 +45,12 @@ import {ApiApi, ApiRecipeListRequest, Keyword, Recipe, RecipeOverview} from "@/o
import {homePageCols} from "@/utils/breakpoint_utils";
import {useI18n} from "vue-i18n";
import {DateTime} from "luxon";
import {tr} from "vuetify/locale";
//TODO mode ideas "last year/month/cooked long ago"
const props = defineProps(
{
mode: {type: String as PropType<'recent' | 'new' | 'keyword' | 'rating'>, required: true},
mode: {type: String as PropType<'recent' | 'new' | 'keyword' | 'rating' | 'random'>, required: true},
skeletons: {type: Number, default: 0},
}
)
@@ -68,6 +69,8 @@ const title = computed(() => {
switch (props.mode) {
case 'recent':
return t('Recently_Viewed')
case 'random':
return t('Random Recipes')
case 'new':
return t('New')
case 'rating':
@@ -87,6 +90,8 @@ const icon = computed(() => {
switch (props.mode) {
case 'recent':
return 'fa-solid fa-eye'
case 'random':
return 'fa-solid fa-dice'
case 'new':
return 'fa-solid fa-calendar-alt'
case 'rating':
@@ -116,9 +121,11 @@ function loadRecipes() {
switch (props.mode) {
case 'recent':
// TODO implement correct parameter
requestParameters.numRecent = 16
break;
case 'random':
requestParameters.random = 'true'
break;
case 'new':
requestParameters._new = 'true'
break;

View File

@@ -91,21 +91,20 @@ const searchResults = computed(() => {
let searchResults = [] as Array<SearchResult>
if (searchQuery.value != '' && searchQuery.value != null) {
// TODO add link to advanced search once it exists
//searchResults.push({name: searchQuery.value, icon: 'fas fa-search', suffix: 'Advanced Search'} as SearchResult)
flatRecipes.value.filter(fr => fr.name.toLowerCase().includes(searchQuery.value.toLowerCase())).slice(0, 10).forEach(r => {
searchResults.push({name: r.name, image: r.image, recipeId: r.id} as SearchResult)
searchResults.push({name: r.name, image: r.image, recipeId: r.id, type: "recipe"} as SearchResult)
})
if (searchResults.length < 3) {
asyncSearchResults.value.slice(0, 5).forEach(r => {
if (searchResults.findIndex(x => x.recipeId == r.id) == -1) {
searchResults.push({name: r.name, image: r.image, recipeId: r.id})
searchResults.push({name: r.name, image: r.image, recipeId: r.id, type: "recipe"})
}
})
}
searchResults.push({name: searchQuery.value, icon: 'fas fa-search', type: "link_advanced_search"} as SearchResult)
} else {
// show first 5 recipes by default
@@ -212,10 +211,17 @@ function cardVariant(index: number) {
function goToSelectedRecipe(index: number) {
dialog.value = false
let searchResult = searchResults.value[index]
console.log('going to', searchResult.recipeId)
if (searchResult.recipeId != null) {
router.push({name: 'view_recipe', params: {'id': searchResult.recipeId}})
if (searchResult.type == 'link_advanced_search') {
router.push({name: 'view_search', query: {'query': searchQuery.value}})
} else {
console.log('going to', searchResult.recipeId)
if (searchResult.recipeId != null) {
router.push({name: 'view_recipe', params: {'id': searchResult.recipeId}})
}
}
}
</script>

View File

@@ -19,7 +19,7 @@
:on-create="createObject"
:createOption="props.allowCreate"
:delay="300"
:object="true"
:object="props.object"
:valueProp="itemValue"
:label="itemLabel"
:searchable="true"
@@ -72,6 +72,7 @@ const props = defineProps({
mode: {type: String as PropType<'single' | 'multiple' | 'tags'>, default: 'single'},
appendToBody: {type: Boolean, default: false},
object: {type: Boolean, default: true},
allowCreate: {type: Boolean, default: false},

View File

@@ -0,0 +1,46 @@
<template>
<model-editor-base
:loading="loading"
:dialog="dialog"
@save="saveObject"
@delete="deleteObject"
@close="emit('close')"
:is-update="isUpdate()"
:is-changed="editingObjChanged"
:model-class="modelClass"
:object-name="editingObjName()">
<v-card-text>
<v-form :disabled="loading">
Coming Soon
</v-form>
</v-card-text>
</model-editor-base>
</template>
<script setup lang="ts">
import {onMounted, PropType} from "vue";
import {CustomFilter} from "@/openapi";
import {useModelEditorFunctions} from "@/composables/useModelEditorFunctions";
import ModelEditorBase from "@/components/model_editors/ModelEditorBase.vue";
const props = defineProps({
item: {type: {} as PropType<CustomFilter>, required: false, default: null},
itemId: {type: [Number, String], required: false, default: undefined},
dialog: {type: Boolean, default: false}
})
const emit = defineEmits(['create', 'save', 'delete', 'close'])
const {setupState, deleteObject, saveObject, isUpdate, editingObjName, loading, editingObj, editingObjChanged, modelClass} = useModelEditorFunctions<CustomFilter>('CustomFilter', emit)
onMounted(() => {
setupState(props.item, props.itemId, {})
})
</script>
<style scoped>
</style>