Apply prettier to files

This commit is contained in:
2024-12-11 10:49:11 +01:00
parent a6aa2a81c2
commit ebfd48e41f
31 changed files with 4889 additions and 3883 deletions

View File

@@ -1,7 +1,7 @@
import { createApp } from 'vue';
import PickEntity from 'ChillMainAssets/vuejs/PickEntity/PickEntity.vue';
import { _createI18n } from 'ChillMainAssets/vuejs/_js/i18n';
import { appMessages } from 'ChillMainAssets/vuejs/PickEntity/i18n';
import { createApp } from "vue";
import PickEntity from "ChillMainAssets/vuejs/PickEntity/PickEntity.vue";
import { _createI18n } from "ChillMainAssets/vuejs/_js/i18n";
import { appMessages } from "ChillMainAssets/vuejs/PickEntity/i18n";
const i18n = _createI18n(appMessages);
@@ -9,158 +9,172 @@ let appsOnPage = new Map();
let appsPerInput = new Map();
function loadDynamicPicker(element) {
let apps = element.querySelectorAll('[data-module="pick-dynamic"]');
let apps = element.querySelectorAll('[data-module="pick-dynamic"]');
apps.forEach(function (el) {
const isMultiple = parseInt(el.dataset.multiple) === 1,
uniqId = el.dataset.uniqid,
input = element.querySelector(
'[data-input-uniqid="' + el.dataset.uniqid + '"]',
),
// the "picked" will always be an array, even if multiple is false
picked = isMultiple
? JSON.parse(input.value)
: input.value === "[]" || input.value === ""
? null
: [JSON.parse(input.value)];
(suggested = JSON.parse(el.dataset.suggested)),
(as_id = parseInt(el.dataset.asId) === 1),
(submit_on_adding_new_entity =
parseInt(el.dataset.submitOnAddingNewEntity) === 1);
label = el.dataset.label;
apps.forEach(function(el) {
if (!isMultiple) {
if (input.value === "[]") {
input.value = null;
}
}
const
isMultiple = parseInt(el.dataset.multiple) === 1,
uniqId = el.dataset.uniqid,
input = element.querySelector('[data-input-uniqid="'+ el.dataset.uniqid +'"]'),
// the "picked" will always be an array, even if multiple is false
picked = isMultiple ?
JSON.parse(input.value) : (
(input.value === '[]' || input.value === '') ?
null : [ JSON.parse(input.value) ]
)
suggested = JSON.parse(el.dataset.suggested),
as_id = parseInt(el.dataset.asId) === 1,
submit_on_adding_new_entity = parseInt(el.dataset.submitOnAddingNewEntity) === 1
label = el.dataset.label;
if (!isMultiple) {
if (input.value === '[]'){
input.value = null;
}
}
const app = createApp({
template: '<pick-entity ' +
':multiple="multiple" ' +
':types="types" ' +
':picked="picked" ' +
':uniqid="uniqid" ' +
':suggested="notPickedSuggested" ' +
':label="label" ' +
'@addNewEntity="addNewEntity" ' +
'@removeEntity="removeEntity" ' +
'@addNewEntityProcessEnded="addNewEntityProcessEnded"' +
'></pick-entity>',
components: {
PickEntity,
},
data() {
return {
multiple: isMultiple,
types: JSON.parse(el.dataset.types),
picked: picked === null ? [] : picked,
uniqid: el.dataset.uniqid,
suggested,
as_id,
submit_on_adding_new_entity,
label,
}
},
computed: {
notPickedSuggested() {
const pickedIds = new Set();
for (const p of this.picked) {
pickedIds.add(`${p.type}${p.id}`);
}
return this.suggested.filter(e => !pickedIds.has(`${e.type}${e.id}`))
const app = createApp({
template:
"<pick-entity " +
':multiple="multiple" ' +
':types="types" ' +
':picked="picked" ' +
':uniqid="uniqid" ' +
':suggested="notPickedSuggested" ' +
':label="label" ' +
'@addNewEntity="addNewEntity" ' +
'@removeEntity="removeEntity" ' +
'@addNewEntityProcessEnded="addNewEntityProcessEnded"' +
"></pick-entity>",
components: {
PickEntity,
},
data() {
return {
multiple: isMultiple,
types: JSON.parse(el.dataset.types),
picked: picked === null ? [] : picked,
uniqid: el.dataset.uniqid,
suggested,
as_id,
submit_on_adding_new_entity,
label,
};
},
computed: {
notPickedSuggested() {
const pickedIds = new Set();
for (const p of this.picked) {
pickedIds.add(`${p.type}${p.id}`);
}
return this.suggested.filter(
(e) => !pickedIds.has(`${e.type}${e.id}`),
);
},
},
methods: {
addNewEntity({ entity }) {
if (this.multiple) {
if (
!this.picked.some((el) => {
return el.type === entity.type && el.id === entity.id;
})
) {
this.picked.push(entity);
if (!as_id) {
input.value = JSON.stringify(this.picked);
} else {
const ids = this.picked.map((el) => el.id);
input.value = ids.join(",");
}
},
methods: {
addNewEntity({entity}) {
if (this.multiple) {
if (!this.picked.some(el => {
return el.type === entity.type && el.id === entity.id;
})) {
this.picked.push(entity);
if (!as_id) {
input.value = JSON.stringify(this.picked);
} else {
const ids = this.picked.map(el => el.id);
input.value = ids.join(',');
}
console.log(entity)
}
} else {
if (!this.picked.some(el => {
return el.type === entity.type && el.id === entity.id;
})) {
this.picked.splice(0, this.picked.length);
this.picked.push(entity);
if (!as_id) {
input.value = JSON.stringify(this.picked[0]);
} else {
input.value = this.picked.map(el => el.id);
}
}
}
},
addNewEntityProcessEnded() {
if (this.submit_on_adding_new_entity) {
input.form.submit();
}
},
removeEntity({entity}) {
if (-1 === this.suggested.findIndex(e => e.type === entity.type && e.id === entity.id)) {
this.suggested.push(entity);
}
this.picked = this.picked.filter(e => !(e.type === entity.type && e.id === entity.id));
if (this.multiple) {
input.value = JSON.stringify(this.picked);
} else {
input.value = "";
}
},
console.log(entity);
}
})
.use(i18n)
.mount(el);
} else {
if (
!this.picked.some((el) => {
return el.type === entity.type && el.id === entity.id;
})
) {
this.picked.splice(0, this.picked.length);
this.picked.push(entity);
if (!as_id) {
input.value = JSON.stringify(this.picked[0]);
} else {
input.value = this.picked.map((el) => el.id);
}
}
}
},
addNewEntityProcessEnded() {
if (this.submit_on_adding_new_entity) {
input.form.submit();
}
},
removeEntity({ entity }) {
if (
-1 ===
this.suggested.findIndex(
(e) => e.type === entity.type && e.id === entity.id,
)
) {
this.suggested.push(entity);
}
this.picked = this.picked.filter(
(e) => !(e.type === entity.type && e.id === entity.id),
);
if (this.multiple) {
input.value = JSON.stringify(this.picked);
} else {
input.value = "";
}
},
},
})
.use(i18n)
.mount(el);
appsOnPage.set(uniqId, app);
appsPerInput.set(input.name, app);
});
appsOnPage.set(uniqId, app);
appsPerInput.set(input.name, app);
});
}
document.addEventListener('show-hide-show', function(e) {
loadDynamicPicker(e.detail.container)
document.addEventListener("show-hide-show", function (e) {
loadDynamicPicker(e.detail.container);
});
document.addEventListener('show-hide-hide', function(e) {
console.log('hiding event caught')
e.detail.container.querySelectorAll('[data-module="pick-dynamic"]').forEach((el) => {
let uniqId = el.dataset.uniqid;
if (appsOnPage.has(uniqId)) {
appsOnPage.get(uniqId).unmount();
appsOnPage.delete(uniqId);
}
})
});
document.addEventListener('pick-entity-type-action', function (e) {
console.log('pick entity event', e);
if (!appsPerInput.has(e.detail.name)) {
console.error('no app with this name');
return;
}
const app = appsPerInput.get(e.detail.name);
if (e.detail.action === 'add') {
app.addNewEntity(e.detail.entity);
} else if (e.detail.action === 'remove') {
app.removeEntity(e.detail.entity);
} else {
console.error('action not supported: '+e.detail.action);
document.addEventListener("show-hide-hide", function (e) {
console.log("hiding event caught");
e.detail.container
.querySelectorAll('[data-module="pick-dynamic"]')
.forEach((el) => {
let uniqId = el.dataset.uniqid;
if (appsOnPage.has(uniqId)) {
appsOnPage.get(uniqId).unmount();
appsOnPage.delete(uniqId);
}
});
});
document.addEventListener('DOMContentLoaded', function(e) {
loadDynamicPicker(document)
})
document.addEventListener("pick-entity-type-action", function (e) {
console.log("pick entity event", e);
if (!appsPerInput.has(e.detail.name)) {
console.error("no app with this name");
return;
}
const app = appsPerInput.get(e.detail.name);
if (e.detail.action === "add") {
app.addNewEntity(e.detail.entity);
} else if (e.detail.action === "remove") {
app.removeEntity(e.detail.entity);
} else {
console.error("action not supported: " + e.detail.action);
}
});
document.addEventListener("DOMContentLoaded", function (e) {
loadDynamicPicker(document);
});
window.loadDynamicPicker = loadDynamicPicker;

View File

@@ -1,174 +1,180 @@
import {ShowHide} from 'ChillMainAssets/lib/show_hide/show_hide.js';
import { ShowHide } from "ChillMainAssets/lib/show_hide/show_hide.js";
window.addEventListener('DOMContentLoaded', function() {
const
divTransitions = document.querySelector('#transitions'),
futureDestUsersContainer = document.querySelector('#futureDests'),
personSignatureField = document.querySelector('#person-signature-field'),
userSignatureField = document.querySelector('#user-signature-field'),
signatureTypeChoices = document.querySelector('#signature-type-choice'),
personChoice = document.querySelector('#workflow_step_isPersonOrUserSignature_0'),
userChoice = document.querySelector('#workflow_step_isPersonOrUserSignature_1'),
signatureZone = document.querySelector('#signature-zone'),
transitionFilterContainer = document.querySelector('#transitionFilter'),
transitionsContainer = document.querySelector('#transitions'),
sendExternalContainer = document.querySelector('#sendExternalContainer')
;
window.addEventListener("DOMContentLoaded", function () {
const divTransitions = document.querySelector("#transitions"),
futureDestUsersContainer = document.querySelector("#futureDests"),
personSignatureField = document.querySelector("#person-signature-field"),
userSignatureField = document.querySelector("#user-signature-field"),
signatureTypeChoices = document.querySelector("#signature-type-choice"),
personChoice = document.querySelector(
"#workflow_step_isPersonOrUserSignature_0",
),
userChoice = document.querySelector(
"#workflow_step_isPersonOrUserSignature_1",
),
signatureZone = document.querySelector("#signature-zone"),
transitionFilterContainer = document.querySelector("#transitionFilter"),
transitionsContainer = document.querySelector("#transitions"),
sendExternalContainer = document.querySelector("#sendExternalContainer");
// ShowHide instance for future dest users
new ShowHide({
debug: false,
load_event: null,
froms: [divTransitions],
container: [futureDestUsersContainer],
test: function (froms, event) {
for (let transition of froms) {
for (let input of transition.querySelectorAll("input")) {
if (input.checked) {
if ("1" === input.dataset.toFinal) {
return false;
}
// ShowHide instance for future dest users
if ("1" === input.dataset.isSentExternal) {
return false;
}
const inputData = JSON.parse(
input.getAttribute("data-is-signature"),
);
if (inputData.includes("person") || inputData.includes("user")) {
return false;
} else {
personChoice.checked = false;
userChoice.checked = false;
return true;
}
}
}
}
return false;
},
});
// ShowHide instance for send external
new ShowHide({
debug: false,
load_event: null,
froms: [divTransitions],
container: [sendExternalContainer],
test: function (froms, event) {
for (let transition of froms) {
for (let input of transition.querySelectorAll("input")) {
if (input.checked) {
if ("1" === input.dataset.isSentExternal) {
return true;
}
}
}
}
return false;
},
});
// ShowHide signature zone
new ShowHide({
debug: false,
load_event: null,
froms: [divTransitions],
container: [signatureZone],
test: function (froms, event) {
for (let transition of froms) {
for (let input of transition.querySelectorAll("input")) {
if (input.checked) {
const inputData = JSON.parse(
input.getAttribute("data-is-signature"),
);
if (inputData.includes("person") || inputData.includes("user")) {
return true;
}
}
}
}
return false;
},
});
// ShowHides for personSignatureField or userSignatureField within signature zone
new ShowHide({
debug: false,
froms: [signatureTypeChoices],
container: [personSignatureField],
test: function (froms, event) {
for (let container of froms) {
return personChoice.checked;
}
return false;
},
});
new ShowHide({
debug: false,
froms: [signatureTypeChoices],
container: [userSignatureField],
test: function (froms, event) {
for (let container of froms) {
return userChoice.checked;
}
return false;
},
});
if (null !== divTransitions) {
new ShowHide({
debug: false,
load_event: null,
froms: [divTransitions],
container: [futureDestUsersContainer],
test: function(froms, event) {
for (let transition of froms) {
for (let input of transition.querySelectorAll('input')) {
test: function (divs, arg2, arg3) {
for (let div of divs) {
for (let input of div.querySelectorAll("input")) {
if (input.checked) {
if ('1' === input.dataset.toFinal) {
return false;
}
if ('1' === input.dataset.isSentExternal) {
return false;
}
const inputData = JSON.parse(input.getAttribute('data-is-signature'))
if (inputData.includes('person') || inputData.includes('user')) {
if (input.dataset.toFinal === "1") {
return false;
} else {
personChoice.checked = false
userChoice.checked = false
return true;
}
}
}
}
return false;
}
});
// ShowHide instance for send external
new ShowHide({
debug: false,
load_event: null,
froms: [divTransitions],
container: [sendExternalContainer],
test: function(froms, event) {
for (let transition of froms) {
for (let input of transition.querySelectorAll('input')) {
if (input.checked) {
if ('1' === input.dataset.isSentExternal) {
return true;
}
}
}
}
return false;
}
})
// ShowHide signature zone
new ShowHide({
debug: false,
load_event: null,
froms: [divTransitions],
container: [signatureZone],
test: function(froms, event) {
for (let transition of froms) {
for (let input of transition.querySelectorAll('input')) {
if (input.checked) {
const inputData = JSON.parse(input.getAttribute('data-is-signature'))
if (inputData.includes('person') || inputData.includes('user')) {
return true;
}
}
}
}
return false;
}
});
// ShowHides for personSignatureField or userSignatureField within signature zone
new ShowHide({
debug: false,
froms: [signatureTypeChoices],
container: [personSignatureField],
test: function(froms, event) {
for (let container of froms) {
return personChoice.checked;
}
return false;
return true;
},
});
}
new ShowHide({
debug: false,
froms: [signatureTypeChoices],
container: [userSignatureField],
test: function(froms, event) {
for (let container of froms) {
return userChoice.checked;
}
return false;
},
});
if (null !== transitionFilterContainer) {
transitionsContainer
.querySelectorAll(".form-check")
.forEach(function (row) {
const isForward = row.querySelector("input").dataset.isForward;
if (null !== divTransitions) {
new ShowHide({
new ShowHide({
load_event: null,
froms: [divTransitions],
container: [futureDestUsersContainer],
test: function(divs, arg2, arg3) {
for (let div of divs) {
for (let input of div.querySelectorAll('input')) {
if (input.checked) {
if (input.dataset.toFinal === "1") {
return false;
} else {
return true;
}
}
}
froms: [transitionFilterContainer],
container: row,
test: function (containers) {
for (let container of containers) {
for (let input of container.querySelectorAll("input")) {
if (input.checked) {
return isForward === input.value;
}
}
return true;
}
return true;
},
toggle_callback: function (c, dir) {
for (let div of c) {
let input = div.querySelector("input");
if ("hide" === dir) {
input.checked = false;
input.disabled = true;
} else {
input.disabled = false;
}
}
},
});
}
if (null !== transitionFilterContainer) {
transitionsContainer.querySelectorAll('.form-check').forEach(function(row) {
const isForward = row.querySelector('input').dataset.isForward;
new ShowHide({
load_event: null,
froms: [transitionFilterContainer],
container: row,
test: function (containers) {
for (let container of containers) {
for (let input of container.querySelectorAll('input')) {
if (input.checked) {
return isForward === input.value;
}
}
}
return true;
},
toggle_callback: function (c, dir) {
for (let div of c) {
let input = div.querySelector('input');
if ('hide' === dir) {
input.checked = false;
input.disabled = true;
} else {
input.disabled = false;
}
}
},
});
});
}
});
}
});

View File

@@ -28,7 +28,11 @@
/>
<span class="mx-2">{{ getStep(w) }}</span>
</div>
<span v-if="w.isOnHoldAtCurrentStep" class="badge bg-success rounded-pill">{{ $t('on_hold') }}</span>
<span
v-if="w.isOnHoldAtCurrentStep"
class="badge bg-success rounded-pill"
>{{ $t("on_hold") }}</span
>
</div>
</td>
<td v-if="w.datas.persons !== null">

View File

@@ -1,83 +1,89 @@
const appMessages = {
fr: {
main_title: "Vue d'ensemble",
my_works: {
tab: "Mes actions",
description: "Liste des actions d'accompagnement dont je suis référent et qui arrivent à échéance.",
},
my_evaluations: {
tab: "Mes évaluations",
description: "Liste des évaluations dont je suis référent et qui arrivent à échéance.",
},
my_tasks: {
tab: "Mes tâches",
description_alert: "Liste des tâches auxquelles je suis assigné et dont la date de rappel est dépassée.",
description_warning: "Liste des tâches auxquelles je suis assigné et dont la date d'échéance est dépassée.",
},
my_accompanying_courses: {
tab: "Mes nouveaux parcours",
description: "Liste des parcours d'accompagnement que l'on vient de m'attribuer depuis moins de 15 jours.",
},
my_notifications: {
tab: "Mes nouvelles notifications",
description: "Liste des notifications reçues et non lues.",
},
my_workflows: {
tab: "Mes workflows",
description: "Liste des workflows en attente d'une action.",
description_cc: "Liste des workflows dont je suis en copie."
},
opening_date: "Date d'ouverture",
social_issues: "Problématiques sociales",
concerned_persons: "Usagers concernés",
max_date: "Date d'échéance",
warning_date: "Date de rappel",
evaluation: "Évaluation",
task: "Tâche",
Date: "Date",
From: "Expéditeur",
Subject: "Objet",
Entity: "Associé à",
Step: "Étape",
concerned_users: "Usagers concernés",
Object_workflow: "Objet du workflow",
on_hold: "En attente",
show_entity: "Voir {entity}",
the_activity: "l'échange",
the_course: "le parcours",
the_action: "l'action",
the_evaluation: "l'évaluation",
the_evaluation_document: "le document",
the_task: "la tâche",
the_workflow: "le workflow",
StartDate: "Date d'ouverture",
SocialAction: "Action d'accompagnement",
no_data: "Aucun résultats",
no_dashboard: "Pas de tableaux de bord",
counter: {
unread_notifications: "{n} notification non lue | {n} notifications non lues",
assignated_courses: "{n} parcours récent assigné | {n} parcours récents assignés",
assignated_actions: "{n} action assignée | {n} actions assignées",
assignated_evaluations: "{n} évaluation assignée | {n} évaluations assignées",
alert_tasks: "{n} tâche en rappel | {n} tâches en rappel",
warning_tasks: "{n} tâche à échéance | {n} tâches à échéance",
},
emergency: "Urgent",
confidential: "Confidentiel",
automatic_notification: "Notification automatique",
widget: {
news: {
title: "Actualités",
readMore: "Lire la suite",
date: "Date",
none: "Aucune actualité"
}
}
}
fr: {
main_title: "Vue d'ensemble",
my_works: {
tab: "Mes actions",
description:
"Liste des actions d'accompagnement dont je suis référent et qui arrivent à échéance.",
},
my_evaluations: {
tab: "Mes évaluations",
description:
"Liste des évaluations dont je suis référent et qui arrivent à échéance.",
},
my_tasks: {
tab: "Mes tâches",
description_alert:
"Liste des tâches auxquelles je suis assigné et dont la date de rappel est dépassée.",
description_warning:
"Liste des tâches auxquelles je suis assigné et dont la date d'échéance est dépassée.",
},
my_accompanying_courses: {
tab: "Mes nouveaux parcours",
description:
"Liste des parcours d'accompagnement que l'on vient de m'attribuer depuis moins de 15 jours.",
},
my_notifications: {
tab: "Mes nouvelles notifications",
description: "Liste des notifications reçues et non lues.",
},
my_workflows: {
tab: "Mes workflows",
description: "Liste des workflows en attente d'une action.",
description_cc: "Liste des workflows dont je suis en copie.",
},
opening_date: "Date d'ouverture",
social_issues: "Problématiques sociales",
concerned_persons: "Usagers concernés",
max_date: "Date d'échéance",
warning_date: "Date de rappel",
evaluation: "Évaluation",
task: "Tâche",
Date: "Date",
From: "Expéditeur",
Subject: "Objet",
Entity: "Associé à",
Step: "Étape",
concerned_users: "Usagers concernés",
Object_workflow: "Objet du workflow",
on_hold: "En attente",
show_entity: "Voir {entity}",
the_activity: "l'échange",
the_course: "le parcours",
the_action: "l'action",
the_evaluation: "l'évaluation",
the_evaluation_document: "le document",
the_task: "la tâche",
the_workflow: "le workflow",
StartDate: "Date d'ouverture",
SocialAction: "Action d'accompagnement",
no_data: "Aucun résultats",
no_dashboard: "Pas de tableaux de bord",
counter: {
unread_notifications:
"{n} notification non lue | {n} notifications non lues",
assignated_courses:
"{n} parcours récent assigné | {n} parcours récents assignés",
assignated_actions: "{n} action assignée | {n} actions assignées",
assignated_evaluations:
"{n} évaluation assignée | {n} évaluations assignées",
alert_tasks: "{n} tâche en rappel | {n} tâches en rappel",
warning_tasks: "{n} tâche à échéance | {n} tâches à échéance",
},
emergency: "Urgent",
confidential: "Confidentiel",
automatic_notification: "Notification automatique",
widget: {
news: {
title: "Actualités",
readMore: "Lire la suite",
date: "Date",
none: "Aucune actualité",
},
},
},
};
Object.assign(appMessages.fr);
export {
appMessages
};
export { appMessages };

View File

@@ -1,6 +1,6 @@
<template>
<ul :class="listClasses" v-if="picked.length && displayPicked">
<li v-for="p in picked" @click="removeEntity(p)" :key="p.type+p.id">
<li v-for="p in picked" @click="removeEntity(p)" :key="p.type + p.id">
<span class="chill_denomination">{{ p.text }}</span>
</li>
</ul>
@@ -18,7 +18,9 @@
</li>
</ul>
<ul class="list-suggest add-items inline">
<li v-for="s in suggested" :key="s.id" @click="addNewSuggested(s)"><span>{{ s.text }}</span></li>
<li v-for="s in suggested" :key="s.id" @click="addNewSuggested(s)">
<span>{{ s.text }}</span>
</li>
</ul>
</template>
@@ -49,86 +51,92 @@ export default {
default: true,
},
displayPicked: {
// display picked entities.
type: Boolean,
default: true,
// display picked entities.
type: Boolean,
default: true,
},
suggested: {
type: Array,
default: []
type: Array,
default: [],
},
label: {
type: String,
required: false,
}
},
},
emits: ['addNewEntity', 'removeEntity', 'addNewEntityProcessEnded'],
emits: ["addNewEntity", "removeEntity", "addNewEntityProcessEnded"],
components: {
AddPersons,
},
data() {
return {
key: ''
key: "",
};
},
computed: {
addPersonsOptions() {
return {
uniq: !this.multiple,
type: this.types,
priority: null,
button: {
size: 'btn-sm',
class: 'btn-submit',
},
};
},
translatedListOfTypes() {
if (this.label !== '') {
return this.label;
}
addPersonsOptions() {
return {
uniq: !this.multiple,
type: this.types,
priority: null,
button: {
size: "btn-sm",
class: "btn-submit",
},
};
},
translatedListOfTypes() {
if (this.label !== "") {
return this.label;
}
let trans = [];
this.types.forEach(t => {
if (this.$props.multiple) {
trans.push(appMessages.fr.pick_entity[t].toLowerCase());
} else {
trans.push(appMessages.fr.pick_entity[t + '_one'].toLowerCase());
}
})
let trans = [];
this.types.forEach((t) => {
if (this.$props.multiple) {
trans.push(appMessages.fr.pick_entity[t].toLowerCase());
} else {
trans.push(
appMessages.fr.pick_entity[t + "_one"].toLowerCase(),
);
}
});
if (this.$props.multiple) {
return appMessages.fr.pick_entity.modal_title + trans.join(', ');
} else {
return appMessages.fr.pick_entity.modal_title_one + trans.join(', ');
}
},
listClasses() {
return {
'list-suggest': true,
'remove-items': this.$props.removableIfSet,
};
},
if (this.$props.multiple) {
return (
appMessages.fr.pick_entity.modal_title + trans.join(", ")
);
} else {
return (
appMessages.fr.pick_entity.modal_title_one +
trans.join(", ")
);
}
},
listClasses() {
return {
"list-suggest": true,
"remove-items": this.$props.removableIfSet,
};
},
},
methods: {
addNewSuggested(entity) {
this.$emit('addNewEntity', {entity: entity});
},
addNewEntity({ selected, modal }) {
selected.forEach((item) => {
this.$emit('addNewEntity', { entity: item.result});
}, this
);
this.$refs.addPersons.resetSearch(); // to cast child method
modal.showModal = false;
this.$emit('addNewEntityProcessEnded');
},
removeEntity(entity) {
if (!this.$props.removableIfSet) {
return;
}
this.$emit('removeEntity',{ entity: entity });
}
addNewSuggested(entity) {
this.$emit("addNewEntity", { entity: entity });
},
addNewEntity({ selected, modal }) {
selected.forEach((item) => {
this.$emit("addNewEntity", { entity: item.result });
}, this);
this.$refs.addPersons.resetSearch(); // to cast child method
modal.showModal = false;
this.$emit("addNewEntityProcessEnded");
},
removeEntity(entity) {
if (!this.$props.removableIfSet) {
return;
}
this.$emit("removeEntity", { entity: entity });
},
},
}
};
</script>

View File

@@ -1,6 +1,6 @@
<script setup lang="ts">
import {UserGroup} from "../../../types";
import {computed} from "vue";
import { UserGroup } from "../../../types";
import { computed } from "vue";
interface UserGroupRenderBoxProps {
userGroup: UserGroup;
@@ -8,19 +8,18 @@ interface UserGroupRenderBoxProps {
const props = defineProps<UserGroupRenderBoxProps>();
const styles = computed<{color: string, "background-color": string}>(() => {
const styles = computed<{ color: string; "background-color": string }>(() => {
return {
color: props.userGroup.foregroundColor,
"background-color": props.userGroup.backgroundColor,
}
};
});
</script>
<template>
<span class="badge-user-group" :style="styles">{{ userGroup.label.fr }}</span>
<span class="badge-user-group" :style="styles">{{
userGroup.label.fr
}}</span>
</template>
<style scoped lang="scss">
</style>
<style scoped lang="scss"></style>

View File

@@ -1,140 +1,163 @@
<template>
<div class="flex-table workflow" id="workflow-list">
<div v-for="(w, i) in workflows" :key="`workflow-${i}`"
class="item-bloc">
<div class="flex-table workflow" id="workflow-list">
<div
v-for="(w, i) in workflows"
:key="`workflow-${i}`"
class="item-bloc"
>
<div>
<div class="item-row col">
<h2>{{ w.title }}</h2>
<div class="flex-grow-1 ms-3 h3">
<div class="visually-hidden">
{{ w.relatedEntityClass }}
{{ w.relatedEntityId }}
</div>
</div>
</div>
<div>
<div class="item-row col">
<h2>{{ w.title }}</h2>
<div class="flex-grow-1 ms-3 h3">
<div class="visually-hidden">
{{ w.relatedEntityClass }}
{{ w.relatedEntityId }}
</div>
</div>
<div class="breadcrumb">
<template v-for="(step, j) in w.steps" :key="`step-${j}`">
<span
class="mx-2"
tabindex="0"
data-bs-trigger="focus hover"
data-bs-toggle="popover"
data-bs-placement="bottom"
data-bs-custom-class="workflow-transition"
:title="getPopTitle(step)"
:data-bs-content="getPopContent(step)"
>
<i
v-if="step.currentStep.name === 'initial'"
class="fa fa-circle me-1 text-chill-yellow"
>
</i>
<i
v-if="step.isFreezed"
class="fa fa-snowflake-o fa-sm me-1"
>
</i>
{{ step.currentStep.text }}
</span>
<span v-if="j !== Object.keys(w.steps).length - 1">
</span>
</template>
</div>
<span
v-if="w.isOnHoldAtCurrentStep"
class="badge bg-success rounded-pill"
>{{ $t("on_hold") }}</span
>
</div>
<div class="breadcrumb">
<template v-for="(step, j) in w.steps" :key="`step-${j}`">
<span class="mx-2"
tabindex="0"
data-bs-trigger="focus hover"
data-bs-toggle="popover"
data-bs-placement="bottom"
data-bs-custom-class="workflow-transition"
:title="getPopTitle(step)"
:data-bs-content="getPopContent(step)">
<i v-if="step.currentStep.name === 'initial'"
class="fa fa-circle me-1 text-chill-yellow">
</i>
<i v-if="step.isFreezed"
class="fa fa-snowflake-o fa-sm me-1">
</i>
{{ step.currentStep.text }}
</span>
<span v-if="j !== Object.keys(w.steps).length - 1">
</span>
</template>
<div class="item-row">
<div class="item-col flex-grow-1">
<p v-if="isUserSubscribedToStep(w)">
<i class="fa fa-check fa-fw"></i>
{{ $t("you_subscribed_to_all_steps") }}
</p>
<p v-if="isUserSubscribedToFinal(w)">
<i class="fa fa-check fa-fw"></i>
{{ $t("you_subscribed_to_final_step") }}
</p>
</div>
<div class="item-col">
<ul class="record_actions">
<li>
<a
:href="goToUrl(w)"
class="btn btn-sm btn-show"
:title="$t('action.show')"
></a>
</li>
</ul>
</div>
</div>
<span v-if="w.isOnHoldAtCurrentStep" class="badge bg-success rounded-pill">{{ $t('on_hold') }}</span>
</div>
<div class="item-row">
<div class="item-col flex-grow-1">
<p v-if="isUserSubscribedToStep(w)">
<i class="fa fa-check fa-fw"></i>
{{ $t('you_subscribed_to_all_steps') }}
</p>
<p v-if="isUserSubscribedToFinal(w)">
<i class="fa fa-check fa-fw"></i>
{{ $t('you_subscribed_to_final_step') }}
</p>
</div>
<div class="item-col">
<ul class="record_actions">
<li>
<a :href="goToUrl(w)" class="btn btn-sm btn-show" :title="$t('action.show')"></a>
</li>
</ul>
</div>
</div>
</div>
</div>
</div>
</div>
</template>
<script>
import Popover from 'bootstrap/js/src/popover';
import Popover from "bootstrap/js/src/popover";
const i18n = {
messages: {
fr: {
you_subscribed_to_all_steps: "Vous recevrez une notification à chaque étape",
you_subscribed_to_final_step: "Vous recevrez une notification à l'étape finale",
by: "Par",
at: "Le",
on_hold: "En attente"
}
}
}
messages: {
fr: {
you_subscribed_to_all_steps:
"Vous recevrez une notification à chaque étape",
you_subscribed_to_final_step:
"Vous recevrez une notification à l'étape finale",
by: "Par",
at: "Le",
on_hold: "En attente",
},
},
};
export default {
name: "ListWorkflow",
i18n: i18n,
props: {
workflows: {
type: Array,
required: true,
}
},
methods: {
goToUrl(w) {
return `/fr/main/workflow/${w.id}/show`;
},
getPopTitle(step) {
if (step.transitionPrevious != null) {
//console.log(step.transitionPrevious.text);
let freezed = step.isFreezed ? `<i class="fa fa-snowflake-o fa-sm me-1"></i>` : ``;
return `${freezed}${step.transitionPrevious.text}`;
}
},
getPopContent(step) {
if (step.transitionPrevious != null) {
if (step.transitionPreviousBy !== null) {
return `<ul class="small_in_title">
name: "ListWorkflow",
i18n: i18n,
props: {
workflows: {
type: Array,
required: true,
},
},
methods: {
goToUrl(w) {
return `/fr/main/workflow/${w.id}/show`;
},
getPopTitle(step) {
if (step.transitionPrevious != null) {
//console.log(step.transitionPrevious.text);
let freezed = step.isFreezed
? `<i class="fa fa-snowflake-o fa-sm me-1"></i>`
: ``;
return `${freezed}${step.transitionPrevious.text}`;
}
},
getPopContent(step) {
if (step.transitionPrevious != null) {
if (step.transitionPreviousBy !== null) {
return `<ul class="small_in_title">
<li><span class="item-key">${i18n.messages.fr.by} : </span><b>${step.transitionPreviousBy.text}</b></li>
<li><span class="item-key">${i18n.messages.fr.at} : </span><b>${this.formatDate(step.transitionPreviousAt.datetime)}</b></li>
</ul>`
;
} else {
return `<ul class="small_in_title">
</ul>`;
} else {
return `<ul class="small_in_title">
<li><span class="item-key">${i18n.messages.fr.at} : </span><b>${this.formatDate(step.transitionPreviousAt.datetime)}</b></li>
</ul>`
}
}
},
formatDate(datetime) {
return datetime.split('T')[0] +' '+ datetime.split('T')[1].substring(0,5)
},
isUserSubscribedToStep(w) {
// todo
return false;
},
isUserSubscribedToFinal(w) {
// todo
return false;
},
},
mounted() {
const triggerList = [].slice.call(document.querySelectorAll('[data-bs-toggle="popover"]'));
const popoverList = triggerList.map(function (el) {
//console.log('popover', el)
return new Popover(el, {
html: true,
});
});
}
}
</ul>`;
}
}
},
formatDate(datetime) {
return (
datetime.split("T")[0] +
" " +
datetime.split("T")[1].substring(0, 5)
);
},
isUserSubscribedToStep(w) {
// todo
return false;
},
isUserSubscribedToFinal(w) {
// todo
return false;
},
},
mounted() {
const triggerList = [].slice.call(
document.querySelectorAll('[data-bs-toggle="popover"]'),
);
const popoverList = triggerList.map(function (el) {
//console.log('popover', el)
return new Popover(el, {
html: true,
});
});
},
};
</script>

View File

@@ -1,126 +1,129 @@
<template>
<pick-workflow
:relatedEntityClass="this.relatedEntityClass"
:relatedEntityId="this.relatedEntityId"
:workflowsAvailables="workflowsAvailables"
:preventDefaultMoveToGenerate="this.$props.preventDefaultMoveToGenerate"
:goToGenerateWorkflowPayload="this.goToGenerateWorkflowPayload"
:countExistingWorkflows="countWorkflows"
@go-to-generate-workflow="goToGenerateWorkflow"
@click-open-list="openModal"
></pick-workflow>
<pick-workflow
:relatedEntityClass="this.relatedEntityClass"
:relatedEntityId="this.relatedEntityId"
:workflowsAvailables="workflowsAvailables"
:preventDefaultMoveToGenerate="this.$props.preventDefaultMoveToGenerate"
:goToGenerateWorkflowPayload="this.goToGenerateWorkflowPayload"
:countExistingWorkflows="countWorkflows"
@go-to-generate-workflow="goToGenerateWorkflow"
@click-open-list="openModal"
></pick-workflow>
<teleport to="body">
<modal v-if="modal.showModal"
:modalDialogClass="modal.modalDialogClass"
@close="modal.showModal = false">
<teleport to="body">
<modal
v-if="modal.showModal"
:modalDialogClass="modal.modalDialogClass"
@close="modal.showModal = false"
>
<template v-slot:header>
<h2 class="modal-title">{{ $t("workflow_list") }}</h2>
</template>
<template v-slot:header>
<h2 class="modal-title">{{ $t('workflow_list') }}</h2>
</template>
<template v-slot:body>
<list-workflow-vue :workflows="workflows"></list-workflow-vue>
</template>
<template v-slot:body>
<list-workflow-vue
:workflows="workflows"
></list-workflow-vue>
</template>
<template v-slot:footer>
<pick-workflow v-if="allowCreate"
:relatedEntityClass="this.relatedEntityClass"
:relatedEntityId="this.relatedEntityId"
:workflowsAvailables="workflowsAvailables"
:preventDefaultMoveToGenerate="this.$props.preventDefaultMoveToGenerate"
:goToGenerateWorkflowPayload="this.goToGenerateWorkflowPayload"
:countExistingWorkflows="countWorkflows"
:embedded-within-list-modal="true"
@go-to-generate-workflow="this.goToGenerateWorkflow"
></pick-workflow>
</template>
</modal>
</teleport>
<template v-slot:footer>
<pick-workflow
v-if="allowCreate"
:relatedEntityClass="this.relatedEntityClass"
:relatedEntityId="this.relatedEntityId"
:workflowsAvailables="workflowsAvailables"
:preventDefaultMoveToGenerate="
this.$props.preventDefaultMoveToGenerate
"
:goToGenerateWorkflowPayload="
this.goToGenerateWorkflowPayload
"
:countExistingWorkflows="countWorkflows"
:embedded-within-list-modal="true"
@go-to-generate-workflow="this.goToGenerateWorkflow"
></pick-workflow>
</template>
</modal>
</teleport>
</template>
<script>
import Modal from 'ChillMainAssets/vuejs/_components/Modal';
import PickWorkflow from 'ChillMainAssets/vuejs/_components/EntityWorkflow/PickWorkflow.vue';
import ListWorkflowVue from 'ChillMainAssets/vuejs/_components/EntityWorkflow/ListWorkflow.vue';
import Modal from "ChillMainAssets/vuejs/_components/Modal";
import PickWorkflow from "ChillMainAssets/vuejs/_components/EntityWorkflow/PickWorkflow.vue";
import ListWorkflowVue from "ChillMainAssets/vuejs/_components/EntityWorkflow/ListWorkflow.vue";
export default {
name: "ListWorkflowModal",
components: {
Modal,
PickWorkflow,
ListWorkflowVue
},
emits: ['goToGenerateWorkflow'],
props: {
workflows: {
type: Array,
required: true,
},
allowCreate: {
type: Boolean,
required: true,
},
relatedEntityClass: {
type: String,
required: true,
},
relatedEntityId: {
type: Number,
required: false,
},
workflowsAvailables: {
type: Array,
required: true,
},
preventDefaultMoveToGenerate: {
type: Boolean,
required: false,
default: false,
},
goToGenerateWorkflowPayload: {
required: false,
default: {}
},
},
name: "ListWorkflowModal",
components: {
Modal,
PickWorkflow,
ListWorkflowVue,
},
emits: ["goToGenerateWorkflow"],
props: {
workflows: {
type: Array,
required: true,
},
allowCreate: {
type: Boolean,
required: true,
},
relatedEntityClass: {
type: String,
required: true,
},
relatedEntityId: {
type: Number,
required: false,
},
workflowsAvailables: {
type: Array,
required: true,
},
preventDefaultMoveToGenerate: {
type: Boolean,
required: false,
default: false,
},
goToGenerateWorkflowPayload: {
required: false,
default: {},
},
},
data() {
return {
modal: {
showModal: false,
modalDialogClass: "modal-dialog-scrollable modal-xl"
},
}
},
computed: {
countWorkflows() {
return this.workflows.length;
},
hasWorkflow() {
return this.countWorkflows > 0;
}
},
methods: {
openModal() {
this.modal.showModal = true;
},
goToGenerateWorkflow(data) {
console.log('go to generate workflow intercepted', data);
this.$emit('goToGenerateWorkflow', data);
}
},
i18n: {
messages: {
fr: {
workflow_list: "Liste des workflows associés",
workflow: " workflow associé",
workflows: " workflows associés",
}
}
}
}
return {
modal: {
showModal: false,
modalDialogClass: "modal-dialog-scrollable modal-xl",
},
};
},
computed: {
countWorkflows() {
return this.workflows.length;
},
hasWorkflow() {
return this.countWorkflows > 0;
},
},
methods: {
openModal() {
this.modal.showModal = true;
},
goToGenerateWorkflow(data) {
console.log("go to generate workflow intercepted", data);
this.$emit("goToGenerateWorkflow", data);
},
},
i18n: {
messages: {
fr: {
workflow_list: "Liste des workflows associés",
workflow: " workflow associé",
workflows: " workflows associés",
},
},
},
};
</script>
<style scoped></style>

View File

@@ -1,12 +1,27 @@
<template>
<template v-if="props.workflowsAvailables.length >= 1">
<div v-if="countExistingWorkflows == 0 || embeddedWithinListModal" class="dropdown d-grid gap-2">
<button class="btn btn-primary dropdown-toggle" type="button" id="createWorkflowButton" data-bs-toggle="dropdown" aria-expanded="false">
<div
v-if="countExistingWorkflows == 0 || embeddedWithinListModal"
class="dropdown d-grid gap-2"
>
<button
class="btn btn-primary dropdown-toggle"
type="button"
id="createWorkflowButton"
data-bs-toggle="dropdown"
aria-expanded="false"
>
Créer un workflow
</button>
<ul class="dropdown-menu" aria-labelledby="createWorkflowButton">
<li v-for="w in props.workflowsAvailables" :key="w.name">
<button class="dropdown-item" type="button" @click.prevent="goToGenerateWorkflow($event, w.name)">{{ w.text }}</button>
<button
class="dropdown-item"
type="button"
@click.prevent="goToGenerateWorkflow($event, w.name)"
>
{{ w.text }}
</button>
</li>
</ul>
</div>
@@ -20,12 +35,31 @@
{{ countExistingWorkflows }} workflows associés
</template>
</button>
<button class="btn btn-primary dropdown-toggle dropdown-toggle-split" type="button" id="createWorkflowButton" data-bs-toggle="dropdown" aria-expanded="false">
<span class="visually-hidden">Liste des workflows disponibles</span>
<button
class="btn btn-primary dropdown-toggle dropdown-toggle-split"
type="button"
id="createWorkflowButton"
data-bs-toggle="dropdown"
aria-expanded="false"
>
<span class="visually-hidden"
>Liste des workflows disponibles</span
>
</button>
<ul class="dropdown-menu" aria-labelledby="createWorkflowButton">
<ul
class="dropdown-menu"
aria-labelledby="createWorkflowButton"
>
<li v-for="w in props.workflowsAvailables" :key="w.name">
<button class="dropdown-item" type="button" @click.prevent="goToGenerateWorkflow($event, w.name)">{{ w.text }}</button>
<button
class="dropdown-item"
type="button"
@click.prevent="
goToGenerateWorkflow($event, w.name)
"
>
{{ w.text }}
</button>
</li>
</ul>
</div>
@@ -33,7 +67,14 @@
</template>
<template v-else>
<div v-if="countExistingWorkflows > 0" class="dropdown d-grid gap-2">
<button @click="emit('clickOpenList')" class="btn btn-primary" type="button" id="createWorkflowButton" data-bs-toggle="dropdown" aria-expanded="false">
<button
@click="emit('clickOpenList')"
class="btn btn-primary"
type="button"
id="createWorkflowButton"
data-bs-toggle="dropdown"
aria-expanded="false"
>
<template v-if="countExistingWorkflows === 1">
1 workflow associé
</template>
@@ -46,9 +87,8 @@
</template>
<script setup lang="ts">
import {buildLinkCreate} from '../../../lib/entity-workflow/api';
import {WorkflowAvailable} from "../../../types";
import { buildLinkCreate } from "../../../lib/entity-workflow/api";
import { WorkflowAvailable } from "../../../types";
interface PickWorkflowConfig {
relatedEntityClass: string;
@@ -58,7 +98,7 @@ interface PickWorkflowConfig {
* if the related entity is not specified or available, for instance when the entity is created within
* the interface and the id will be available later
*/
relatedEntityId: number|undefined;
relatedEntityId: number | undefined;
workflowsAvailables: WorkflowAvailable[];
preventDefaultMoveToGenerate: boolean;
goToGenerateWorkflowPayload: object;
@@ -69,39 +109,68 @@ interface PickWorkflowConfig {
embeddedWithinListModal: boolean;
}
const props = withDefaults(defineProps<PickWorkflowConfig>(), {preventDefaultMoveToGenerate: false, goToGenerateWorkflowPayload: {}, allowCreateWorkflow: false});
const props = withDefaults(defineProps<PickWorkflowConfig>(), {
preventDefaultMoveToGenerate: false,
goToGenerateWorkflowPayload: {},
allowCreateWorkflow: false,
});
const emit = defineEmits<{
(e: 'goToGenerateWorkflow', {event: MouseEvent, workflowName: string, isLinkValid: boolean, link: string, payload: object}): void;
(e: 'clickOpenList'): void;
(
e: "goToGenerateWorkflow",
{
event: MouseEvent,
workflowName: string,
isLinkValid: boolean,
link: string,
payload: object,
},
): void;
(e: "clickOpenList"): void;
}>();
const makeLink = (workflowName: string): string => buildLinkCreate(workflowName, props.relatedEntityClass, props.relatedEntityId);
const makeLink = (workflowName: string): string =>
buildLinkCreate(
workflowName,
props.relatedEntityClass,
props.relatedEntityId,
);
const goToGenerateWorkflow = (event: MouseEvent, workflowName: string): void => {
console.log('goToGenerateWorkflow', event, workflowName);
let link = '';
const goToGenerateWorkflow = (
event: MouseEvent,
workflowName: string,
): void => {
console.log("goToGenerateWorkflow", event, workflowName);
let link = "";
let isLinkValid = false;
try {
link = makeLink(workflowName);
isLinkValid = true;
} catch (e) {
console.info("could not generate link to create workflow, maybe the relatedEntityId is not yet known", e);
console.info(
"could not generate link to create workflow, maybe the relatedEntityId is not yet known",
e,
);
}
if (!props.preventDefaultMoveToGenerate) {
window.location.assign(link);
}
emit('goToGenerateWorkflow', {event, workflowName, link, isLinkValid, payload: props.goToGenerateWorkflowPayload});
}
emit("goToGenerateWorkflow", {
event,
workflowName,
link,
isLinkValid,
payload: props.goToGenerateWorkflowPayload,
});
};
const goToDuplicateRelatedEntity = (event: MouseEvent, workflowName: string): void => {
}
const goToDuplicateRelatedEntity = (
event: MouseEvent,
workflowName: string,
): void => {};
</script>
<style scoped>
</style>
<style scoped></style>