Uname: Linux webm012.cluster130.gra.hosting.ovh.net 5.15.167-ovh-vps-grsec-zfs-classid #1 SMP Tue Sep 17 08:14:20 UTC 2024 x86_64
Software: Apache
PHP version: 8.0.30 [ PHP INFO ] PHP os: Linux
Server Ip: 145.239.37.162
Your Ip: 216.73.216.190
User: dreampi (1009562) | Group: users (100)
Safe Mode: OFF
Disable Function:
_dyuweyrj4,_dyuweyrj4r,dl

name : Catalog.vue
<template>
  <div id="amelia-booking-wrap" class="am-wrap" ref="catalogContainer">

    <div id="am-catalog" v-if="!empty">

      <!-- Categories -->
      <transition name="fade">
        <div v-show="fetchedCatalog && showCatalog && !loadingCacheCatalogData">

          <!-- Categories Label -->
          <div v-if="formLabels.categories.visibility" class="am-catalog-headline">
            <h3 :style="{color: formColors.formTextColor, fontWeight: 500}">
              {{ formLabels.categories.value || $root.labels.categories }}
            </h3>
          </div>

          <el-row :gutter="24">
            <el-col
              v-for="category in options.entities.categories"
              v-if="showCategoryInCatalog(category) && getServicesForCategory(category).length > 0"
              :key="category.id"
              :lg="columnsLg"
              :md="12"
              :sm="12"
            >
              <div
                class="am-category"
                :style="{backgroundColor: formColors.formBackgroundColor}"
                @click="selectCategory(category.id)"
              >
                <!-- Category Name -->
                <div class="am-category-title" :style="{color: formColors.formTextColor}">
                  {{ category.name }}
                </div>

                <!-- Number Of Services -->
                <span v-if="formLabels.services_lower.visibility" :style="{color: formColors.formTextColor}">
                  {{ `${formLabels.services_lower.value || capitalizeFirstLetter($root.labels.services_lower)}: ${getServicesForCategory(category).length}` }}
                </span>

                <!-- Services Images -->
                <div v-if="formParts.service_images_thumbs.visibility" class="am-category-services-thumbs">
                  <img
                    v-for="(service, index) in getServicesForCategory(category)"
                    v-if="index < 3"
                    :key="service.id"
                    :src="pictureLoad(service, false)"
                    @error="imageLoadError(service, false)"
                  >

                  <!-- Invisible Services Count -->
                  <span v-if="getServicesForCategory(category).length > 3" :style="{color: formColors.formTextColor}">
                    +{{ getInvisibleServicesCount(category) }}
                  </span>
                  <!-- /Invisible Services Count -->
                </div>
                <!-- /Services Images -->
              </div>
            </el-col>
          </el-row>
        </div>
      </transition>

      <!-- Category -->
      <category
        v-if="showCategory"
        :forms-data="forms.catalogForm"
        :passedCategory="passCategory()"
        :passedResponseEntities="responseEntities"
        :passedEntities="options.entities"
        :passedEntitiesRelations="options.entitiesRelations"
        @showAllCategories="showAllCategories"
      >
      </category>


      <!-- Spinner -->
      <div class="am-spinner am-section" v-show="!fetchedCatalog || loadingCacheCatalogData">
        <img class="svg-catalog am-spin" :src="$root.getUrl + 'public/img/oval-spinner.svg'"/>
        <img class="svg-catalog am-hourglass" :src="$root.getUrl + 'public/img/hourglass.svg'"/>
      </div>

    </div>

    <div v-else class="am-no-services">
      <img :src="$root.getUrl+'public/img/am-empty-booking.svg'" style="margin-top: 10px;">
      <h1>{{$root.labels.oops}}</h1>
      <h3>{{$root.labels.no_services_employees}}</h3>
      <p>{{$root.labels.add_services_employees}}</p>
      <a href="https://wpamelia.com/services-and-categories/" rel="nofollow">
        {{$root.labels.add_services_url}}
      </a>
      <span style="font-size:14px">{{$root.labels.and}}</span>
      <a href="https://wpamelia.com/employees/" rel="nofollow">
        {{$root.labels.add_employees_url}}
      </a>
    </div>

    <div v-if="showCatalog && $root.licence.isLite && $root.settings.general.backLink.enabled" class="am-lite-footer">
      <a
        rel="nofollow"
        class="am-lite-footer-link"
        :href="$root.settings.general.backLink.url"
        target="_blank"
      >
        {{ $root.settings.general.backLink.label }}
      </a>
    </div>

  </div>
</template>

<script>
import formsCustomizationMixin from '../../../../assets/js/common/mixins/formsCustomizationMixin'
import imageMixin from '../../../js/common/mixins/imageMixin'
import Category from '../catalog/Category'
import entitiesMixin from '../../../js/common/mixins/entitiesMixin'
import cacheMixin from '../../../js/frontend/mixins/cacheMixin'
import helperMixin from '../../../js/backend/mixins/helperMixin'
import marketingMixin from '../../../js/frontend/mixins/marketingMixin'

export default {
  name: 'catalogForm',

  mixins: [cacheMixin, imageMixin, entitiesMixin, helperMixin, formsCustomizationMixin],

  data () {
    return {
      empty: false,
      categoryId: '',
      marketing: {
        service: null,
        employee: null,
        location: null,
        category: null,
        package: null,
        payment: null
      },
      fetchedCatalog: false,
      responseEntities: {
        taxes: [],
        categories: [],
        employees: [],
        locations: [],
        services: []
      },
      options: {
        availableEntitiesIds: {
          categories: [],
          employees: [],
          locations: [],
          services: []
        },
        entitiesRelations: {},
        entities: {
          employees: [],
          locations: []
        }
      },
      showCatalog: true,
      showCategory: false,
      columnsLg: 6,
      forms: {},
      formColors: {},
      formLabels: {},
      formParts: {}
    }
  },

  created () {
    this.forms = this.getTranslatedForms('catalogForm')

    if (this.$root.settings.customization.forms) {
      this.formColors = this.$root.settings.customization.useGlobalColors[this.$options.name] ? this.$root.settings.customization.globalColors : this.forms.catalogForm.catalogListForm.globalSettings
    } else {
      this.formColors = this.defaultFormsData.catalogForm.catalogListForm.globalSettings
    }

    this.formLabels = this.$root.settings.customization.forms ? this.forms.catalogForm.catalogListForm.labels : this.defaultFormsData.catalogForm.catalogListForm.labels
    this.formParts = this.$root.settings.customization.forms ? this.forms.catalogForm.catalogListForm.parts : this.defaultFormsData.catalogForm.catalogListForm.parts

    window.addEventListener('resize', this.handleResize)
  },

  mounted () {
    this.setCacheData('amelia-app-booking' + this.$root.shortcodeData.counter, false)

    this.inlineCatalogSVG()

    let $this = this

    this.fetchEntities(function (success) {
      if (success) {
        $this.fetchedEntities(success)
      }
    }, {
      types: ['locations', 'employees', 'categories', 'custom_fields', 'packages', 'taxes'],
      isFrontEnd: true,
      isPanel: false
    })

    // Customization hook
    if ('beforeCatalogLoaded' in window) {
      window.beforeCatalogLoaded()
    }
  },

  updated () {
    this.handleResize()
  },

  methods: {
    cacheDataProcessing () {
      if (this.loadingCacheBookingData) {
        this.categoryId = this.cacheData.request.passedCategoryId

        this.selectCategory(this.categoryId)

        this.loadingCacheCatalogData = false
      }
    },

    fetchedEntities () {
      if (this.options.entities.services.length === 0 || this.options.entities.employees.length === 0) this.empty = true

      this.fetchedCatalog = true

      this.cacheDataProcessing()
    },

    getInvisibleServicesCount (category) {
      let services = this.getServicesForCategory(category)

      return services.length > 3 ? services.length - 3 : ''
    },

    selectCategory (categoryId) {
      this.$nextTick(() => {
        if (this.$refs && this.$refs.catalogContainer) {
          this.$refs.catalogContainer.scrollIntoView({ behavior: 'smooth', block: 'start', inline: 'nearest' })
        }
      })

      this.categoryId = categoryId
      this.showCatalog = false
      this.showCategory = true

      // Customization hook
      if ('afterSelectCatalogCategory' in window) {
        window.afterSelectCatalogCategory(this.passCategory())
      }

      if (marketingMixin.hasAmeliaTracking(this.$root.marketing, this.categoryId)) {
        this.marketing.category = this.getCategoryById(this.categoryId)

        marketingMixin.trackAmeliaData(this, this.$root.marketing, 'appointment', 'SelectCategory')
      }
    },

    showAllCategories () {
      this.categoryId = ''
      this.showCatalog = true
      this.showCategory = false
    },

    // Show category if have at least one employee in one of the services
    showCategoryInCatalog (category) {
      let oneServiceHaveEmployee = false

      for (let i = 0; i < category.serviceList.length; i++) {
        if (oneServiceHaveEmployee === true) { break }

        oneServiceHaveEmployee = this.getServiceProviders(category.serviceList[i].id).length > 0
      }

      return category.serviceList.length > 0 && oneServiceHaveEmployee
    },

    getServicesForCategory (category) {
      return this.options.entities.services.filter(service => service.categoryId === category.id)
    },

    passCategory () {
      let category = Object.assign({}, this.options.entities.categories.find(category => category.id === this.categoryId))
      category.serviceList = this.getServicesForCategory(category)

      return category
    },

    handleResize () {
      let amContainer = document.getElementById('amelia-app-booking' + this.$root.shortcodeData.counter)
      let amContainerWidth = amContainer.offsetWidth
      if (amContainerWidth < 670) {
        this.columnsLg = 12
      }
    },

    inlineCatalogSVG () {
      let inlineSVG = require('inline-svg')
      inlineSVG.init({
        svgSelector: 'img.svg-catalog',
        initClass: 'js-inlinesvg'
      })
    }
  },

  components: {
    Category
  }

}
</script>
© 2026 GrazzMean-Shell