mirror of
https://github.com/TandoorRecipes/recipes.git
synced 2026-01-03 21:37:49 -05:00
add ignore_shopping && additional help
This commit is contained in:
58
vue/src/components/Badges/Help.vue
Normal file
58
vue/src/components/Badges/Help.vue
Normal file
@@ -0,0 +1,58 @@
|
||||
<template>
|
||||
<span><i class="mx-1 far fa-question-circle text-muted" @click="this_help.show = !this_help.show" /></span>
|
||||
</template>
|
||||
|
||||
<script>
|
||||
import Vue from "vue"
|
||||
import VueCookies from "vue-cookies"
|
||||
Vue.use(VueCookies)
|
||||
let HELP_COOKIE_NAME = "help_settings"
|
||||
|
||||
export default {
|
||||
name: "HelpBadge",
|
||||
props: {
|
||||
component: { type: String, required: true },
|
||||
},
|
||||
data() {
|
||||
return {
|
||||
help: {},
|
||||
|
||||
default: {
|
||||
show: true,
|
||||
},
|
||||
this_help: undefined,
|
||||
}
|
||||
},
|
||||
mounted() {
|
||||
this.$nextTick(function () {
|
||||
if (this.$cookies.isKey(HELP_COOKIE_NAME)) {
|
||||
this.help = Object.assign({}, this.help, this.$cookies.get(HELP_COOKIE_NAME))
|
||||
}
|
||||
this.this_help = Object.assign({}, this.default, this.help?.[this.component])
|
||||
})
|
||||
},
|
||||
watch: {
|
||||
help: {
|
||||
handler() {
|
||||
this.$cookies.set(HELP_COOKIE_NAME, this.help)
|
||||
},
|
||||
deep: true,
|
||||
},
|
||||
this_help: {
|
||||
handler() {
|
||||
this.help[this.component] = Object.assign({}, this.this_help)
|
||||
this.$cookies.set(HELP_COOKIE_NAME, this.help)
|
||||
},
|
||||
deep: true,
|
||||
},
|
||||
"this_help.show": function () {
|
||||
if (this.this_help.show) {
|
||||
this.$emit("show")
|
||||
} else {
|
||||
this.$emit("hide")
|
||||
}
|
||||
},
|
||||
},
|
||||
methods: {},
|
||||
}
|
||||
</script>
|
||||
@@ -1,5 +1,5 @@
|
||||
<template>
|
||||
<span>
|
||||
<span v-if="!item.ignore_shopping">
|
||||
<b-button class="btn text-decoration-none px-1 border-0" variant="link" :id="`shopping${item.id}`" @click="addShopping()">
|
||||
<i
|
||||
class="fas"
|
||||
|
||||
@@ -34,6 +34,7 @@
|
||||
</td>
|
||||
<td v-else-if="show_shopping" class="text-right text-nowrap">
|
||||
<b-button
|
||||
v-if="!ingredient.food.ignore_shopping"
|
||||
class="btn text-decoration-none fas fa-shopping-cart px-2 user-select-none"
|
||||
variant="link"
|
||||
v-b-popover.hover.click.blur.html.top="{ title: ShoppingPopover, variant: 'outline-dark' }"
|
||||
@@ -43,10 +44,10 @@
|
||||
'text-warning': shopping_status === null,
|
||||
}"
|
||||
/>
|
||||
<span class="px-2">
|
||||
<span v-if="!ingredient.food.ignore_shopping" class="px-2">
|
||||
<input type="checkbox" class="align-middle" v-model="shop" @change="changeShopping" />
|
||||
</span>
|
||||
<on-hand-badge :item="ingredient.food" />
|
||||
<on-hand-badge v-if="!ingredient.food.ignore_shopping" :item="ingredient.food" />
|
||||
</td>
|
||||
</template>
|
||||
</tr>
|
||||
@@ -100,10 +101,10 @@ export default {
|
||||
filtered_list = filtered_list.filter((x) => x.list_recipe == this.recipe_list)
|
||||
}
|
||||
// how many ShoppingListRecipes are there for this recipe?
|
||||
let count_shopping_recipes = [...new Set(filtered_list.map((x) => x.list_recipe))].length
|
||||
let count_shopping_recipes = [...new Set(filtered_list.filter((x) => x.list_recipe))].length
|
||||
let count_shopping_ingredient = filtered_list.filter((x) => x.ingredient == this.ingredient.id).length
|
||||
|
||||
if (count_shopping_recipes >= 1) {
|
||||
if (count_shopping_recipes >= 1 && this.recipe_list) {
|
||||
// This recipe is in the shopping list
|
||||
this.shop = false // don't check any boxes until user selects a shopping list to edit
|
||||
if (count_shopping_ingredient >= 1) {
|
||||
@@ -117,7 +118,7 @@ export default {
|
||||
} else {
|
||||
// there are not recipes in the shopping list
|
||||
// set default value
|
||||
this.shop = !this.ingredient?.food?.food_onhand && !this.ingredient?.food?.recipe
|
||||
this.shop = !this.ingredient?.food?.food_onhand && !this.ingredient?.food?.recipe && !this.ingredient?.food?.ignore_shopping
|
||||
this.$emit("add-to-shopping", { item: this.ingredient, add: this.shop })
|
||||
// mark checked if the food is in the shopping list for this ingredient/recipe
|
||||
if (count_shopping_ingredient >= 1) {
|
||||
@@ -135,7 +136,7 @@ export default {
|
||||
if (this.add_shopping_mode) {
|
||||
// if we are in add shopping mode (e.g. recipe_shopping_modal) start with all checks marked
|
||||
// except if on_hand (could be if recipe too?)
|
||||
this.shop = !this.ingredient?.food?.food_onhand && !this.ingredient?.food?.recipe
|
||||
this.shop = !this.ingredient?.food?.food_onhand && !this.ingredient?.food?.recipe && !this.ingredient?.food?.ignore_shopping
|
||||
}
|
||||
},
|
||||
},
|
||||
|
||||
@@ -1,34 +1,34 @@
|
||||
<template>
|
||||
<div>
|
||||
<b-form-checkbox v-model="new_value">{{label}}</b-form-checkbox>
|
||||
<b-form-checkbox v-model="new_value">{{ label }}</b-form-checkbox>
|
||||
<em v-if="help" class="small text-muted">{{ help }}</em>
|
||||
</div>
|
||||
</template>
|
||||
|
||||
<script>
|
||||
|
||||
export default {
|
||||
name: 'CheckboxInput',
|
||||
props: {
|
||||
field: {type: String, default: 'You Forgot To Set Field Name'},
|
||||
label: {type: String, default: 'Checkbox Field'},
|
||||
value: {type: Boolean, default: false},
|
||||
show_move: {type: Boolean, default: false},
|
||||
show_merge: {type: Boolean, default: false},
|
||||
},
|
||||
data() {
|
||||
return {
|
||||
new_value: undefined,
|
||||
}
|
||||
},
|
||||
mounted() {
|
||||
this.new_value = this.value
|
||||
},
|
||||
watch: {
|
||||
'new_value': function () {
|
||||
this.$root.$emit('change', this.field, this.new_value)
|
||||
name: "CheckboxInput",
|
||||
props: {
|
||||
field: { type: String, default: "You Forgot To Set Field Name" },
|
||||
label: { type: String, default: "Checkbox Field" },
|
||||
value: { type: Boolean, default: false },
|
||||
show_move: { type: Boolean, default: false },
|
||||
show_merge: { type: Boolean, default: false },
|
||||
help: { type: String, default: undefined },
|
||||
},
|
||||
},
|
||||
methods: {
|
||||
}
|
||||
data() {
|
||||
return {
|
||||
new_value: undefined,
|
||||
}
|
||||
},
|
||||
mounted() {
|
||||
this.new_value = this.value
|
||||
},
|
||||
watch: {
|
||||
new_value: function () {
|
||||
this.$root.$emit("change", this.field, this.new_value)
|
||||
},
|
||||
},
|
||||
methods: {},
|
||||
}
|
||||
</script>
|
||||
</script>
|
||||
|
||||
@@ -2,22 +2,26 @@
|
||||
<div>
|
||||
<b-modal :id="'modal_' + id" @hidden="cancelAction">
|
||||
<template v-slot:modal-title>
|
||||
<h4>{{ form.title }}</h4>
|
||||
<h4 class="d-inline">{{ form.title }}</h4>
|
||||
<help-badge v-if="form.show_help" @show="show_help = true" @hide="show_help = false" :component="`GenericModal${form.title}`" />
|
||||
</template>
|
||||
<div v-for="(f, i) in form.fields" v-bind:key="i">
|
||||
<p v-if="visibleCondition(f, 'instruction')">{{ f.label }}</p>
|
||||
<lookup-input v-if="visibleCondition(f, 'lookup')" :form="f" :model="listModel(f.list)" @change="storeValue" />
|
||||
<checkbox-input class="mb-3" v-if="visibleCondition(f, 'checkbox')" :label="f.label" :value="f.value" :field="f.field" />
|
||||
<text-input v-if="visibleCondition(f, 'text')" :label="f.label" :value="f.value" :field="f.field" :placeholder="f.placeholder" />
|
||||
<lookup-input v-if="visibleCondition(f, 'lookup')" :form="f" :model="listModel(f.list)" @change="storeValue" :help="showHelp && f.help" />
|
||||
<checkbox-input class="mb-3" v-if="visibleCondition(f, 'checkbox')" :label="f.label" :value="f.value" :field="f.field" :help="showHelp && f.help" />
|
||||
<text-input v-if="visibleCondition(f, 'text')" :label="f.label" :value="f.value" :field="f.field" :placeholder="f.placeholder" :help="showHelp && f.help" :subtitle="f.subtitle" />
|
||||
<choice-input v-if="visibleCondition(f, 'choice')" :label="f.label" :value="f.value" :field="f.field" :options="f.options" :placeholder="f.placeholder" />
|
||||
<emoji-input v-if="visibleCondition(f, 'emoji')" :label="f.label" :value="f.value" :field="f.field" @change="storeValue" />
|
||||
<file-input v-if="visibleCondition(f, 'file')" :label="f.label" :value="f.value" :field="f.field" @change="storeValue" />
|
||||
<small-text v-if="visibleCondition(f, 'smalltext')" :value="f.value" />
|
||||
</div>
|
||||
|
||||
<template v-slot:modal-footer>
|
||||
<b-button class="float-right mx-1" variant="secondary" v-on:click="cancelAction">{{ $t("Cancel") }}</b-button>
|
||||
<b-button class="float-right mx-1" variant="primary" v-on:click="doAction">{{ form.ok_label }}</b-button>
|
||||
<div class="row w-100 justify-content-end">
|
||||
<div class="col-auto">
|
||||
<b-button class="mx-1" variant="secondary" v-on:click="cancelAction">{{ $t("Cancel") }}</b-button>
|
||||
<b-button class="mx-1" variant="primary" v-on:click="doAction">{{ form.ok_label }}</b-button>
|
||||
</div>
|
||||
</div>
|
||||
</template>
|
||||
</b-modal>
|
||||
</div>
|
||||
@@ -31,7 +35,7 @@ import { getForm, formFunctions } from "@/utils/utils"
|
||||
Vue.use(BootstrapVue)
|
||||
|
||||
import { ApiApiFactory } from "@/utils/openapi/api"
|
||||
import { ApiMixin, StandardToasts, ToastMixin } from "@/utils/utils"
|
||||
import { ApiMixin, StandardToasts, ToastMixin, getUserPreference } from "@/utils/utils"
|
||||
import CheckboxInput from "@/components/Modals/CheckboxInput"
|
||||
import LookupInput from "@/components/Modals/LookupInput"
|
||||
import TextInput from "@/components/Modals/TextInput"
|
||||
@@ -39,10 +43,11 @@ import EmojiInput from "@/components/Modals/EmojiInput"
|
||||
import ChoiceInput from "@/components/Modals/ChoiceInput"
|
||||
import FileInput from "@/components/Modals/FileInput"
|
||||
import SmallText from "@/components/Modals/SmallText"
|
||||
import HelpBadge from "@/components/Badges/Help"
|
||||
|
||||
export default {
|
||||
name: "GenericModalForm",
|
||||
components: { FileInput, CheckboxInput, LookupInput, TextInput, EmojiInput, ChoiceInput, SmallText },
|
||||
components: { FileInput, CheckboxInput, LookupInput, TextInput, EmojiInput, ChoiceInput, SmallText, HelpBadge },
|
||||
mixins: [ApiMixin, ToastMixin],
|
||||
props: {
|
||||
model: { required: true, type: Object },
|
||||
@@ -73,6 +78,7 @@ export default {
|
||||
form: {},
|
||||
dirty: false,
|
||||
special_handling: false,
|
||||
show_help: true,
|
||||
}
|
||||
},
|
||||
mounted() {
|
||||
@@ -83,11 +89,19 @@ export default {
|
||||
buttonLabel() {
|
||||
return this.buttons[this.action].label
|
||||
},
|
||||
showHelp() {
|
||||
if (this.show_help) {
|
||||
return true
|
||||
} else {
|
||||
return undefined
|
||||
}
|
||||
},
|
||||
},
|
||||
watch: {
|
||||
show: function () {
|
||||
if (this.show) {
|
||||
this.form = getForm(this.model, this.action, this.item1, this.item2)
|
||||
|
||||
if (this.form?.form_function) {
|
||||
this.form = formFunctions[this.form.form_function](this.form)
|
||||
}
|
||||
@@ -256,15 +270,33 @@ export default {
|
||||
let type_match = field?.type == field_type
|
||||
let checks = true
|
||||
if (type_match && field?.condition) {
|
||||
if (field.condition?.condition === "exists") {
|
||||
if ((this.item1[field.condition.field] != undefined) === field.condition.value) {
|
||||
checks = true
|
||||
} else {
|
||||
checks = false
|
||||
}
|
||||
const value = this.item1[field?.condition?.field]
|
||||
const preference = getUserPreference(field?.condition?.field)
|
||||
console.log("condition", field?.condition?.condition)
|
||||
switch (field?.condition?.condition) {
|
||||
case "field_exists":
|
||||
if ((value != undefined) === field.condition.value) {
|
||||
checks = true
|
||||
} else {
|
||||
checks = false
|
||||
}
|
||||
break
|
||||
case "preference__array_exists":
|
||||
if (preference?.length > 0 === field.condition.value) {
|
||||
checks = true
|
||||
} else {
|
||||
checks = false
|
||||
}
|
||||
break
|
||||
case "preference_equals":
|
||||
if (preference === field.condition.value) {
|
||||
checks = true
|
||||
} else {
|
||||
checks = false
|
||||
}
|
||||
break
|
||||
}
|
||||
}
|
||||
|
||||
return type_match && checks
|
||||
},
|
||||
},
|
||||
|
||||
@@ -19,6 +19,7 @@
|
||||
@new="addNew"
|
||||
>
|
||||
</generic-multiselect>
|
||||
<em v-if="help" class="small text-muted">{{ help }}</em>
|
||||
</b-form-group>
|
||||
</div>
|
||||
</template>
|
||||
@@ -47,6 +48,7 @@ export default {
|
||||
class_list: { type: String, default: "mb-3" },
|
||||
show_label: { type: Boolean, default: true },
|
||||
clear: { type: Number },
|
||||
help: { type: String, default: undefined },
|
||||
},
|
||||
data() {
|
||||
return {
|
||||
|
||||
@@ -2,6 +2,8 @@
|
||||
<div>
|
||||
<b-form-group v-bind:label="label" class="mb-3">
|
||||
<b-form-input v-model="new_value" type="text" :placeholder="placeholder"></b-form-input>
|
||||
<em v-if="help" class="small text-muted">{{ help }}</em>
|
||||
<small v-if="subtitle" class="text-muted">{{ subtitle }}</small>
|
||||
</b-form-group>
|
||||
</div>
|
||||
</template>
|
||||
@@ -14,7 +16,8 @@ export default {
|
||||
label: { type: String, default: "Text Field" },
|
||||
value: { type: String, default: "" },
|
||||
placeholder: { type: String, default: "You Should Add Placeholder Text" },
|
||||
show_merge: { type: Boolean, default: false },
|
||||
help: { type: String, default: undefined },
|
||||
subtitle: { type: String, default: undefined },
|
||||
},
|
||||
data() {
|
||||
return {
|
||||
|
||||
Reference in New Issue
Block a user