codevdesign 0.0.77 → 0.0.79

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -1,265 +1,316 @@
1
1
  <template>
2
2
  <div class="pa-2 mt-2 mb-1 mr-1">
3
- <!--on affiche une div avec les infos de préférences si le user a déjà au moins une préférence, au moins une unité et si activerDiv est à true.-->
4
- <div v-if="preferences && unites && unites.length > 0 && activerDivPreferences">
3
+ <!-- Affiche la carte récap si activée et qu'il y a des unités -->
4
+ <div v-if="activerDivPreferences && unites && unites.length > 0">
5
5
  <v-card
6
6
  width="375"
7
- border
7
+ variant="outlined"
8
8
  >
9
- <v-card-text
10
- flat
11
- class="pt-0 mt-0"
12
- >
9
+ <v-card-text class="pt-0 mt-0">
13
10
  <v-progress-linear
14
11
  v-if="chargementEnCours"
15
12
  indeterminate
16
13
  />
14
+
17
15
  <div
18
- v-if="!chargementEnCours"
16
+ v-else
19
17
  class="pt-2"
20
18
  >
21
19
  <div class="text-overline text-h6 mb-2">{{ texteTitre }}</div>
22
- <!-- <div v-if="existePreference == false">
23
- Cliquer sur modifier ou lors de la soumission, vous pourrez sélectionner vos préférences de suivi.
24
- </div>-->
20
+
25
21
  <div>
26
22
  <v-list-item
27
- v-for="uniteId in Object.keys(dictChaisesReleve).map(Number)"
23
+ v-for="uniteId in Object.keys(dictChaisesReleve)"
28
24
  :key="uniteId"
29
25
  class="mb-1"
30
26
  >
31
- <chaiseItem
32
- :unite-id="uniteId"
27
+ <ChaisePreferenceItem
28
+ :uniteId="Number(uniteId)"
33
29
  :preferences="preferences"
34
- :dict-chaises-releve="dictChaisesReleve"
30
+ :dictChaisesReleve="dictChaisesReleve"
35
31
  :unites="unites"
36
32
  />
37
33
  </v-list-item>
38
34
  </div>
39
35
  </div>
40
36
  </v-card-text>
37
+
41
38
  <v-card-actions>
42
- <div class="flex-grow-1"></div>
39
+ <div class="flex-grow-1" />
43
40
  <v-btn
44
- v-if="chargementEnCours == false"
41
+ v-if="!chargementEnCours"
45
42
  rounded
46
43
  variant="outlined"
47
44
  size="small"
48
45
  @click.stop="modifier"
49
- >{{ $t('csqc.bouton.modifier') }}</v-btn
50
46
  >
47
+ {{ texteBoutonModifier }}
48
+ </v-btn>
51
49
  </v-card-actions>
52
50
  </v-card>
53
51
  </div>
54
52
 
55
- <v-dialog
56
- v-model="visible"
57
- max-width="largeur"
58
- :fullscreen="display.name.value == 'xs'"
59
- @click:outside="annuler"
60
- @keydown.esc="annuler"
61
- >
62
- <v-card :class="['pa-0', display.name.value != 'xs' ? 'v-card-color-solid' : 'v-card-color-solid-xs']">
63
- <v-container :class="display.name.value == 'xs' ? 'pl-1 pr-3' : ''">
64
- <h3 class="pb-3 pl-2">{{ texteTitre }}</h3>
65
- <hr class="pl-2" />
66
- <v-card-text flat>
67
- <i>{{ info }}</i>
68
- <v-progress-linear
69
- v-if="chargementEnCours"
70
- indeterminate
71
- />
72
- <div
73
- v-if="!chargementEnCours"
74
- class="pt-4"
75
- >
76
- <v-row v-if="toutesUnitesPreferencesSelectionnees === false">
77
- <v-col cols="12">
78
- <v-alert
79
- v-model="afficherErreur"
80
- closable
81
- type="error"
82
- >{{ $t('csqc.message.chaiseSelectionToutes') }}</v-alert
83
- >
84
- </v-col>
85
- </v-row>
86
- <v-row>
87
- <v-col
88
- v-for="uniteId in Object.keys(dictChaisesReleve).map(Number)"
89
- :key="uniteId"
90
- cols="12"
91
- sm="4"
92
- md="3"
93
- >
94
- <label>{{ getUnite(uniteId)?.nom || '' }}</label>
95
- <br />
96
- <v-radio-group v-model="selection[uniteId]">
97
- <v-radio
98
- v-for="chaise in dictChaisesReleve[uniteId]"
99
- :key="chaise.id"
100
- :label="chaise.nom"
101
- :value="chaise.id"
102
- ></v-radio>
103
- </v-radio-group>
104
- </v-col>
105
- </v-row>
106
- </div>
107
- </v-card-text>
108
- </v-container>
53
+ <csqcDialogue
54
+ ref="modale"
55
+ :operation-en-cours="chargementEnCours"
56
+ :btn-ok-desactiver="chargementEnCours"
57
+ :titre="texteTitre"
58
+ :btn-annuler-texte="texteBoutonAnnuler"
59
+ @annuler="annuler"
60
+ @ok="ok"
61
+ ><template #contenu>
62
+ <div class="pt-2"></div>
63
+ <hr class="pt-0 mt-0 pl-0" />
64
+ <div class="pt-4">
65
+ <i>{{ info }}</i>
109
66
 
110
- <v-card-actions>
111
- <div class="flex-grow-1"></div>
112
- <v-btn
113
- color="primary"
114
- variant="outlined"
115
- @click.stop="annuler"
116
- >Annuler</v-btn
117
- >
118
- <v-btn
119
- color="primary"
120
- @click.stop="ok"
121
- >Ok</v-btn
67
+ <v-progress-linear
68
+ v-if="chargementEnCours"
69
+ indeterminate
70
+ />
71
+
72
+ <div
73
+ v-else
74
+ class="pt-4"
122
75
  >
123
- </v-card-actions>
124
- </v-card>
125
- </v-dialog>
76
+ <v-row v-if="!toutesUnitesPreferencesSelectionnees">
77
+ <v-col cols="12">
78
+ <v-alert
79
+ v-model="afficherErreur"
80
+ type="error"
81
+ variant="tonal"
82
+ dismissible
83
+ >
84
+ {{ texteMessageErreur }}
85
+ </v-alert>
86
+ </v-col>
87
+ </v-row>
88
+
89
+ <v-row>
90
+ <v-col
91
+ v-for="uniteId in Object.keys(dictChaisesReleve)"
92
+ :key="uniteId"
93
+ cols="12"
94
+ sm="6"
95
+ md="4"
96
+ >
97
+ <label>{{ getUnite(uniteId)?.nom ?? '' }}</label>
98
+ <br />
99
+ <v-radio-group v-model="selection[uniteId]">
100
+ <v-radio
101
+ v-for="chaise in dictChaisesReleve[uniteId]"
102
+ :key="chaise.id"
103
+ :label="chaise.nom"
104
+ :value="chaise.id"
105
+ />
106
+ </v-radio-group>
107
+ </v-col>
108
+ </v-row>
109
+ </div>
110
+ </div>
111
+ </template>
112
+ </csqcDialogue>
126
113
  </div>
127
114
  </template>
128
115
 
129
- <script lang="ts" setup>
130
- import { ref, computed, onMounted } from 'vue'
131
- import axios from '@/outils/appAxios.ts'
132
- import chaiseItem from './chaiseItem.vue'
116
+ <script setup lang="ts">
117
+ import { ref, computed, onMounted, nextTick, watch, toRefs } from 'vue'
133
118
  import { useDisplay } from 'vuetify'
134
- const display = useDisplay()
135
-
136
- // Définition des props
119
+ import ChaisePreferenceItem from './chaiseItem.vue'
120
+ import csqcDialogue from '../csqcDialogue.vue'
121
+ import axios from '@/outils/appAxios' // <- adapte si besoin (ex: axios.getAxios())
122
+ import type { Unite } from '@/codev/modeles/unite'
123
+ import { useI18n } from 'vue-i18n'
124
+
125
+ interface Chaise {
126
+ id: number
127
+ nom: string
128
+ }
129
+ interface Preference {
130
+ uniteId: number
131
+ chaiseId: number
132
+ }
133
+ const modale = ref<InstanceType<typeof csqcDialogue> | null>(null)
134
+ /** Props */
137
135
  const props = defineProps<{
138
- activerDivPreferences: boolean
139
- typeintervenant: string
140
- demandeid: string
141
- formulaireid: string
142
- urlbase: string
143
- titre?: string
144
- texteinfo?: string
145
- largeur?: number
136
+ activerDivPreferences?: boolean
137
+ typeIntervenant: number
138
+ demandeId: number
139
+ formulaireId: number
140
+ urlBase: string
141
+ texteTitre?: string
142
+ texteInfo?: string
143
+ largeurModale?: number
146
144
  }>()
147
-
148
- // Définition des emits
145
+ const { typeIntervenant, demandeId, formulaireId, urlBase } = toRefs(props)
146
+ /** Emits */
149
147
  const emit = defineEmits<{
150
- (event: 'annuler'): void
151
- (event: 'confirmer'): void
148
+ (e: 'annuler'): void
149
+ (e: 'confirmer'): void
152
150
  }>()
153
151
 
154
- // Variables réactives
152
+ const { t } = useI18n({ useScope: 'global' })
153
+ const { xs } = useDisplay()
154
+ const isXs = computed(() => xs.value)
155
+
156
+ /** State */
155
157
  const visible = ref(false)
156
158
  const chargementEnCours = ref(false)
157
159
  const afficherErreur = ref(false)
158
- const unites = ref<{ id: number; nom: string }[]>([])
159
- const preferences = ref<{ uniteId: number; chaiseId: number }[]>([])
160
- const dictChaisesReleve = ref<Record<number, { id: number; nom: string }[]>>({})
161
- const selection = ref<Record<number, number>>({})
160
+ const unites = ref<Unite[]>([])
161
+ const preferences = ref<Preference[]>([])
162
+ const dictChaisesReleve = ref<Record<string, Chaise[]>>({})
163
+ const selection = ref<Record<string, number>>({})
162
164
  const modeModifier = ref(false)
163
165
 
164
- // Méthodes
165
- const soumettre = async () => {
166
+ /** Textes */
167
+ const texteMessageErreur = computed(() => t('csqc.csqcChaise.erreur'))
168
+ const texteBoutonAnnuler = computed(() => t('csqc.bouton.annuler'))
169
+ const texteBoutonModifier = computed(() => t('csqc.bouton.modifier'))
170
+ const texteTitre = computed(() =>
171
+ props.texteTitre && props.texteTitre.length > 0 ? props.texteTitre : t('csqc.csqcChaise.titre'),
172
+ )
173
+ const info = computed(() =>
174
+ props.texteInfo && props.texteInfo.length > 0 ? props.texteInfo : t('csqc.csqcChaise.info'),
175
+ )
176
+
177
+ // Option A — ne recharger que si typeIntervenant change
178
+
179
+ const largeur = computed(() => props.largeurModale ?? 1200)
180
+ const activerDivPreferences = computed(() => props.activerDivPreferences ?? true)
181
+
182
+ function getUnite(uniteId: string) {
183
+ return unites.value.find((u: Unite) => String(u.id) === String(uniteId))
184
+ }
185
+
186
+ /*
187
+ function estPrefere(uniteId: string | number, chaiseId: number) {
188
+ return preferences.value.some(p => String(p.uniteId) === String(uniteId) && p.chaiseId === chaiseId)
189
+ }*/
190
+
191
+ /** Sélection par défaut à partir des préférences existantes */
192
+ function definitionSelectionDepart() {
193
+ for (const uniteId in dictChaisesReleve.value) {
194
+ const chaises = dictChaisesReleve.value[uniteId] ?? []
195
+ const pref = preferences.value.find(
196
+ p => String(p.uniteId) === String(uniteId) && chaises.some(chaise => chaise.id === p.chaiseId),
197
+ )
198
+ const chaiseIdDefaut = pref?.chaiseId ?? (chaises.length === 1 ? (chaises[0]?.id ?? -1) : -1)
199
+ selection.value[uniteId] = chaiseIdDefaut
200
+ }
201
+ }
202
+
203
+ /** Toutes les unités ont-elles une préférence sélectionnée ? */
204
+ const toutesUnitesPreferencesSelectionnees = computed(() => {
205
+ for (const uniteId in dictChaisesReleve.value) {
206
+ const chaises = dictChaisesReleve.value[uniteId] ?? []
207
+ const uniteOk = chaises.some(c => preferences.value.some(p => p.chaiseId === c.id))
208
+ if (!uniteOk) return false
209
+ }
210
+ return true
211
+ })
212
+
213
+ async function chargerUnites() {
214
+ const url = `${props.urlBase}/api/ComposantUI/Unites`
215
+ const unitesData = (await axios.getAxios().get<Unite[]>(url)) as unknown as Unite[]
216
+ unites.value = unitesData ?? []
217
+ }
218
+
219
+ async function chargementPreferences() {
220
+ chargementEnCours.value = true
221
+
222
+ // Chaises par unité
223
+ {
224
+ const data = (await axios
225
+ .getAxios()
226
+ .get<
227
+ Record<string, Chaise[]>
228
+ >(`${props.urlBase}/api/ComposantUI/ReleveDe/${props.typeIntervenant}/Demande/${props.demandeId}`)) as unknown as Record<
229
+ string,
230
+ Chaise[]
231
+ >
232
+ dictChaisesReleve.value = data ?? {}
233
+ }
234
+
235
+ // Préférences de l'usager
236
+ {
237
+ const data = (await axios
238
+ .getAxios()
239
+ .get<
240
+ Preference[]
241
+ >(`${props.urlBase}/api/ComposantUI/Preferences/${props.formulaireId}/TypeIntervenant/${props.typeIntervenant}`)) as unknown as Preference[]
242
+ preferences.value = (data ?? []).filter(Boolean)
243
+ }
244
+
245
+ definitionSelectionDepart()
246
+
247
+ // Sauvegarde immédiate pour les choix uniques (si demandé par ton flux)
248
+ await sauvegarder()
249
+
250
+ chargementEnCours.value = false
251
+ }
252
+
253
+ /** Actions UI */
254
+ /*async function soumettre() {
166
255
  modeModifier.value = false
167
256
  await ouvrir()
168
- }
257
+ }*/
169
258
 
170
- const ouvrir = async () => {
171
- // Mode sans les divs
172
- if (props.activerDivPreferences === false) {
259
+ async function ouvrir() {
260
+ if (!activerDivPreferences.value) {
173
261
  await chargementPreferences()
174
262
  visible.value = true
175
263
  return
176
264
  }
177
265
 
178
- // Mode avec div, mais il manque une sélection
179
266
  if (!toutesUnitesPreferencesSelectionnees.value) {
180
267
  visible.value = true
181
268
  return
182
269
  }
183
270
 
184
- // Tout est beau
185
271
  await ok()
186
272
  }
187
273
 
188
- const definitionSelectionDepart = () => {
189
- for (const uniteId in dictChaisesReleve.value) {
190
- const chaises = dictChaisesReleve.value[uniteId]
191
- const uniteIdNum = Number(uniteId) // Convert to number
192
-
193
- const pref = preferences.value.find(
194
- pref => pref.uniteId === uniteIdNum && chaises.some(chaise => chaise.id === pref.chaiseId),
195
- )
196
-
197
- const chaiseIdDefaut = pref?.chaiseId ?? (chaises.length === 1 ? chaises[0].id : -1)
198
- selection.value[uniteIdNum] = chaiseIdDefaut // Ensure key consistency
199
- }
200
- }
201
- const estPrefere = (uniteId: number, chaiseId: number) => {
202
- return preferences.value.some(x => x.uniteId === uniteId && x.chaiseId === chaiseId)
203
- }
204
-
205
- const annuler = () => {
274
+ function annuler() {
206
275
  visible.value = false
207
276
  modeModifier.value = false
208
277
  emit('annuler')
209
278
  }
210
279
 
211
- const getUnite = (uniteId: number) => {
212
- return unites.value.find(x => x.id === uniteId)
213
- }
214
-
215
- const modifier = () => {
280
+ function modifier() {
216
281
  modeModifier.value = true
217
282
  visible.value = true
283
+ modale.value?.ouvrir()
218
284
  }
219
285
 
220
- const ok = async () => {
221
- await sauvegarder()
222
- if (toutesUnitesPreferencesSelectionnees.value) {
223
- if (!modeModifier.value) {
224
- emit('confirmer')
225
- }
226
- visible.value = false
227
- modeModifier.value = false
228
- } else {
229
- afficherErreur.value = true
230
- }
231
- }
232
-
233
- const sauvegarder = async () => {
286
+ async function sauvegarder() {
234
287
  for (const uniteId in dictChaisesReleve.value) {
235
288
  const chaiseId = selection.value[uniteId]
236
- if (chaiseId <= 0) {
237
- continue
238
- }
289
+ if (!chaiseId || chaiseId <= 0) continue
239
290
 
240
- // Cibler l'ancienne préférence reliée à une des chaises de cette unité
241
- let prefIndexDeUnite = -1
242
- for (let i = 0; i < dictChaisesReleve.value[uniteId].length; i++) {
243
- prefIndexDeUnite = preferences.value.findIndex(p => p.chaiseId === dictChaisesReleve.value[uniteId][i].id)
244
- if (prefIndexDeUnite >= 0) {
245
- break
246
- }
247
- }
291
+ const chaises = dictChaisesReleve.value[uniteId] ?? []
292
+ if (chaises.length === 0) continue
293
+
294
+ // Préférence existante pour CETTE unité ?
295
+ const prefIndexDeUnite = preferences.value.findIndex(p => chaises.some(c => c.id === p.chaiseId))
248
296
 
249
297
  try {
250
- const response = await axios
298
+ const data = (await axios
251
299
  .getAxios()
252
- .put(
253
- `${props.urlbase}/api/ComposantUI/Preferences/${props.formulaireid}/Unite/${uniteId}/Chaise/${chaiseId}/TypeIntervenant/${props.typeintervenant}`,
254
- )
255
-
256
- const itemRecu = response.data // Extract the actual data
300
+ .put<Preference>(
301
+ `${props.urlBase}/api/ComposantUI/Preferences/${props.formulaireId}` +
302
+ `/Unite/${encodeURIComponent(uniteId)}` +
303
+ `/Chaise/${chaiseId}` +
304
+ `/TypeIntervenant/${props.typeIntervenant}`,
305
+ )) as unknown as Preference
306
+ const itemRecu = data as Preference
257
307
 
258
- // Écraser l'ancienne sélection
259
308
  if (prefIndexDeUnite >= 0) {
260
- preferences.value[prefIndexDeUnite] = itemRecu
309
+ // remplace l'élément à l'index
310
+ preferences.value.splice(prefIndexDeUnite, 1, itemRecu)
261
311
  } else {
262
- preferences.value = [itemRecu]
312
+ // ajoute un nouvel élément
313
+ preferences.value.push(itemRecu)
263
314
  }
264
315
  } catch (e) {
265
316
  console.error(e)
@@ -267,64 +318,45 @@
267
318
  }
268
319
  }
269
320
 
270
- const chargementPreferences = async () => {
271
- chargementEnCours.value = true
272
- // Ramasse les infos des chaises par unité
273
- dictChaisesReleve.value = await axios
274
- .getAxios()
275
- .get(`${props.urlbase}/api/ComposantUI/ReleveDe/${props.typeintervenant}/Demande/${props.demandeid}`)
276
-
277
- // Ramasse les préférences de l'usager
278
- preferences.value = await axios
279
- .getAxios()
280
- .get(
281
- `${props.urlbase}/api/ComposantUI/Preferences/${props.formulaireid}/TypeIntervenant/${props.typeintervenant}`,
282
- )
283
- definitionSelectionDepart()
284
-
285
- await sauvegarder() // Immédiatement on sauvegarde pour les choix uniques.
321
+ /** Validation finale */
322
+ async function ok() {
323
+ await sauvegarder()
286
324
 
287
- chargementEnCours.value = false
325
+ if (toutesUnitesPreferencesSelectionnees.value) {
326
+ if (!modeModifier.value) emit('confirmer')
327
+ visible.value = false
328
+ modeModifier.value = false
329
+ } else {
330
+ afficherErreur.value = true
331
+ await nextTick()
332
+ }
288
333
  }
289
334
 
290
- const texteTitre = computed(() => {
291
- return props.titre || ''
335
+ onMounted(async () => {
336
+ chargementEnCours.value = true
337
+ await chargerUnites()
338
+ await chargementPreferences()
339
+ chargementEnCours.value = false
292
340
  })
293
341
 
294
- const info = computed(() => {
295
- return props.texteinfo || ''
342
+ // si le type d'intervenant change
343
+ watch(typeIntervenant, async (nv, ov) => {
344
+ if (nv === ov) return
345
+ await rechargerPourTypeIntervenant()
296
346
  })
297
347
 
298
- const existePreference = computed(() => {
299
- for (const uniteId in dictChaisesReleve.value) {
300
- for (let i = 0; i < dictChaisesReleve.value[uniteId].length; i++) {
301
- if (preferences.value.some(p => p.chaiseId === dictChaisesReleve.value[uniteId][i].id)) {
302
- return true
303
- }
304
- }
305
- }
306
- return false
307
- })
308
-
309
- const toutesUnitesPreferencesSelectionnees = computed(() => {
310
- for (const uniteId in dictChaisesReleve.value) {
311
- let uniteOk = false
312
- for (let i = 0; i < dictChaisesReleve.value[uniteId].length; i++) {
313
- if (preferences.value.some(p => p.chaiseId === dictChaisesReleve.value[uniteId][i].id)) {
314
- uniteOk = true
315
- }
316
- }
348
+ async function rechargerPourTypeIntervenant() {
349
+ try {
350
+ chargementEnCours.value = true
351
+ preferences.value = []
352
+ dictChaisesReleve.value = {}
353
+ selection.value = {}
354
+ afficherErreur.value = false
317
355
 
318
- if (!uniteOk) return false
356
+ // recharge les données dépendantes
357
+ await chargementPreferences()
358
+ } finally {
359
+ chargementEnCours.value = false
319
360
  }
320
-
321
- return true // Toutes les unités ont été sélectionnées
322
- })
323
-
324
- onMounted(async () => {
325
- chargementEnCours.value = true
326
- // Ramasse les unités de l'usager
327
- unites.value = await axios.getAxios().get(`${props.urlbase}/api/ComposantUI/Unites`)
328
- chargementPreferences()
329
- })
361
+ }
330
362
  </script>
@@ -33,9 +33,12 @@
33
33
  })
34
34
 
35
35
  const getPreference = computed(() => {
36
- for (let i = 0; i < props.dictChaisesReleve[props.uniteId]?.length; i += 1) {
37
- if (props.preferences.some(p => p.chaiseId == props.dictChaisesReleve[props.uniteId][i].id)) {
38
- return props.dictChaisesReleve[props.uniteId][i].nom
36
+ const chaises = props.dictChaisesReleve?.[props.uniteId] ?? []
37
+ const prefs = props.preferences ?? []
38
+
39
+ for (const chaise of chaises) {
40
+ if (prefs.some(p => p.chaiseId === chaise.id)) {
41
+ return chaise.nom
39
42
  }
40
43
  }
41
44