368 lines
9.5 KiB
Vue
368 lines
9.5 KiB
Vue
<template>
|
|
<form class="form" @submit.prevent="sendProduct">
|
|
<div class="cont-col">
|
|
<BFormCheckbox
|
|
id="customSwitch1"
|
|
v-model="form.active"
|
|
class="label"
|
|
>Activo
|
|
<span class="help-text"
|
|
>Desactiva el producto si quieres paralizar temporalmente su
|
|
venta</span
|
|
>
|
|
</BFormCheckbox>
|
|
</div>
|
|
<br />
|
|
<FormHeader
|
|
title="General"
|
|
subtitle="Estos son los datos básicos de un producto. Procura completar el mayor
|
|
número de campos posible. Los campos señalados con asterisco (*) son
|
|
obligatorios, los demás son opcionales. Si el producto o servicio no tiene
|
|
precio asignado, aparecerá 'Consultar precio'."
|
|
/>
|
|
<fieldset class="fieldset">
|
|
<div class="cont">
|
|
<FormInput
|
|
v-model="form.name"
|
|
:value="form.name ? form.name : ''"
|
|
type="text"
|
|
label-text="Nombre"
|
|
required
|
|
@input="form.name = $event"
|
|
/>
|
|
<FormInput
|
|
v-model="form.price"
|
|
:value="form.price ? form.price : ''"
|
|
min="0"
|
|
step="0.01"
|
|
type="number"
|
|
label-text="Precio"
|
|
placeholder="precio + iva"
|
|
@input="form.price = $event"
|
|
/>
|
|
</div>
|
|
<div class="cont">
|
|
<FormInput
|
|
v-model="form.url"
|
|
:value="form.url ? form.url : ''"
|
|
type="text"
|
|
label-text="Url"
|
|
placeholder="enlace directo al producto en tu tienda o web"
|
|
@input="form.url = $event"
|
|
/>
|
|
<small v-if="form.url && !isValidUrl(form.url)" class="error">
|
|
La url no es válida
|
|
</small>
|
|
<br />
|
|
<FormInput
|
|
v-model="form.sku"
|
|
:value="form.sku ? form.sku : ''"
|
|
type="text"
|
|
label-text="SKU o identificador"
|
|
@input="form.sku = $event"
|
|
/>
|
|
</div>
|
|
<div class="cont-col">
|
|
<label for="imagen">Imagen</label>
|
|
<ClientOnly>
|
|
<FormInputImage :image-url="form.image" @change="handleImage" />
|
|
</ClientOnly>
|
|
</div>
|
|
<!-- <div class="cont-col">
|
|
<input
|
|
id="imagen"
|
|
type="file"
|
|
accept="image/*"
|
|
class="imagenInput"
|
|
placeholder="Elige una imagen"
|
|
@change="handleImage"
|
|
/>
|
|
</div> -->
|
|
<div class="cont-col">
|
|
<label for="">Descripción del producto</label>
|
|
<textarea v-model="form.description" class="textarea" type="text" />
|
|
</div>
|
|
<div class="cont">
|
|
<FormInput
|
|
v-model="form.stock"
|
|
:value="form.stock ? form.stock : ''"
|
|
type="number"
|
|
label-text="Stock"
|
|
@input="form.stock = $event"
|
|
/>
|
|
<FormInput
|
|
v-model="form.discount"
|
|
:value="form.discount ? form.discount : ''"
|
|
step="0.01"
|
|
type="number"
|
|
label-text="Descuento"
|
|
@input="form.discount = $event"
|
|
/>
|
|
</div>
|
|
<div class="cont-col">
|
|
<FormInput
|
|
v-model="form.identifiers"
|
|
:value="form.identifiers ? form.identifiers : ''"
|
|
label-text="Identificador único"
|
|
@input="form.identifiers = $event"
|
|
/>
|
|
</div>
|
|
</fieldset>
|
|
<fieldset class="fieldset">
|
|
<FormHeader
|
|
title="Categorías"
|
|
subtitle="Estos datos ayudan a que tu producto sea encontrado por los clientes.
|
|
Procura completar el mayor número de campos posibles. Los campos
|
|
señalados con asterisco (*) son obligatorios, los demás son opcionales."/>
|
|
|
|
<div class="cont-col">
|
|
<label for="category">Categoría*</label>
|
|
<BFormInput
|
|
id="category"
|
|
v-model="form.category"
|
|
autocomplete="off"
|
|
list="my-list-id"
|
|
/>
|
|
<datalist id="my-list-id">
|
|
<option v-for="(choice, index) in categories" :key="`category-${index}`">
|
|
{{ choice }}
|
|
</option>
|
|
</datalist>
|
|
<!-- <b-form-select required v-model="form.category" name="" id="category">
|
|
<option disabled value="">Categoría</option>
|
|
<option
|
|
v-for="(category, key) in categories"
|
|
:key="key"
|
|
:value="category"
|
|
>
|
|
{{ category }}
|
|
</option>
|
|
</b-form-select> -->
|
|
</div>
|
|
<div class="cont-col">
|
|
<label for="tags-basic">Palabras clave</label>
|
|
<BFormTags
|
|
v-model="form.tags"
|
|
placeholder="Añade palabras clave (moda, complementos...)"
|
|
input-id="tags-basic"
|
|
/>
|
|
</div>
|
|
<div class="cont-col">
|
|
<label for="tags-basic">Atributos</label>
|
|
<BFormTags
|
|
v-model="form.attributes"
|
|
placeholder="Añade características del producto (talla, color...)"
|
|
input-id="tags-basic"
|
|
/>
|
|
</div>
|
|
</fieldset>
|
|
<FormHeader title="Envío" />
|
|
<fieldset class="fieldset">
|
|
<div class="cont-col">
|
|
<label for="">Condiciones de envío</label>
|
|
<p class="help-text">
|
|
Aquí podrás indicar las condiciones de envío específicas para este
|
|
producto. Si no lo rellenas se mostrarán las opciones por defecto que
|
|
puedes editar en tu formulario de edición de la Cooperativa en el
|
|
apartado condiciones de envío.
|
|
</p>
|
|
<textarea v-model="form.shipping_terms" class="textarea" type="text" />
|
|
</div>
|
|
<div class="cont-col">
|
|
<FormInput
|
|
v-model="form.shipping_cost"
|
|
:value="form.shipping_cost ? form.shipping_cost : ''"
|
|
step="0.01"
|
|
type="number"
|
|
label-text="Gastos de envío"
|
|
placeholder="ej. 4,50"
|
|
@input="form.shipping_cost = $event"
|
|
/>
|
|
</div>
|
|
</fieldset>
|
|
<div class="submit-btn" align="center">
|
|
<SubmitButton text="guardar" image-url="" />
|
|
</div>
|
|
</form>
|
|
</template>
|
|
|
|
<script>
|
|
import FormInputImage from './FormInputImage.vue'
|
|
import dataProcessing from '~/utils/dataProcessing'
|
|
export default {
|
|
components: { FormInputImage },
|
|
props: {
|
|
productForm: {
|
|
type: Object,
|
|
default: () => ({}),
|
|
},
|
|
},
|
|
emits: ['send'],
|
|
data() {
|
|
return {
|
|
form: {
|
|
sku: '',
|
|
name: '',
|
|
description: '',
|
|
image: null,
|
|
url: '',
|
|
price: '',
|
|
shipping_cost: '',
|
|
shipping_terms: '',
|
|
source: 'MANUAL',
|
|
active: true,
|
|
discount: '',
|
|
stock: null,
|
|
category: '',
|
|
tags: [],
|
|
attributes: [],
|
|
identifiers: '',
|
|
},
|
|
// tagsArray: ['tag1', 'tag2', 'tag3', 'tag33'],
|
|
categories: [
|
|
'Alimentación',
|
|
'Agricultura ',
|
|
'Energía',
|
|
'Hogar y jardín',
|
|
'Moda y Textil',
|
|
'Salud y Cuidados',
|
|
'Movilidad y Mensajería',
|
|
'Ocio y Deporte',
|
|
'Turismo y Gastronomía',
|
|
'Cultura, Educación y Medios',
|
|
'Tecnología y Servicios Digitales',
|
|
'Economía Circular y Reparación',
|
|
'Finanzas Éticas y Seguros',
|
|
'Servicios Profesionales',
|
|
],
|
|
}
|
|
},
|
|
|
|
async mounted() {
|
|
await this.getAllCategories()
|
|
if (this.productForm && Object.keys(this.productForm).length > 0) {
|
|
Object.keys(this.form).forEach((key) => {
|
|
this.form[key] = this.productForm[key]
|
|
})
|
|
}
|
|
},
|
|
|
|
methods: {
|
|
isValidUrl: dataProcessing.isValidUrl,
|
|
async getAllCategories() {
|
|
const config = useRuntimeConfig()
|
|
const data = await $fetch(`/products/all_categories/`,{
|
|
baseURL: config.public.baseURL,
|
|
method: 'GET',
|
|
|
|
})
|
|
this.categories = data
|
|
},
|
|
parseForm() {
|
|
const formData = new FormData()
|
|
|
|
Object.keys(this.form).forEach((key) => {
|
|
if ((key === 'tags') | (key === 'attributes')) {
|
|
formData.append(key, JSON.stringify(this.form[key]))
|
|
} else if (this.form[key] || this.form[key] === '')
|
|
formData.append(key, this.form[key])
|
|
})
|
|
if (typeof formData.get('image') === 'string') {
|
|
formData.delete('image')
|
|
}
|
|
//console.log('FormData:', formData)
|
|
return formData
|
|
},
|
|
|
|
async handleImage(e) {
|
|
this.form.image = e
|
|
},
|
|
|
|
sendProduct() {
|
|
const formData = this.parseForm()
|
|
//TODO: review with Diego. I changed formaData with this.form
|
|
this.$emit('send', formData)
|
|
},
|
|
},
|
|
}
|
|
</script>
|
|
|
|
<style lang="scss" scoped>
|
|
.form {
|
|
@include desktop {
|
|
width: 40%;
|
|
}
|
|
@include tablet {
|
|
width: 60%;
|
|
}
|
|
@include mobile {
|
|
width: 90%;
|
|
}
|
|
|
|
.imagenInput {
|
|
font-size: $s;
|
|
}
|
|
|
|
label, .label {
|
|
color: $color-primary;
|
|
font-weight: $medium;
|
|
font-size: $s;
|
|
display: block;
|
|
}
|
|
|
|
.textarea {
|
|
width: 100%;
|
|
background-color: $color-grey-inputs;
|
|
border: 1px solid $color-grey-inputs-border;
|
|
border-radius: 4px;
|
|
padding: 10px 5px;
|
|
display: block;
|
|
margin-bottom: 10px;
|
|
}
|
|
}
|
|
.fieldset {
|
|
margin-top: 40px;
|
|
margin-bottom: 40px;
|
|
}
|
|
.cont {
|
|
display: flex;
|
|
justify-content: space-between;
|
|
@include mobile {
|
|
flex-direction: column;
|
|
}
|
|
}
|
|
|
|
.cont-col {
|
|
margin: 15px 0;
|
|
display: flex;
|
|
flex-direction: column;
|
|
|
|
h3 {
|
|
color: $color-navy;
|
|
font-size: $m;
|
|
margin: 10px 0 15px 0;
|
|
}
|
|
}
|
|
.submit-btn {
|
|
margin-top: 20px;
|
|
}
|
|
.help-text {
|
|
text-align: left;
|
|
font-size: $s;
|
|
text-align: justify;
|
|
font-weight: $regular;
|
|
color: $color-primary;
|
|
font-family: $font-secondary;
|
|
margin-bottom: 20px;
|
|
margin-top: 6px;
|
|
|
|
a {
|
|
text-decoration: underline;
|
|
color: $color-greytext;
|
|
}
|
|
}
|
|
.error {
|
|
color: $color-error;
|
|
}
|
|
</style>
|