From d0a9a7b5f41d6624211e37c7ff9c584f207c4ac8 Mon Sep 17 00:00:00 2001 From: Stanislas Kita Date: Mon, 6 Oct 2025 15:48:06 +0200 Subject: [PATCH 1/5] Fix(UI): fix UI --- CHANGELOG.md | 8 ++++++++ inc/container.class.php | 10 ++++------ inc/field.class.php | 30 ++++++++++++------------------ templates/fields.html.twig | 18 ++++++++++-------- 4 files changed, 34 insertions(+), 32 deletions(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index e77b78ef..1c35812b 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -5,6 +5,14 @@ All notable changes to this project will be documented in this file. The format is based on [Keep a Changelog](http://keepachangelog.com/) and this project adheres to [Semantic Versioning](http://semver.org/). + +## ['UNRELEASED'] + +### Fixed + +- Fix UI with GLPI 11 +- Fix `tab` container not displayed + ## [1.22.0] - 2025-09-30 ### Added diff --git a/inc/container.class.php b/inc/container.class.php index dc448ff4..af804251 100644 --- a/inc/container.class.php +++ b/inc/container.class.php @@ -1240,13 +1240,12 @@ public function getTabNameForItem(CommonGLPI $item, $withtemplate = 0) if (!$item->isEntityAssign() || in_array($item->fields['entities_id'], $entities)) { $display_condition = new PluginFieldsContainerDisplayCondition(); if ($display_condition->computeDisplayContainer($item, $data['id'])) { - $tabs_entries[$tab_name] = self::createTabEntry($data['label'], 0, null, PluginFieldsContainer::getIcon()); + $tabs_entries[$data['id']] = self::createTabEntry($data['label'], 0, null, PluginFieldsContainer::getIcon()); } } } } } - return $tabs_entries; } @@ -1262,11 +1261,10 @@ public static function displayTabContentForItem(CommonGLPI $item, $tabnum = 1, $ //retrieve container for current tab $container = new self(); - $found_c = $container->find(['type' => 'tab', 'name' => $tabnum, 'is_active' => 1]); - foreach ($found_c as $data) { - $dataitemtypes = json_decode($data['itemtypes']); + if ($container->getFromDB($tabnum)) { + $dataitemtypes = json_decode($container->fields['itemtypes']); if (in_array(get_class($item), $dataitemtypes) != false) { - return PluginFieldsField::showForTabContainer($data['id'], $item); + return PluginFieldsField::showForTabContainer($container->fields['id'], $item); } } diff --git a/inc/field.class.php b/inc/field.class.php index 21b5dfc4..6e6a2927 100644 --- a/inc/field.class.php +++ b/inc/field.class.php @@ -826,21 +826,19 @@ public static function showForTabContainer($c_id, $item) //get fields for this container $field_obj = new self(); $fields = $field_obj->find(['plugin_fields_containers_id' => $c_id, 'is_active' => 1], 'ranking'); - echo "
"; + echo ""; echo Html::hidden('plugin_fields_containers_id', ['value' => $c_id]); echo Html::hidden('items_id', ['value' => $item->getID()]); echo Html::hidden('itemtype', ['value' => $item->getType()]); - echo ""; echo self::prepareHtmlFields($fields, $item, $canedit); if ($canedit) { - echo "'; } - echo '
"; + echo "
"; echo ""; echo '
'; Html::closeForm(); return true; @@ -960,17 +958,15 @@ public static function showForTab($params) return; } + $class = match (true) { + !($item instanceof CommonITILObject) && $item instanceof CommonDropdown => 'card-body row', + // @phpstan-ignore-next-line -> Instanceof between CommonDBTM and CommonDropdown will always evaluate to false. + !($item instanceof CommonITILObject) && !($item instanceof CommonDropdown) => 'card-body d-flex flex-wrap', // lign 969 + default => '', + }; $html_id = 'plugin_fields_container_' . mt_rand(); - if (str_contains($current_url, 'helpdesk.public.php')) { - echo "
"; - echo "
"; - $field_options = [ - 'label_class' => 'col-lg-3', - 'input_class' => 'col-lg-9', - ]; - } else { - echo "
"; - } + + echo "
"; $display_condition = new PluginFieldsContainerDisplayCondition(); if ($display_condition->computeDisplayContainer($item, $c_id)) { self::showDomContainer( @@ -978,12 +974,9 @@ public static function showForTab($params) $item, $type, $subtype, - $field_options ?? [], + [], ); } - if (str_contains($current_url, 'helpdesk.public.php')) { - echo '
'; - } echo '
'; //JS to trigger any change and check if container need to be display or not @@ -1085,6 +1078,7 @@ public static function prepareHtmlFields( $massiveaction = false, $field_options = [] ) { + if (empty($fields)) { return false; } diff --git a/templates/fields.html.twig b/templates/fields.html.twig index 0a8b43a7..4f2270b2 100644 --- a/templates/fields.html.twig +++ b/templates/fields.html.twig @@ -29,13 +29,15 @@ {% import 'components/form/fields_macros.html.twig' as macros %} {% set already_wrapped = item is instanceof('CommonITILObject') and container.fields['type'] == 'dom' %} +{% set dropdown_item = item is instanceof('CommonDropdown') and container.fields['type'] == 'dom' %} -{% if not already_wrapped %} -
-
-
-
-
+{% if not already_wrapped and not dropdown_item%} + +{% set class = item.isNewItem() ? 'col-xxl-12' : 'col-xxl-9' %} +
+
+
+
{% endif %} {% for field in fields %} @@ -184,8 +186,8 @@ {% endif %} {% endfor %} -{% if not already_wrapped %} -
+{% if not already_wrapped and not dropdown_item%} +
From 3a76da95a7cb24eaf0757fdfc5c8e3cc33330af2 Mon Sep 17 00:00:00 2001 From: Stanislas Kita Date: Thu, 9 Oct 2025 09:32:59 +0200 Subject: [PATCH 2/5] move tab renderer to twig --- inc/field.class.php | 25 +++++++------------ templates/forms/tab_container.html.twig | 32 +++++++++++++++++++++++++ 2 files changed, 41 insertions(+), 16 deletions(-) create mode 100644 templates/forms/tab_container.html.twig diff --git a/inc/field.class.php b/inc/field.class.php index 6e6a2927..0257413d 100644 --- a/inc/field.class.php +++ b/inc/field.class.php @@ -813,9 +813,6 @@ public function showForm($ID, $options = []) public static function showForTabContainer($c_id, $item) { - /** @var array $CFG_GLPI */ - global $CFG_GLPI; - //profile restriction $right = PluginFieldsProfile::getRightOnContainer($_SESSION['glpiactiveprofile']['id'], $c_id); if ($right < READ) { @@ -826,20 +823,16 @@ public static function showForTabContainer($c_id, $item) //get fields for this container $field_obj = new self(); $fields = $field_obj->find(['plugin_fields_containers_id' => $c_id, 'is_active' => 1], 'ranking'); - echo ""; - echo Html::hidden('plugin_fields_containers_id', ['value' => $c_id]); - echo Html::hidden('items_id', ['value' => $item->getID()]); - echo Html::hidden('itemtype', ['value' => $item->getType()]); - echo self::prepareHtmlFields($fields, $item, $canedit); - - if ($canedit) { - echo "
"; - echo ""; - echo ''; - } + $html_fields = self::prepareHtmlFields($fields, $item, $canedit); + + //display fields as tab container + TemplateRenderer::getInstance()->display('@fields/forms/tab_container.html.twig', [ + 'canedit' => $canedit, + 'html_fields' => $html_fields, + 'item' => $item, + 'c_id' => $c_id, + ]); - Html::closeForm(); return true; } diff --git a/templates/forms/tab_container.html.twig b/templates/forms/tab_container.html.twig new file mode 100644 index 00000000..73a97e6e --- /dev/null +++ b/templates/forms/tab_container.html.twig @@ -0,0 +1,32 @@ + + +
+
+
+
+
+ + {% if canedit %} + + + + + {% endif %} + + {{ html_fields|raw }} + + {% if canedit %} + +
+ +
+ + {% endif %} +
+
+
+
+
From 0221d4a553311f174f6c67382939c7d7f2942daf Mon Sep 17 00:00:00 2001 From: Stanislas Kita Date: Thu, 9 Oct 2025 09:37:48 +0200 Subject: [PATCH 3/5] fix license --- templates/forms/tab_container.html.twig | 28 ++++++++++++++++++++++++- 1 file changed, 27 insertions(+), 1 deletion(-) diff --git a/templates/forms/tab_container.html.twig b/templates/forms/tab_container.html.twig index 73a97e6e..1be8116e 100644 --- a/templates/forms/tab_container.html.twig +++ b/templates/forms/tab_container.html.twig @@ -1,4 +1,30 @@ - +{# + # ------------------------------------------------------------------------- + # Fields plugin for GLPI + # ------------------------------------------------------------------------- + # + # LICENSE + # + # This file is part of Fields. + # + # Fields is free software; you can redistribute it and/or modify + # it under the terms of the GNU General Public License as published by + # the Free Software Foundation; either version 2 of the License, or + # (at your option) any later version. + # + # Fields is distributed in the hope that it will be useful, + # but WITHOUT ANY WARRANTY; without even the implied warranty of + # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + # GNU General Public License for more details. + # + # You should have received a copy of the GNU General Public License + # along with Fields. If not, see . + # ------------------------------------------------------------------------- + # @copyright Copyright (C) 2013-2023 by Fields plugin team. + # @license GPLv2 https://www.gnu.org/licenses/gpl-2.0.html + # @link https://github.com/pluginsGLPI/fields + # ------------------------------------------------------------------------- + #}
From 1c8bd77a50da88c09497cce5d26f51175b8948b3 Mon Sep 17 00:00:00 2001 From: Stanislas Kita Date: Thu, 9 Oct 2025 10:01:25 +0200 Subject: [PATCH 4/5] fix rector --- ajax/container.php | 1 - ajax/reorder.php | 2 ++ inc/labeltranslation.class.php | 1 - inc/profile.class.php | 1 - 4 files changed, 2 insertions(+), 3 deletions(-) diff --git a/ajax/container.php b/ajax/container.php index fdad86a9..1cb02cd9 100644 --- a/ajax/container.php +++ b/ajax/container.php @@ -1,5 +1,4 @@ Date: Fri, 10 Oct 2025 14:36:11 +0200 Subject: [PATCH 5/5] fix --- ajax/container.php | 1 + ajax/reorder.php | 2 -- inc/labeltranslation.class.php | 1 + inc/profile.class.php | 1 + 4 files changed, 3 insertions(+), 2 deletions(-) diff --git a/ajax/container.php b/ajax/container.php index 1cb02cd9..fdad86a9 100644 --- a/ajax/container.php +++ b/ajax/container.php @@ -1,4 +1,5 @@