Browse Source

V8-7024 : nouvelle page mon abonnement

Vincent 10 months ago
parent
commit
0e1a46ca27

+ 10 - 0
assets/css/theme.scss

@@ -51,3 +51,13 @@
   background-color: rgb(var(--v-theme-x-create-btn)) !important;
   color: rgb(var(--v-theme-on-x-create-btn)) !important;
 }
+
+.theme-artist{
+  background-color: rgb(var(--v-theme-artist)) !important;
+  color: rgb(var(--v-theme-on-surface)) !important;
+}
+
+.theme-school{
+  background-color: rgb(var(--v-theme-school)) !important;
+  color: rgb(var(--v-theme-on-primary)) !important;
+}

+ 116 - 0
components/Pages/Subscription/Card.vue

@@ -0,0 +1,116 @@
+<template>
+    <v-card elevation="2" outlined shaped class="card" :class="{['border-'+color] : true}">
+      <span v-if="extraHeader" class="extraBorder" :class="'extraBorder-'+color">{{extraHeader}}</span>
+
+      <!-- Titre -->
+      <v-card-title class="title" :class="{['margin-sup'] : !extraHeader}">
+        {{title}}
+      </v-card-title>
+
+      <v-card-subtitle class="subtitle">
+        {{subTitle}}
+        <slot name="card.subTitle" />
+      </v-card-subtitle>
+
+      <!-- Texte -->
+      <v-card-text>
+        <PagesSubscriptionList
+          :elements="list"
+          :color="color" />
+      </v-card-text>
+
+      <!-- Actions -->
+      <v-card-actions class="mb-3">
+        <slot name="card.action" />
+      </v-card-actions>
+
+    </v-card>
+
+
+</template>
+
+<script setup lang="ts">
+
+const props = defineProps({
+  title: {
+    type: String,
+    required: true,
+  },
+  subTitle: {
+    type: String,
+    required: false,
+  },
+  extraHeader: {
+    type: String,
+    required: false,
+  },
+  color: {
+    type: String,
+    required: true,
+  },
+  list: {
+    type: Array,
+    required: true,
+  },
+})
+</script>
+
+<style scoped lang="scss">
+
+  .card{
+    border-width: 1px;
+    border-top-width: 4px;
+    height: 100%;
+
+    .title{
+      padding-top: 10px;
+      white-space: normal;
+    }
+    .subtitle{
+      text-transform: uppercase;
+      font-weight: bold;
+      font-size: 1.25rem;
+      opacity: unset;
+    }
+//1280 1670
+    :deep(.v-btn){
+      padding: 10px;
+      width: 100%;
+      @media (min-width:1280px) and (max-width: 1670px) {
+        letter-spacing: 0px;
+        font-size: 11px;
+      }
+    }
+  }
+
+  .extraBorder{
+    text-align: center;
+    text-transform: uppercase;
+    margin: auto;
+    border-radius: 0px 0px 5px 5px;
+    width: 90%;
+    padding: 2px 10px 2px 10px;
+    font-weight: bold;
+    display: block;
+  }
+  .card.border-primary{
+    border-color: rgb(var(--v-theme-primary));
+  }
+  .card.border-artist{
+    border-color: rgb(var(--v-theme-artist));
+  }
+  .card.border-school{
+    border-color: rgb(var(--v-theme-school));
+  }
+  .extraBorder.extraBorder-artist{
+    background: rgb(var(--v-theme-artist));
+  }
+  .extraBorder.extraBorder-school{
+    background: rgb(var(--v-theme-school));
+    color:#fff;
+  }
+
+  .margin-sup{
+    margin-top: 30px;
+  }
+</style>

+ 36 - 0
components/Pages/Subscription/List.vue

@@ -0,0 +1,36 @@
+<template>
+  <ul>
+    <li v-for="li in elements">
+      <v-icon
+        class="check"
+        :color="color"
+        icon="fa-solid fa-check"
+        size="large"
+      ></v-icon>
+      <span class="pl-2">{{li}}</span>
+    </li>
+  </ul>
+</template>
+
+<script setup lang="ts">
+const props = defineProps({
+  elements: {
+    type: Array,
+    required: true,
+  },
+  color: {
+    type: String,
+    required: true,
+  },
+})
+</script>
+
+<style scoped lang="scss">
+  ul{
+    list-style: none;
+    .check{
+      font-size: 15px;
+      font-weight: bold;
+    }
+  }
+</style>

+ 8 - 0
config/theme.ts

@@ -34,6 +34,8 @@ interface Theme {
     'on-warning': string
     info: string
     'on-info': string
+    artist:string
+    school:string
 
     // Special cases
     // TODO: voir ceux dont on peut se passer
@@ -91,6 +93,9 @@ export const lightTheme: Theme = {
 
     'x-create-btn': '#f39c12',
     'on-x-create-btn': '#ffffff',
+
+    artist: '#fac20a',
+    school: '#1893bf',
   },
 }
 
@@ -143,5 +148,8 @@ export const darkTheme: Theme = {
 
     'x-create-btn': '#f39c12',
     'on-x-create-btn': '#ffffff',
+
+    artist: '#fac20a',
+    school: '#1893bf',
   },
 }

+ 3 - 0
lang/fr.json

@@ -1,4 +1,7 @@
 {
+  "opentalent_options": "Les options Opentalent",
+  "opentalent_offer": "Les offres Opentalent",
+  "service_detail": "Détails des services",
   "my_settings_page": "Mes paramètres",
   "allow_report_message": "Je souhaite recevoir les rapports d'envoi des emails que j'envoie",
   "my-settings_breadcrumbs": "Mes paramètres",

+ 6 - 0
models/OnlineRegistration/RegistrationStatus.ts

@@ -1,5 +1,7 @@
 import { Str, Uid } from 'pinia-orm/dist/decorators'
 import ApiResource from '~/models/ApiResource'
+import {IdField} from "~/models/decorators";
+import {Num} from "pinia-orm/decorators";
 
 /**
  * AP2i Model : File
@@ -12,6 +14,10 @@ export default class RegistrationStatus extends ApiResource {
   @Uid()
   declare id: number | string | null
 
+  @IdField()
+  @Num(0, { notNullable: true })
+  declare accessId: number
+
   @Str('')
   declare status: 'PENDING' | 'NEGOTIABLE' | 'ACCEPTED' | 'DENIED' | null
 }

+ 2 - 0
models/Organization/MobytUserStatus.ts

@@ -1,5 +1,6 @@
 import { Bool, Num, Uid } from 'pinia-orm/dist/decorators'
 import ApiResource from '~/models/ApiResource'
+import {IdField} from "~/models/decorators";
 
 /**
  * The Mobyt user status of an organization
@@ -12,6 +13,7 @@ export default class MobytUserStatus extends ApiResource {
   @Uid()
   declare id: number | string | null
 
+  @IdField()
   @Num(0, { notNullable: true })
   declare organizationId: number
 

+ 358 - 540
pages/subscription.vue

@@ -5,91 +5,49 @@ Page 'Mon abonnement'
 -->
 <template>
   <LayoutContainer>
-    <v-col cols="12" sm="12" md="12">
       <v-expansion-panels v-model="openedPanels" :multiple="true">
-        <UiExpansionPanel title="informations" icon="fas fa-info">
+        <UiExpansionPanel :title="$t('subscription_page')" icon="fas fa-info">
           <v-container fluid class="container">
             <v-row>
-              <v-table>
-                <tbody>
-                  <tr>
-                    <td v-if="smAndUp">{{ $t('client_id') }}</td>
-                    <td class="py-2">
-                      <h5
-                        v-if="!smAndUp"
-                        class="text-decoration-underline py-2"
-                      >
-                        {{ $t('client_id') }}
-                      </h5>
-                      <span>{{
-                        dolibarrAccount ? dolibarrAccount.clientNumber : '-'
-                      }}</span>
-                    </td>
-                  </tr>
-                  <tr>
-                    <td v-if="smAndUp">{{ $t('version') }}</td>
-                    <td class="py-2">
-                      <h5
-                        v-if="!smAndUp"
-                        class="text-decoration-underline py-2"
-                      >
-                        {{ $t('version') }}
-                      </h5>
-                      <span>{{
-                        dolibarrAccount ? $t(dolibarrAccount.product) : '-'
-                      }}</span>
-                    </td>
-                  </tr>
-                  <tr v-if="dolibarrAccount && dolibarrAccount.contract">
-                    <td v-if="smAndUp">{{ $t('services') }}</td>
-                    <td class="py-2">
-                      <h5
-                        v-if="!smAndUp"
-                        class="text-decoration-underline py-2"
-                      >
-                        {{ $t('services') }}
-                      </h5>
-                      <div
-                        v-for="line in dolibarrAccount.contract.lines"
-                        :key="line.id"
-                      >
-                        {{ line.serviceLabel }} - {{ $t('until') }} :
-                        {{ $d(line.dateEnd) }}
-                      </div>
-                    </td>
-                  </tr>
-                  <tr v-if="ability.can('manage', 'texto')">
-                    <td v-if="smAndUp">{{ $t('remaining_sms_credit') }}</td>
-                    <td class="py-2">
-                      <h5
-                        v-if="!smAndUp"
-                        class="text-decoration-underline py-2"
-                      >
-                        {{ $t('remaining_sms_credit') }}
-                      </h5>
-                      <span
-                        v-if="
-                          !mobytPending &&
-                          mobytStatus !== null &&
-                          mobytStatus.active
-                        "
-                      >
+              <v-col cols="12" lg="6" sm="12">
+                {{ $t('version') }} : <strong>{{ dolibarrAccount ? $t(dolibarrAccount.product) : '-' }}</strong>
+              </v-col>
+              <v-col cols="12" lg="6" sm="12">
+                {{ $t('client_id') }} : {{ dolibarrAccount ? dolibarrAccount.clientNumber : '-' }}
+              </v-col>
+            </v-row>
+          </v-container>
+        </UiExpansionPanel>
+
+        <UiExpansionPanel :title="$t('service_detail')" icon="fas fa-info"
+                          v-if="dolibarrAccount && dolibarrAccount.contract"
+        >
+          <v-container fluid class="container">
+            <v-row>
+              <v-col cols="12"
+                     lg="12"
+                     v-for="line in dolibarrAccount.contract.lines"
+                     :key="line.id"
+              >
+                <strong>{{ line.serviceLabel }}</strong> - {{ $t('until') }} : {{ $d(line.dateEnd) }}
+              </v-col>
+
+              <v-col cols="12" lg="12" v-if="ability.can('manage', 'texto')">
+                <strong>{{ $t('remaining_sms_credit') }}</strong> -
+                <span v-if="!mobytPending && mobytStatus !== null && mobytStatus.active">
                         {{
-                          mobytStatus.money.toLocaleString($i18n.locale, {
-                            style: 'currency',
-                            currency: 'EUR',
-                          })
-                        }}
+                    mobytStatus.money.toLocaleString($i18n.locale, {
+                      style: 'currency',
+                      currency: 'EUR',
+                    })
+                  }}
                         {{
-                          i18n.t('convert_price_to_sms', {
-                            nb_sms: mobytStatus.amount,
-                          })
-                        }}
-                      </span>
-                    </td>
-                  </tr>
-                </tbody>
-              </v-table>
+                    i18n.t('convert_price_to_sms', {
+                      nb_sms: mobytStatus.amount,
+                    })
+                  }}
+                </span>
+              </v-col>
             </v-row>
           </v-container>
         </UiExpansionPanel>
@@ -103,538 +61,398 @@ Page 'Mon abonnement'
             <v-row>
               <v-table v-if="dolibarrAccount !== null">
                 <thead>
-                  <tr>
-                    <th>{{ $t('reference') }}</th>
-                    <th>{{ $t('date') }}</th>
-                    <th>{{ $t('taxExcludedAmount') }}</th>
-                    <th>{{ $t('status') }}</th>
-                  </tr>
+                <tr>
+                  <th>{{ $t('reference') }}</th>
+                  <th>{{ $t('date') }}</th>
+                  <th>{{ $t('taxExcludedAmount') }}</th>
+                  <th>{{ $t('status') }}</th>
+                </tr>
                 </thead>
                 <tbody>
-                  <tr v-for="bill in dolibarrAccount.bills" :key="bill.id">
-                    <td>{{ bill.ref }}</td>
-                    <td>{{ $d(bill.date) }}</td>
-                    <td>
-                      {{
-                        bill.taxExcludedAmount.toLocaleString($i18n.locale, {
-                          style: 'currency',
-                          currency: 'EUR',
-                        })
-                      }}
-                    </td>
-                    <td>
-                      {{ bill.paid === true ? $t('paid') : $t('unpaid') }}
-                    </td>
-                  </tr>
+                <tr v-for="bill in dolibarrAccount.bills" :key="bill.id">
+                  <td>{{ bill.ref }}</td>
+                  <td>{{ $d(bill.date) }}</td>
+                  <td>
+                    {{
+                      bill.taxExcludedAmount.toLocaleString($i18n.locale, {
+                        style: 'currency',
+                        currency: 'EUR',
+                      })
+                    }}
+                  </td>
+                  <td>
+                    {{ bill.paid === true ? $t('paid') : $t('unpaid') }}
+                  </td>
+                </tr>
                 </tbody>
               </v-table>
             </v-row>
           </v-container>
         </UiExpansionPanel>
 
-        <UiExpansionPanel title="more_features" icon="fas fa-plus">
-          <v-container id="products-section" :fluid="true" class="container">
-            <v-row>
-              <!-- Opentalent Artist Premium -->
-              <v-col
-                v-if="organizationProfile.isArtistProduct"
-                :cols="colWidth"
-              >
-                <v-row>
-                  {{ $t('PRODUCT_ARTIST_PREMIUM') }}
-                </v-row>
-                <v-row class="align-end">
-                  <nuxt-img src="/images/Opentalent_Artist.png" />
-                </v-row>
-                <v-row>
-                  <p>
-                    {{ $t('get_more_functionalities_with_version') }}
-                    <b>{{ $t('PRODUCT_ARTIST_PREMIUM') }}</b>
-                  </p>
-
-                  <!-- Cmf member -->
-                  <div v-if="organizationProfile.isCmf">
-                    <p>
-                      <b
-                        >{{
-                          i18n.t('for_only_x_eur_ttc_by_month', {
-                            price: formatCurrency(7.5, 'EUR'),
-                          })
-                        }}&nbsp;*</b
-                      >
-                    </p>
-                    <div>
-                      <i
-                        >*&nbsp;{{
-                          i18n.t('yearly_paid_giving_x_eur_ttc_per_year', {
-                            price: formatCurrency(90.0, 'EUR'),
-                          })
-                        }}</i
-                      >
-                    </div>
-                    <div>
-                      <i
-                        >{{ $t('only_for_cmf_members') }} ({{
-                          i18n.t('public_price_x_ttc_a_year', {
-                            price: formatCurrency(216.0, 'EUR'),
-                          })
-                        }})</i
-                      >
-                    </div>
-                  </div>
+        <UiExpansionPanel :title="$t('opentalent_offer')" icon="fas fa-plus" v-if="!organizationProfile.isManagerProduct">
+          <v-container fluid class="container">
+            <v-row class="offer_title" v-if="!md && mdAndUp && !organizationProfile.isSchool">
+              <v-col cols="12" :lg="organizationProfile.isArtistPremiumProduct ? 3 : 6" sm="12">
+                <span class="theme-artist">Pour les orchestres, chorales, compagnies et troupes artistiques</span>
+              </v-col>
+              <v-col cols="12" :lg="organizationProfile.isArtistPremiumProduct ? 3 : 5" sm="12" :offset="organizationProfile.isArtistPremiumProduct ? 0 : 1">
+                <span class="theme-school">Pour les établissements d'enseignements artistiques*</span>
+              </v-col>
+            </v-row>
 
-                  <!-- Not a cmf member -->
-                  <div v-else>
-                    <p>
-                      <b
-                        >{{
-                          i18n.t('for_only_x_eur_ttc_by_month', {
-                            price: formatCurrency(18.0, 'EUR'),
-                          })
-                        }}&nbsp;*</b
-                      >
-                    </p>
-                    <p>
-                      <i>
-                        *&nbsp;{{
-                          i18n.t('yearly_paid_giving_x_eur_ttc_per_year', {
-                            price: formatCurrency(216.0, 'EUR'),
-                          })
-                        }}
-                      </i>
-                    </p>
+            <v-row class="card-container">
+              <v-col lg="3" sm="12" md="6" v-if="organizationProfile.isArtistProduct">
+                <PagesSubscriptionCard
+                class="artistCard"
+                title="Logiciel Artist Standard"
+                :extraHeader="organizationProfile.isArtistProduct ? 'Votre version' : false"
+                color="artist"
+                :list="listCheck.artist"
+              >
+                <template #card.subTitle>
+                  <div class="priceBlock">
+                    <span class="price">{{formatCurrency(11, 'EUR')}}</span> TTC/mois
                   </div>
-
-                  <p class="mt-3">
-                    <a
-                      :href="
-                        runtimeConfig.public.fileStorageBaseUrl +
-                        '/Fiche_produit/Fiche_produit_Opentalent_Artist.pdf'
-                      "
-                      target="_blank"
-                    >
-                      {{ $t('product_sheet') }}
-                      {{ $t('PRODUCT_ARTIST_PREMIUM') }}
-                    </a>
-                  </p>
-
-                  <p v-if="organizationProfile.isCmf" class="mt-3">
-                    <a
-                      :href="
-                        runtimeConfig.public.fileStorageBaseUrl +
-                        '/Bon_de_commande/Opentalent_Artist_CMF.pdf'
-                      "
-                      target="_blank"
-                    >
-                      <b>{{ $t('download_cmf_order_form') }}</b>
-                    </a>
-                  </p>
-                  <p v-else class="mt-3">
-                    <a
-                      :href="
-                        runtimeConfig.public.fileStorageBaseUrl +
-                        '/Bon_de_commande/Opentalent_Artist_Public.pdf'
-                      "
-                      target="_blank"
-                    >
-                      <b>{{ $t('download_order_form') }}</b>
-                    </a>
-                  </p>
-                </v-row>
+                </template>
+                <template #card.action>
+                  <v-btn
+                    class="theme-artist btn"
+                    href="https://logiciels.opentalent.fr/opentalent-artist"
+                    target="_blank"
+                  >
+                    En savoir plus <i class="fa-solid fa-greater-than small"></i>
+                  </v-btn>
+                </template>
+              </PagesSubscriptionCard>
               </v-col>
 
-              <!-- Opentalent School Premium -->
-              <v-col v-if="organizationProfile.isArtist" :cols="colWidth">
-                <v-row>
-                  {{ $t('PRODUCT_SCHOOL') }}
-                </v-row>
-                <v-row class="align-end">
-                  <nuxt-img src="/images/Opentalent_School.png" />
-                </v-row>
-                <v-row>
-                  <p>
-                    {{ $t('switch_to_version') }}
-                    <b>{{ $t('PRODUCT_SCHOOL_PREMIUM') }}</b>
-                    {{ $t('and_benefit') }} :
-                  </p>
-
-                  <ul class="mb-2">
-                    <li>{{ $t('of_accounts_for_teachers_and_students') }}</li>
-                    <li>{{ $t('of_a_complete_website') }}</li>
-                  </ul>
-
-                  <!-- Cmf member -->
-                  <div v-if="organizationProfile.isCmf">
-                    <p>
-                      <b
-                        >{{
-                          i18n.t('starting_from_x_eur_ttc_per_month', {
-                            price: formatCurrency(30.5, 'EUR'),
-                          })
-                        }}&nbsp;*</b
-                      >
-                    </p>
-                    <div>
-                      <i
-                        >*
-                        {{
-                          i18n.t('yearly_paid_giving_x_eur_ttc_per_year', {
-                            price: formatCurrency(366.0, 'EUR'),
-                          })
-                        }}</i
-                      >
-                    </div>
-                    <div>
-                      <i>{{
-                        i18n.t('version_x_up_to_x_students', {
-                          product: $t('PRODUCT_SCHOOL_PREMIUM'),
-                          max_students: '69',
-                        })
-                      }}</i>
-                    </div>
-                    <div>
-                      <i>{{ $t('excluding_license_and_training_fees') }}.</i>
-                    </div>
-                    <div>
-                      <i
-                        >{{ $t('only_for_cmf_members') }} ({{
-                          i18n.t('public_price_x_ttc_a_year', {
-                            price: formatCurrency(607.2, 'EUR'),
-                          })
-                        }})</i
-                      >
+              <v-col lg="3" sm="12" md="6" v-if="organizationProfile.isArtist">
+                <PagesSubscriptionCard
+                  class="artistCard"
+                  title="Logiciel Artist Premium*"
+                  :extraHeader="organizationProfile.isArtistPremiumProduct ? 'Votre version' : '1 mois d\'essai offert'"
+                  color="artist"
+                  :list="listCheck.artistPremium"
+                >
+                  <template #card.subTitle>
+                    <div class="priceBlock">
+                      <span class="price">{{organizationProfile.isCmf ? formatCurrency(7.5, 'EUR') : formatCurrency(18.0, 'EUR')}}</span> TTC/mois
                     </div>
-                  </div>
-                  <!-- Not cmf member -->
-                  <div v-else>
-                    <p>
-                      {{
-                        i18n.t('starting_from_x_eur_ttc_per_month', {
-                          price: formatCurrency(50.6, 'EUR'),
-                        })
-                      }}&nbsp;*
-                    </p>
-                    <div>
-                      <i
-                        >*&nbsp;{{
-                          i18n.t('yearly_paid_giving_x_eur_ttc_per_year', {
-                            price: formatCurrency(607.2, 'EUR'),
-                          })
-                        }}</i
-                      >
-                    </div>
-                    <div>
-                      <i>{{
-                        i18n.t('version_x_up_to_x_students', {
-                          product: $t('PRODUCT_SCHOOL_PREMIUM'),
-                          max_students: '69',
-                        })
-                      }}</i>
-                    </div>
-                    <div>
-                      <i>{{ $t('excluding_license_and_training_fees') }}.</i>
-                    </div>
-                  </div>
-
-                  <p class="mt-4">
-                    <a
-                      :href="
-                        runtimeConfig.public.fileStorageBaseUrl +
-                        '/Fiche_produit/Fiche_produit_Opentalent_School.pdf'
-                      "
-                      target="_blank"
-                    >
-                      {{ $t('product_sheet') }} {{ $t('PRODUCT_SCHOOL') }}
-                    </a>
-                  </p>
-
-                  <p>
-                    {{ $t('contact_us_at') }}
-                    <a href="tel:+33972126017">0 972 126 017</a>,
-                    {{ $t('or_by_mail_at') }}
-                    <a href="mailto:contact@opentalent.fr"
-                      >contact@opentalent.fr</a
-                    >
-                  </p>
-                </v-row>
+                  </template>
+                  <template #card.action>
+                    <v-row >
+                      <v-col cols="12" v-if="!organizationProfile.isArtistPremiumProduct && (accessProfileStore.isAdmin || accessProfileStore.isCaMember)">
+                        <v-btn
+                          class="btn trialBtn"
+                          href="https://logiciels.opentalent.fr/opentalent-artist"
+                          target="_blank"
+                        >
+                          Essayer la version premium <i class="fa-solid fa-greater-than small"></i>
+                        </v-btn>
+                      </v-col>
+                      <v-col cols="12" v-if="!organizationProfile.isArtistPremiumProduct && (accessProfileStore.isAdmin || accessProfileStore.isCaMember)">
+                        <v-btn
+                          class="theme-artist btn"
+                          href="https://logiciels.opentalent.fr/opentalent-artist"
+                          target="_blank"
+                        >
+                          Souscrire à l'offre <i class="fa-solid fa-greater-than small"></i>
+                        </v-btn>
+                      </v-col>
+                      <v-col cols="12">
+                        <v-btn
+                          class="theme-artist btn"
+                          href="https://logiciels.opentalent.fr/opentalent-artist"
+                          target="_blank"
+                        >
+                          En savoir plus <i class="fa-solid fa-greater-than small"></i>
+                        </v-btn>
+                      </v-col>
+                      <v-col cols="12">
+                          <span class="special_conditions">
+                          *Convient aux petites écoles sans besoins spécifiques de gestion pédagogique, de facturation, etc.
+                          Pour une solution complète optez pour Opentalent School
+                        </span>
+                      </v-col>
+                    </v-row>
+                  </template>
+                </PagesSubscriptionCard>
               </v-col>
 
-              <!-- SMS -->
-              <v-col :cols="colWidth">
-                <v-row>
-                  {{ $t('sms') }}
-                </v-row>
-                <v-row class="align-end">
-                  <nuxt-img src="/images/sms.png" :height="140" :width="175" />
-                </v-row>
-                <v-row>
-                  <p>
-                    <b
-                      >{{ $t('send_sms') }}
-                      {{ $t('to_your_members_from_app') }}</b
-                    >
-                  </p>
-
-                  <!-- Cmf member -->
-                  <div v-if="organizationProfile.isCmf">
-                    <p>
-                      <b
-                        >{{
-                          i18n.t('starting_from_x_eur_ttc_per_sms', {
-                            price: formatCurrency(0.11, 'EUR'),
-                          })
-                        }}&nbsp;*</b
-                      >
-                    </p>
-                    <p>
-                      <i
-                        >*&nbsp;{{ i18n.t('for_x_sms', { amount: '5000' }) }}</i
-                      >
-                    </p>
-
-                    <p>
-                      <b>
-                        <a
-                          :href="
-                            runtimeConfig.public.fileStorageBaseUrl +
-                            '/Bon_de_commande/Achat_SMS_CMF.pdf'
-                          "
+              <v-col lg="3" sm="12" md="6" :offset="!md && mdAndUp ? (organizationProfile.isSchool ? 4 : (organizationProfile.isArtistPremiumProduct ? 0 : 2)) : 0">
+                <PagesSubscriptionCard
+                  class="schoolCard"
+                  :title="!organizationProfile.isSchool ? 'Logiciel School Standard / Premium' : (
+                    organizationProfile.isSchoolPremiumProduct ? 'Logiciel School Premium' : 'Logiciel School Standard'
+                  )"
+                  :subTitle="!organizationProfile.isSchool ? 'Sur devis' : ''"
+                  :extraHeader="organizationProfile.isSchool ? 'Votre version' : false"
+                  color="school"
+                  :list="listCheck.school"
+                >
+                  <template #card.action>
+                    <v-row>
+                      <v-col cols="12">
+                        <v-btn
+                          class="theme-school btn"
+                          href="https://logiciels.opentalent.fr/opentalent-school"
                           target="_blank"
                         >
-                          {{ i18n.t('download_cmf_order_form') }}
-                        </a>
-                      </b>
-                    </p>
-                  </div>
-                  <!-- Not cmf member -->
-                  <div v-else>
-                    <p>
-                      <b
-                        >{{
-                          i18n.t('starting_from_x_eur_ttc_per_sms', {
-                            price: formatCurrency(0.13, 'EUR'),
-                          })
-                        }}&nbsp;*</b
-                      >
-                    </p>
-                    <p>
-                      <i
-                        >*&nbsp;{{ i18n.t('for_x_sms', { amount: '5000' }) }}</i
-                      >
-                    </p>
+                          En savoir plus <i class="fa-solid fa-greater-than small"></i>
+                        </v-btn>
+                      </v-col>
+                      <v-col cols="12">
+                          <span class="special_conditions">
+                          *Extranet disponible uniquement dans la version Opentalent School Premium
+                        </span>
+                      </v-col>
+                    </v-row>
+                  </template>
+                </PagesSubscriptionCard>
+              </v-col>
+            </v-row>
+          </v-container>
+        </UiExpansionPanel>
 
-                    <p>
-                      <a
-                        :href="
+        <UiExpansionPanel :title="$t('opentalent_options')" icon="fas fa-plus">
+          <v-container fluid class="container card-container">
+            <v-row cols="12" >
+              <v-col lg="3" sm="12" md="6">
+                <PagesSubscriptionCard
+                  class="optionsCard"
+                  title="SMS"
+                  sub-title="Option payante"
+                  color="primary"
+                  :list="listCheck.sms"
+                >
+                  <template #card.action>
+                    <v-btn
+                      class="theme-primary btn"
+                      :href="
                           runtimeConfig.public.fileStorageBaseUrl +
-                          '/Bon_de_commande/Achat_SMS_Public.pdf'
+                          (organizationProfile.isCmf ? '/Bon_de_commande/Achat_SMS_CMF.pdf' : '/Bon_de_commande/Achat_SMS_Public.pdf')
                         "
-                        target="_blank"
-                      >
-                        <b>{{ $t('download_order_form') }}</b>
-                      </a>
-                    </p>
-                  </div>
-                </v-row>
+                      target="_blank"
+                    >
+                      acheter des credits SMS <i class="fa-solid fa-greater-than small"></i>
+                    </v-btn>
+                  </template>
+                </PagesSubscriptionCard>
               </v-col>
 
-              <!-- Custom domain -->
-              <v-col :cols="colWidth">
-                <v-row>
-                  {{ $t('website') }}
-                </v-row>
-                <v-row class="align-end">
-                  <nuxt-img src="/images/nom_de_domaine.png" :height="160" />
-                </v-row>
-                <v-row>
-                  <v-col>
-                    <p>
-                      <b>{{
-                        i18n.t(
-                          'get_your_own_domain_and_up_to_five_emails_for_only_x_eur_ttc_per_year',
-                          { price: formatCurrency(46.8, 'EUR') },
-                        )
-                      }}</b>
-                    </p>
-
-                    <p>{{ $t('example') }} :</p>
-
-                    <table>
-                      <tbody>
-                        <tr>
-                          <td class="pa-2" style="width: 190px">
-                            {{ $t('domain_name') }}&nbsp;:
-                          </td>
-                          <td>
-                            <i>{{ $t('dummy_domain_name') }}</i>
-                          </td>
-                        </tr>
-                        <tr>
-                          <td class="pa-2">
-                            {{ $t('associated_mail_address') }}&nbsp;:
-                          </td>
-                          <td>
-                            <i>{{ $t('dummy_email_address') }}</i>
-                          </td>
-                        </tr>
-                      </tbody>
-                    </table>
-
-                    <p>
-                      <a
-                        :href="
+              <v-col lg="3" sm="12" md="6">
+                <PagesSubscriptionCard
+                  class="optionsCard"
+                  title="Nom de domaine"
+                  sub-title="Option payante"
+                  color="primary"
+                  :list="listCheck.domain"
+                >
+                  <template #card.action>
+                    <v-btn
+                      class="theme-primary btn"
+                      :href="
                           runtimeConfig.public.fileStorageBaseUrl +
                           '/Bon_de_commande/Nom_de_domaine.pdf'
                         "
-                        target="_blank"
-                      >
-                        <b>{{ $t('download_order_form') }}</b>
-                      </a>
-                    </p>
-                  </v-col>
-                </v-row>
+                      target="_blank"
+                    >
+                      souscrire à l'option <i class="fa-solid fa-greater-than small"></i>
+                    </v-btn>
+                  </template>
+                </PagesSubscriptionCard>
               </v-col>
             </v-row>
           </v-container>
         </UiExpansionPanel>
+
       </v-expansion-panels>
-    </v-col>
+
   </LayoutContainer>
 </template>
 
 <script setup lang="ts">
-import { useAbility } from '@casl/vue'
-import type { Ref } from 'vue'
-import { useDisplay } from 'vuetify'
-import type { AsyncData } from '#app'
-import { useOrganizationProfileStore } from '~/stores/organizationProfile'
-import { useEntityFetch } from '~/composables/data/useEntityFetch'
+import {useAbility} from '@casl/vue'
+import type {Ref} from 'vue'
+import {useDisplay} from 'vuetify'
+import type {AsyncData} from '#app'
+import {useOrganizationProfileStore} from '~/stores/organizationProfile'
+import {useEntityFetch} from '~/composables/data/useEntityFetch'
 import DolibarrAccount from '~/models/Organization/DolibarrAccount'
 import MobytUserStatus from '~/models/Organization/MobytUserStatus'
 
-const ability = useAbility()
-
-const runtimeConfig = useRuntimeConfig()
-
+//meta
 definePageMeta({
   name: 'subscription_page',
 })
 
+//Get composables
+const ability = useAbility()
+const runtimeConfig = useRuntimeConfig()
+const {mdAndUp, md} = useDisplay()
+const {fetch} = useEntityFetch()
+const i18n = useI18n()
+
+//Init ref
+const openedPanels: Ref<Array<string>> = initPanel()
+const organizationProfile = getOrganizationProfile()
+const accessProfileStore = useAccessProfileStore()
+const {mobytStatus, mobytPending}: Record<Ref<MobytUserStatus | null>, Ref<boolean>> = getMobytInformations()
+
+const {data: dolibarrAccount, pending: dolibarrPending} = fetch(
+  DolibarrAccount,
+  organizationProfile.id,
+)
+
 const showDolibarrPanel = computed(
   () =>
     !dolibarrPending.value &&
     dolibarrAccount.value &&
     dolibarrAccount.value.bills.length > 0,
 )
+const formatCurrency = (value: number, currency: string): string => {
+  return value.toLocaleString(i18n.locale.value, {
+    style: 'currency',
+    currency,
+  })
+}
 
-const { smAndUp } = useDisplay()
-
-// On déplie les expansion panels dans le onMounted en attendant la résolution du bug : https://github.com/vuetifyjs/vuetify/issues/16427#issuecomment-1380927133
-// TODO: quand le bug ci dessus est résolu, remplacer par `const openedPanels: Ref<Array<string>> = ref(['informations', 'bills', 'more_features'])`
-const openedPanels: Ref<Array<string>> = ref([])
-onMounted(() => {
-  openedPanels.value = ['informations', 'bills', 'more_features']
-})
-
-const i18n = useI18n()
-const organizationProfile = useOrganizationProfileStore()
-if (organizationProfile.id === null) {
-  throw new Error("Missing organization's id")
+const listCheck: Record<string, Array<string>> = {
+  'artist' : [
+    '100 Mo de stockage',
+    '75 comptes utilisateurs',
+    'Gestion de la structure',
+    'Site internet restreint',
+    'Options disponibles',
+  ],
+  'artistPremium' : [
+    '1Go de stockage',
+    '150 comptes utilisateurs',
+    'Gestion de la structure',
+    'Site internet illimité',
+    'Options disponibles',
+  ],
+  'school' : [
+    '500 Mo ou 1Go de stockage',
+    '3 comptes administrateurs',
+    'Extranet élèves, tuteurs, professeurs*',
+    'Gestion de la structure',
+    'Suivi pédagogique, facturation, ...',
+    'Site internet complet',
+    'Options adaptées à chaque structure',
+  ],
+  'sms': [
+    'Envoyez des SMS depuis votre logiciel',
+    'Choisissez le nombre de crédits'
+  ],
+  'domain':[
+    'Bénéficiez de votre propre nom de domaine',
+    'Et d\'une adresse mail personnalisée'
+  ]
 }
 
-const { fetch } = useEntityFetch()
+/**
+ * Initialisation des panels ouverts
+ */
+function initPanel(): Ref<Array<string>> {
+  // On déplie les expansion panels dans le onMounted en attendant la résolution du bug : https://github.com/vuetifyjs/vuetify/issues/16427#issuecomment-1380927133
+  // TODO: quand le bug ci dessus est résolu, remplacer par `const openedPanels: Ref<Array<string>> = ref(['informations', 'bills', 'more_features'])`
+  const openedPanels: Ref<Array<string>> = ref([])
+  onMounted(() => {
+    openedPanels.value = [i18n.t('subscription_page'), i18n.t('opentalent_offer'), i18n.t('opentalent_options')]
+  })
+  return openedPanels
+}
 
-const { data: dolibarrAccount, pending: dolibarrPending } = fetch(
-  DolibarrAccount,
-  organizationProfile.id,
-)
+/**
+ * Récupération de l'organization profile
+ */
+function getOrganizationProfile() {
+  const organizationProfile = useOrganizationProfileStore()
+  if (organizationProfile.id === null) {
+    throw new Error("Missing organization's id")
+  }
+  return organizationProfile
+}
 
-let mobytStatus: Ref<MobytUserStatus | null>
-let mobytPending: Ref<boolean>
+/**
+ * Récupération des informations Mobyt
+ */
+function getMobytInformations(): Record<Ref<MobytUserStatus | null>, Ref<boolean>> {
+  let mobytStatus: Ref<MobytUserStatus | null> = ref(null)
+  let mobytPending: Ref<boolean> = ref(false)
 
-if (ability.can('manage', 'texto')) {
-  const fetchMobytStatus = () => {
-    const { data, pending } = fetch(
+  if (ability.can('manage', 'texto')) {
+    const {data, pending} = fetch(
       MobytUserStatus,
       organizationProfile!.id!,
     ) as AsyncData<MobytUserStatus | null, Error | null>
-
     mobytStatus = data
     mobytPending = pending
   }
-  fetchMobytStatus()
-} else {
-  mobytStatus = ref(null)
-  mobytPending = ref(false)
-}
-
-const formatCurrency = (value: number, currency: string): string => {
-  return value.toLocaleString(i18n.locale.value, {
-    style: 'currency',
-    currency,
-  })
+  return {mobytStatus, mobytPending}
 }
-
-// Compute the number of columns of the more_features pannel
-const nbCols =
-  2 +
-  (organizationProfile.isArtist ? 1 : 0) +
-  (organizationProfile.isArtistProduct ? 1 : 0)
-const colWidth = 12 / nbCols
 </script>
 
-<style scoped lang="scss">
-#products-section {
-  width: 100%;
-
-  .v-col {
-    min-width: 260px;
-    border: solid 1px rgb(var(--v-theme-on-primary));
-
-    .v-row:nth-child(1) {
-      //background: rgb(var(--v-theme-neutral-soft));
-      height: 64px;
-      color: rgb(var(--v-theme-on-neutral-soft));
-      //font-size: 15px;
-      font-weight: bold;
-      border-bottom: solid 1px rgb(var(--v-theme-neutral));
-    }
 
-    .v-row:nth-child(2) {
-      height: 230px;
-      display: flex;
-      justify-content: center;
-      border-bottom: solid 1px rgb(var(--v-theme-neutral));
-    }
-
-    .v-row:nth-child(3) {
-    }
+<style scoped lang="scss">
+.offer_title{
+  span{
+    border-radius: 5px;
+    display: block;
+    font-weight: bold;
+    text-align: center;
+    padding: 5px;
   }
+}
 
-  .v-col:not(:first-child) {
-    border-left: none;
+.card-container{
+  .v-row {
+    display: -webkit-box;
+    display: -webkit-flex;
+    display: -ms-flexbox;
+    display:  flex;
+    flex-wrap: wrap;
   }
-
-  img {
-    max-height: 90%;
-    max-width: 90%;
+  .v-row > [class*='v-col-'] {
+    display: flex;
+    flex-direction: column;
   }
-
-  .v-row {
-    padding: 12px 18px;
-    vertical-align: top;
-    border-bottom: solid 1px rgb(var(--v-theme-on-primary));
+  .small{
+    font-size:6px;
+    padding-top: 5px;
+    padding-left: 5px;
   }
-  .v-row:last-child {
-    border: none;
+  .priceBlock{
+    text-align: center;
+    font-size: 15px;
+    font-weight: normal;
+    .price{
+      font-size: 30px;
+      font-weight: bold;
+    }
   }
+}
 
-  p {
-    margin-bottom: 12px;
+.artistCard{
+  :deep(.v-card-title){
+    text-align: center;
   }
+}
+
+.special_conditions{
+  font-size: 10px;
+}
+
+.trialBtn{
+  color: #000;
+  border: 1px solid rgb(var(--v-theme-artist));
+}
 
-  ul {
-    padding-left: 24px;
+.optionsCard{
+  :deep(.margin-sup){
+    margin-top: 0px;
   }
 }
 </style>