Skip to content
Snippets Groups Projects
Commit 225e79e0 authored by Camille Blanchon's avatar Camille Blanchon
Browse files

Merge branch 'redmine-issues/19723' into 'develop'

REDMINE_ISSUE-19723 | Sélectionner les filtres « classiques » à afficher sur l’accueil projet

See merge request !758
parents 8be60cee 243a87fd
No related branches found
No related tags found
1 merge request!758REDMINE_ISSUE-19723 | Sélectionner les filtres « classiques » à afficher sur l’accueil projet
<template> <template>
<Multiselect <Multiselect
v-model="selection" v-model="selection"
:class="{ multiple }"
:options="options" :options="options"
:allow-empty="true" :allow-empty="true"
track-by="label" track-by="label"
...@@ -157,3 +158,9 @@ export default { ...@@ -157,3 +158,9 @@ export default {
} }
}; };
</script> </script>
<style>
#filters-container .multiple .multiselect__option--selected:not(:hover) {
background-color: #e8e8e8 !important;
}
</style>
\ No newline at end of file
<template> <template>
<div <div
id="filters-container" id="filters-container"
v-if="displayedClassicFilters || displayedAttributeFilters"
class="margin-bottom" class="margin-bottom"
> >
<div <div
...@@ -19,39 +20,25 @@ ...@@ -19,39 +20,25 @@
</div> </div>
</div> </div>
<div :class="['full-width', 'filters', { 'hidden': displayFilters }]"> <div :class="['full-width', 'filters', { 'hidden': displayFilters }]">
<div class="ui menu filter-row"> <div
<div class="item"> v-if="displayedClassicFilters.length > 0"
class="ui menu filter-row"
>
<div
v-for="filter in displayedClassicFilters"
:key="filter.name"
class="item"
>
<label> <label>
Niveau d'autorisation requis {{ filter.label }}
</label> </label>
<DropdownMenuItem <search-projects
:options="accessLevelOptions" v-if="filter.name === 'search'"
v-on="$listeners" v-on="$listeners"
/> />
</div>
<div class="item">
<label>
Mon niveau d'autorisation
</label>
<DropdownMenuItem <DropdownMenuItem
:options="userAccessLevelOptions" v-else
v-on="$listeners" :options="filter.options"
/>
</div>
<div class="item">
<label>
Modération
</label>
<DropdownMenuItem
:options="moderationOptions"
v-on="$listeners"
/>
</div>
<div class="item">
<label>
Recherche par nom
</label>
<search-projects
v-on="$listeners" v-on="$listeners"
/> />
</div> </div>
...@@ -101,83 +88,115 @@ export default { ...@@ -101,83 +88,115 @@ export default {
data() { data() {
return { return {
displayFilters: false, displayFilters: false,
moderationOptions: [ classicFilters: [
{
label: 'Tous',
filter: 'moderation',
value: null
},
{
label: 'Projet modéré',
filter: 'moderation',
value: 'true'
},
{
label: 'Projet non modéré',
filter: 'moderation',
value: 'false'
},
],
accessLevelOptions: [
{
label: 'Tous',
filter: 'access_level',
value: null
},
{
label: 'Utilisateur anonyme',
filter: 'access_level',
value: 'anonymous'
},
{
label: 'Utilisateur connecté',
filter: 'access_level',
value: 'logged_user'
},
{
label: 'Contributeur',
filter: 'access_level',
value: 'contributor'
},
],
userAccessLevelOptions: [
{ {
label: 'Tous', name: 'access_level',
filter: 'user_access_level', label: 'Niveau d\'autorisation requis',
value: null options: [
{
label: 'Utilisateur anonyme',
value: 'anonymous'
},
{
label: 'Utilisateur connecté',
value: 'logged_user'
},
{
label: 'Contributeur',
value: 'contributor'
},
],
}, },
{ {
label: 'Utilisateur connecté', name: 'user_access_level',
filter: 'user_access_level', label: 'Mon niveau d\'autorisation',
value: '1' options: [
{
label: 'Utilisateur connecté',
value: '1'
},
{
label: 'Contributeur',
value: '2'
},
{
label: 'Super contributeur',
value: '3'
},
{
label: 'Modérateur',
value: '4'
},
{
label: 'Administrateur projet',
value: '5'
},
],
}, },
{ {
label: 'Contributeur', name: 'moderation',
filter: 'user_access_level', label: 'Modération',
value: '2' options: [
{
label: 'Projet modéré',
value: 'true'
},
{
label: 'Projet non modéré',
value: 'false'
},
]
}, },
{ {
label: 'Super contributeur', name: 'search',
filter: 'user_access_level', label: 'Recherche par nom',
value: '3' }
},
{
label: 'Modérateur',
filter: 'user_access_level',
value: '4'
},
{
label: 'Administrateur projet',
filter: 'user_access_level',
value: '5'
},
], ],
attributesFilter: {}, attributesFilter: {},
}; };
}, },
computed: { computed: {
...mapState(['user', 'projectAttributes']), ...mapState([
'user',
'configuration',
'projectAttributes'
]),
/**
* Processes project filters to prepare them for display.
* It also adds a global 'Tous' (All) option to each attribute's options for filtering purposes.
*
* @returns {Array} An array of filter objects with modified options for display.
*/
displayedClassicFilters() {
const projectFilters = this.configuration.VUE_APP_PROJECT_FILTERS.split(',');
// Filter filters to be displayed according to configuration and process filters
const processedFilters = this.classicFilters.filter(filter => projectFilters.includes(filter.name))
.map(filter => {
if (filter.options) {
// if user is not connected display its user access level corresponding to anonymous user
if (!this.user && filter.name ==='user_access_level') {
filter.options.unshift({
label: 'Utilisateur anonyme',
value: '0'
});
}
// Format the options to be displayed by dropdowns
const options = this.generateFilterOptions(filter);
// Add the global option at beginning
options.unshift({
label: 'Tous',
filter: filter.name,
value: null,
});
return { ...filter, options };
} else { // Search input field doesn't take options
return filter;
}
});
return processedFilters;
},
/** /**
* Processes project attributes to prepare them for display, adjusting the options based on the attribute type. * Processes project attributes to prepare them for display, adjusting the options based on the attribute type.
* For boolean attributes, it creates specific options for true and false values. * For boolean attributes, it creates specific options for true and false values.
...@@ -190,7 +209,9 @@ export default { ...@@ -190,7 +209,9 @@ export default {
// Filter and process attributes // Filter and process attributes
const processedAttributes = this.projectAttributes.filter(attribute => attribute.display_filter) const processedAttributes = this.projectAttributes.filter(attribute => attribute.display_filter)
.map(attribute => { .map(attribute => {
const options = this.generateOptionsForAttribute(attribute); // Format the options to be displayed by dropdowns
const options = this.generateFilterOptions(attribute);
// Add the global option at beginning
options.unshift({ options.unshift({
label: 'Tous', label: 'Tous',
filter: attribute.id, filter: attribute.id,
...@@ -204,16 +225,6 @@ export default { ...@@ -204,16 +225,6 @@ export default {
}, },
}, },
created() {
if (!this.user) {
this.userAccessLevelOptions.splice(1, 0, {
label: 'Utilisateur anonyme',
filter: 'user_access_level',
value: '0'
});
}
},
methods: { methods: {
/** /**
* Helper function to chunk an array into smaller arrays of a specified size. * Helper function to chunk an array into smaller arrays of a specified size.
...@@ -231,27 +242,27 @@ export default { ...@@ -231,27 +242,27 @@ export default {
}, },
/** /**
* Generates options for a given attribute based on its field type. * Generates options for a given filter.
* It handles boolean attributes specially by creating explicit true/false options. * It handles boolean attributes specially by creating explicit true/false options.
* Other attribute types use their predefined options. * Other attribute types use their predefined options.
* *
* @param {Object} attribute - The project attribute for which to generate options. * @param {Object} attribute - The project attribute for which to generate options.
* @returns {Array} An array of options for the given attribute. * @returns {Array} An array of options for the given attribute.
*/ */
generateOptionsForAttribute(attribute) { generateFilterOptions(filter) {
// Handle boolean attributes specially by creating true/false options // Handle boolean attributes specially by creating true/false options
if (attribute.field_type === 'boolean') { if (filter.field_type === 'boolean') {
return [ return [
{ filter: attribute.id, label: 'Oui', value: 'true' }, { filter: filter.id, label: 'Oui', value: 'true' },
{ filter: attribute.id, label: 'Non', value: 'false' }, { filter: filter.id, label: 'Non', value: 'false' },
]; ];
} }
// For other attribute types, map each option to the expected format // For other filter types, map each option to the expected format
return attribute.options.map(option => ({ return filter.options.map(option => ({
filter: attribute.id, filter: filter.id || filter.name,
label: option, label: option.label || option,
value: option, value: option.value || option,
})); }));
}, },
......
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment