diff --git a/application/applicationcontext.class.inc.php b/application/applicationcontext.class.inc.php index 34654ace9..1361f92d3 100644 --- a/application/applicationcontext.class.inc.php +++ b/application/applicationcontext.class.inc.php @@ -228,6 +228,20 @@ class ApplicationContext } return $sContext; } + /** + * Returns the context an array of input blocks + * + * @return array The context as a sequence of tags + * @since 3.0.0 + */ + public function GetForUIForm() + { + $aContextInputBlocks = []; + foreach ($this->aValues as $sName => $sValue) { + $aContextInputBlocks[] = InputUIBlockFactory::MakeForHidden("c[$sName]", htmlentities($sValue, ENT_QUOTES, 'UTF-8')); + } + return $aContextInputBlocks; + } /** * Returns the context as sequence of input tags to be inserted inside a
tag diff --git a/application/cmdbabstract.class.inc.php b/application/cmdbabstract.class.inc.php index dc180e360..73d22b03a 100644 --- a/application/cmdbabstract.class.inc.php +++ b/application/cmdbabstract.class.inc.php @@ -3317,7 +3317,7 @@ HTML $oForm->AddSubBlock(InputUIBlockFactory::MakeForHidden('ownership_token', utils::HtmlEntities($sOwnershipToken))); } - // Note: Remove the table is we want fields to occupy the whole width of the container + // Note: Remove the table if we want fields to occupy the whole width of the container $oForm->AddHtml('
'); $oForm->AddHtml($oPage->GetDetails($aDetails)); $oForm->AddHtml('
'); @@ -5018,7 +5018,6 @@ EOF $sHeaderTitle = Dict::Format('UI:Modify_N_ObjectsOf_Class', count($aSelectedObj), MetaModel::GetName($sClass)); $sClassIcon = MetaModel::GetClassIcon($sClass, false); - $oTitle = TitleUIBlockFactory::MakeForPageWithIcon($sHeaderTitle, $sClassIcon, Title::DEFAULT_ICON_COVER_METHOD, false); $oP->set_title(Dict::Format('UI:Modify_N_ObjectsOf_Class', count($aSelectedObj), $sClass)); @@ -5061,6 +5060,8 @@ EOF $oTable->AddOption("bFullscreen", true); $oPanel = PanelUIBlockFactory::MakeForClass($sClass, ''); + $oPanel->SetIcon($sClassIcon); + $oPanel->SetTitle($sHeaderTitle); $oPanel->AddCSSClass('ibo-datatable-panel'); $oPanel->AddSubBlock($oTable); @@ -5071,7 +5072,6 @@ EOF $oForm = FormUIBlockFactory::MakeStandard('')->SetAction($sFormAction); $oP->AddSubBlock($oForm); $oForm->AddSubBlock($oPanel); - $oPanel->SetTitleBlock($oTitle); $oAppContext = new ApplicationContext(); $oP->add($oAppContext->GetForForm()); @@ -5102,7 +5102,6 @@ EOF } } } else { - $oP->AddUiBlock($oTitle); $oP->AddUiBlock($oPanel); $oP->AddSubBlock(ButtonUIBlockFactory::MakeForSecondaryAction(Dict::S('UI:Button:Done')))->SetOnClickJsCode("window.location.href='$sCancelUrl'")->AddCSSClass('mt-5'); } @@ -5220,19 +5219,21 @@ EOF } $iImpactedIndirectly = $oDeletionPlan->GetTargetCount() - count($aObjects); + $sImpactedTableTitle = ''; + $sImpactedTableSubtitle = ''; if ($iImpactedIndirectly > 0) { if (count($aObjects) == 1) { $oObj = $aObjects[0]; - $oP->p(Dict::Format('UI:Delete:Count_Objects/LinksReferencing_Object', $iImpactedIndirectly, - $oObj->GetName())); + $sImpactedTableTitle = Dict::Format('UI:Delete:Count_Objects/LinksReferencing_Object', $iImpactedIndirectly, + $oObj->GetName()); } else { - $oP->p(Dict::Format('UI:Delete:Count_Objects/LinksReferencingTheObjects', $iImpactedIndirectly)); + $sImpactedTableTitle = Dict::Format('UI:Delete:Count_Objects/LinksReferencingTheObjects', $iImpactedIndirectly); } - $oP->p(Dict::S('UI:Delete:ReferencesMustBeDeletedToEnsureIntegrity')); + $sImpactedTableSubtitle = Dict::S('UI:Delete:ReferencesMustBeDeletedToEnsureIntegrity'); } if (($iImpactedIndirectly > 0) || $oDeletionPlan->FoundStopper()) @@ -5244,7 +5245,11 @@ EOF 'label' => 'Consequence', 'description' => Dict::S('UI:Delete:Consequence+'), ); - $oP->AddSubBlock(DataTableUIBlockFactory::MakeForForm(preg_replace('/[^a-zA-Z0-9_-]/', '', uniqid('form_', true)), $aDisplayConfig, $aDisplayData)); + $oBlock = PanelUIBlockFactory::MakeNeutral($sImpactedTableTitle, $sImpactedTableSubtitle); + + $oDataTable = DataTableUIBlockFactory::MakeForForm(preg_replace('/[^a-zA-Z0-9_-]/', '', uniqid('form_', true)), $aDisplayConfig, $aDisplayData); + $oBlock->AddSubBlock($oDataTable); + $oP->AddUiBlock($oBlock); } if ($oDeletionPlan->FoundStopper()) { @@ -5275,7 +5280,6 @@ EOF $sSubtitle = Dict::Format('UI:Delect:Confirm_Count_ObjectsOf_Class', count($aObjects), MetaModel::GetName($sClass)); } - $oP->AddUiBlock(TitleUIBlockFactory::MakeStandard(new Html($sSubtitle))); foreach ($aObjects as $oObj) { $aKeys[] = $oObj->GetKey(); @@ -5285,7 +5289,14 @@ EOF $oSet = new CMDBobjectSet($oFilter); $oDisplaySet = UIContentBlockUIBlockFactory::MakeStandard("0"); $oP->AddSubBlock($oDisplaySet); - $oDisplaySet->AddSubBlock(CMDBAbstractObject::GetDisplaySetBlock($oP, $oSet, array('display_limit' => false, 'menu' => false))); + $oDisplaySet->AddSubBlock(CMDBAbstractObject::GetDisplaySetBlock($oP, $oSet, array( + 'display_limit' => false, + 'menu' => false, + 'surround_with_panel' => true, + 'panel_title' => $sSubtitle, + 'panel_icon' => MetaModel::GetClassIcon($sClass, false), + 'panel_class' => $sClass, + ))); $oForm = FormUIBlockFactory::MakeStandard(''); $oP->AddSubBlock($oForm); @@ -5384,18 +5395,16 @@ EOF $sSubtitle = Dict::Format('UI:Delete:CleaningUpRefencesTo_Several_ObjectsOf_Class', count($aObjects), MetaModel::GetName($sClass)); } - $oP->AddUiBlock(TitleUIBlockFactory::MakeForPage($sSubtitle)); $aDisplayConfig = array(); $aDisplayConfig['class'] = array('label' => 'Class', 'description' => ''); $aDisplayConfig['object'] = array('label' => 'Object', 'description' => ''); $aDisplayConfig['consequence'] = array('label' => 'Done', 'description' => Dict::S('UI:Delete:Done+')); - $oResultsPanel = PanelUIBlockFactory::MakeForInformation(''); + $oResultsPanel = PanelUIBlockFactory::MakeForInformation($sSubtitle); $oP->AddUiBlock($oResultsPanel); - $oResultsPanel->AddSubBlock( - DataTableUIBlockFactory::MakeForStaticData('', $aDisplayConfig, $aDisplayData) - ); + $oDatatable = DataTableUIBlockFactory::MakeForStaticData('', $aDisplayConfig, $aDisplayData); + $oResultsPanel->AddSubBlock($oDatatable); } } } diff --git a/pages/UI.php b/pages/UI.php index 218f72734..a4160cb97 100644 --- a/pages/UI.php +++ b/pages/UI.php @@ -7,6 +7,7 @@ use Combodo\iTop\Application\Helper\Session; use Combodo\iTop\Application\TwigBase\Twig\TwigHelper; use Combodo\iTop\Application\UI\Base\Component\Button\ButtonUIBlockFactory; +use Combodo\iTop\Application\UI\Base\Component\DataTable\DataTableUIBlockFactory; use Combodo\iTop\Application\UI\Base\Component\Form\Form; use Combodo\iTop\Application\UI\Base\Component\GlobalSearch\GlobalSearchHelper; use Combodo\iTop\Application\UI\Base\Component\Input\InputUIBlockFactory; @@ -16,6 +17,7 @@ use Combodo\iTop\Application\UI\Base\Component\Title\Title; use Combodo\iTop\Application\UI\Base\Component\Title\TitleUIBlockFactory; use Combodo\iTop\Application\UI\Base\Component\Toolbar\ToolbarUIBlockFactory; use Combodo\iTop\Application\UI\Base\Layout\PageContent\PageContentFactory; +use Combodo\iTop\Application\UI\Base\Layout\UIContentBlock; /** * Displays a popup welcome message, once per session at maximum @@ -197,12 +199,15 @@ function DisplaySearchSet($oP, $oFilter, $bSearchForm = true, $sBaseClass = '', * @param string $sNextOperation string The next operation (code) to be executed when the form is submitted * @param ActionChecker $oChecker ActionChecker The helper class/instance used to check for which object the action is valid * @param array $aExtraFormParams + * @param array $aDisplayParams + * + * @since 3.0.0 $aDisplayParams parameter * * @throws \ApplicationException * @throws \ArchivedObjectException * @throws \CoreException */ -function DisplayMultipleSelectionForm(WebPage $oP, DBSearch $oFilter, string $sNextOperation, ActionChecker $oChecker, array $aExtraFormParams = []) +function DisplayMultipleSelectionForm(WebPage $oP, DBSearch $oFilter, string $sNextOperation, ActionChecker $oChecker, array $aExtraFormParams = [], array $aDisplayParams = []) { $oAppContext = new ApplicationContext(); $iBulkActionAllowed = $oChecker->IsAllowed(); @@ -228,6 +233,15 @@ function DisplayMultipleSelectionForm(WebPage $oP, DBSearch $oFilter, string $sN $oDisplayBlock = new DisplayBlock($oFilter, 'list', false); //by default all the elements are selected $aExtraParams['selectionMode'] = 'negative'; + if(array_key_exists('icon', $aDisplayParams) || array_key_exists('title', $aDisplayParams)){ + $aExtraParams['surround_with_panel'] = true; + if(array_key_exists('icon', $aDisplayParams)){ + $aExtraParams['panel_icon'] = $aDisplayParams['icon']; + } + if(array_key_exists('title', $aDisplayParams)){ + $aExtraParams['panel_title'] = $aDisplayParams['title']; + } + } $oForm->AddSubBlock($oDisplayBlock->GetDisplay($oP, 1, $aExtraParams)); $oToolbarButtons = ToolbarUIBlockFactory::MakeStandard(null); $oToolbarButtons->AddCSSClass('ibo-toolbar--button'); @@ -931,11 +945,18 @@ EOF throw new ApplicationException(Dict::Format('UI:Error:1ParametersMissing', 'filter')); } $oP->set_title(Dict::S('UI:BulkDeletePageTitle')); - $oP->add("

".Dict::S('UI:BulkDeleteTitle')."

\n"); + $oFilter = DBSearch::unserialize($sFilter); // TO DO : check that the filter is valid $oFilter->UpdateContextFromUser(); + + $sClass = $oFilter->GetClass(); + + $aDisplayParams = [ + 'icon' => MetaModel::GetClassIcon($sClass, false), + 'title' => Dict::S('UI:BulkDeleteTitle'), + ]; $oChecker = new ActionChecker($oFilter, UR_ACTION_BULK_DELETE); - DisplayMultipleSelectionForm($oP, $oFilter, 'bulk_delete', $oChecker); + DisplayMultipleSelectionForm($oP, $oFilter, 'bulk_delete', $oChecker, [], $aDisplayParams); break; /////////////////////////////////////////////////////////////////////////////////////////// @@ -1163,13 +1184,15 @@ EOF $sActionLabel = $aStimuli[$sStimulus]->GetLabel(); $sActionDetails = $aStimuli[$sStimulus]->GetDescription(); $oP->set_title($sActionLabel); - $oP->add(''); + $sClass = $oFilter->GetClass(); + $aDisplayParams = [ + 'icon' => MetaModel::GetClassIcon($sClass, false), + 'title' => $sActionLabel, + ]; $oChecker = new StimulusChecker($oFilter, $sState, $sStimulus); $aExtraFormParams = array('stimulus' => $sStimulus, 'state' => $sState); - DisplayMultipleSelectionForm($oP, $oFilter, 'bulk_stimulus', $oChecker, $aExtraFormParams); + DisplayMultipleSelectionForm($oP, $oFilter, 'bulk_stimulus', $oChecker, $aExtraFormParams, $aDisplayParams); break; case 'bulk_stimulus': @@ -1203,9 +1226,17 @@ EOF $aTargetStateDef = $aStates[$sTargetState]; $oP->set_title(Dict::Format('UI:StimulusModify_N_ObjectsOf_Class', $sActionLabel, count($aSelectObject), $sClass)); - $oP->add(''); + $oP->add(<< +
+HTML + ); + $oP->AddUiBlock(TitleUIBlockFactory::MakeForPage(Dict::Format('UI:StimulusModify_N_ObjectsOf_Class', $sActionLabel, count($aSelectObject), $sClass))); + if (!empty($sActionDetails)) { + $oP->AddUiBlock(TitleUIBlockFactory::MakeForPage($sActionDetails)); + } + + $aExpectedAttributes = MetaModel::GetTransitionAttributes($sClass, $sStimulus, $sState); $aDetails = array(); @@ -1286,40 +1317,43 @@ EOF $iFieldIndex++; } } - $sButtonsPosition = MetaModel::GetConfig()->Get('buttons_position'); - if ($sButtonsPosition == 'bottom') - { - // bottom: Displays the ticket details BEFORE the actions - $oP->add('
'); - $oObj->DisplayBareProperties($oP); - $oP->add('
'); + $oFormContainer = new UIContentBlock(null, ['ibo-wizard-container']); + $oP->AddUiBlock($oFormContainer); + $oForm = new Combodo\iTop\Application\UI\Base\Component\Form\Form($sFormId); + $oFormContainer->AddSubBlock($oForm); + $oForm->SetOnSubmitJsCode("return OnSubmit('{$sFormId}');") + ->AddSubBlock(InputUIBlockFactory::MakeForHidden('class', $sClass)) + ->AddSubBlock(InputUIBlockFactory::MakeForHidden('operation', 'bulk_apply_stimulus')) + ->AddSubBlock(InputUIBlockFactory::MakeForHidden('stimulus', $sStimulus)) + ->AddSubBlock(InputUIBlockFactory::MakeForHidden('preview_mode', 1)) + ->AddSubBlock(InputUIBlockFactory::MakeForHidden('filter', utils::HtmlEntities($sFilter))) + ->AddSubBlock(InputUIBlockFactory::MakeForHidden('state', $sState)) + ->AddSubBlock(InputUIBlockFactory::MakeForHidden('selectObject', implode(',',$aSelectObject))) + ->AddSubBlock(InputUIBlockFactory::MakeForHidden('transaction_id', utils::GetNewTransactionId())); + + $aContextInputBlocks = $oAppContext->GetForUIForm(); + foreach ($aContextInputBlocks as $oContextInputBlock){ + $oForm->AddSubBlock($oContextInputBlock); } - $oP->add("
\n"); - $oP->add("\n"); - $oP->add("
\n"); - $oP->details($aDetails); - $oP->add("
\n"); - $oP->add("\n"); - $oP->add("\n"); - $oP->add("\n"); - $oP->add("\n"); - $oP->add("\n"); - $oP->add("\n"); - $oP->add("\n"); - $oP->add($oAppContext->GetForForm()); - $oP->add("\n"); + // Note: Remove the table if we want fields to occupy the whole width of the container + $oForm->AddHtml('
'); + $oForm->AddHtml($oP->GetDetails($aDetails)); + $oForm->AddHtml('
'); + $sURL = "./UI.php?operation=search&filter=".urlencode($sFilter)."&".$oAppContext->GetForLink(); - $oP->add("    \n"); - $oP->add("\n"); - $oP->add("\n"); - $oP->add("
\n"); - if ($sButtonsPosition != 'bottom') - { - // top or both: Displays the ticket details AFTER the actions - $oP->add('
'); - $oObj->DisplayBareProperties($oP); - $oP->add('
'); - } + $oCancelButton = ButtonUIBlockFactory::MakeForCancel(Dict::S('UI:Button:Cancel'), 'cancel', 'cancel'); + $oCancelButton->SetOnClickJsCode("window.location.href='$sURL'"); + $oForm->AddSubBlock($oCancelButton); + + $oSubmitButton = ButtonUIBlockFactory::MakeForPrimaryAction($sActionLabel, 'submit', 'submit', true); + $oForm->AddSubBlock($oSubmitButton); + + $oP->add(<< +
+HTML + ); + $iFieldsCount = count($aFieldsMap); $sJsonFieldsMap = json_encode($aFieldsMap); @@ -1381,9 +1415,6 @@ EOF $sActionDetails = $aStimuli[$sStimulus]->GetDescription(); $oP->set_title(Dict::Format('UI:StimulusModify_N_ObjectsOf_Class', $sActionLabel, count($aObjects), $sClass)); - $oP->add(''); $oSet = DBObjectSet::FromArray($sClass, $aObjects); @@ -1469,10 +1500,22 @@ EOF 'errors' => $sError, ); } - $oP->Table($aHeaders, $aRows); + $oBlock = PanelUIBlockFactory::MakeForClass($sClass, Dict::Format('UI:StimulusModify_N_ObjectsOf_Class', $sActionLabel, count($aObjects), $sClass)); + $oBlock->SetIcon(MetaModel::GetClassIcon($sClass, false)); + + + $oDataTable = DataTableUIBlockFactory::MakeForStaticData('', $aHeaders,$aRows); + $oBlock->AddSubBlock($oDataTable); + $oP->AddUiBlock($oBlock); + // Back to the list $sURL = "./UI.php?operation=search&filter=".urlencode($sFilter)."&".$oAppContext->GetForLink(); - $oP->add(''); + $oSubmitButton = ButtonUIBlockFactory::MakeForSecondaryAction(Dict::S('UI:Button:Done'), 'submit', 'submit', true); + $oSubmitButton->SetOnClickJsCode("window.location.href='$sURL'"); + $oToolbarButtons = ToolbarUIBlockFactory::MakeStandard(null); + $oToolbarButtons->AddCSSClass('ibo-toolbar--button'); + $oToolbarButtons->AddSubBlock($oSubmitButton); + $oP->AddSubBlock($oToolbarButtons); } break; @@ -1868,9 +1911,13 @@ class UI // Add user filter $oFilter->UpdateContextFromUser(); $oChecker = new ActionChecker($oFilter, UR_ACTION_BULK_MODIFY); - $oP->AddUiBlock(TitleUIBlockFactory::MakeForPage(Dict::S('UI:ModifyAllPageTitle'))); + $sClass = $oFilter->GetClass(); - DisplayMultipleSelectionForm($oP, $oFilter, 'form_for_modify_all', $oChecker); + $aDisplayParams = [ + 'icon' => MetaModel::GetClassIcon($sClass, false), + 'title' => Dict::S('UI:ModifyAllPageTitle'), + ]; + DisplayMultipleSelectionForm($oP, $oFilter, 'form_for_modify_all', $oChecker, [], $aDisplayParams); } /** diff --git a/sources/application/WebPage/WebPage.php b/sources/application/WebPage/WebPage.php index d0961088f..0e581d853 100644 --- a/sources/application/WebPage/WebPage.php +++ b/sources/application/WebPage/WebPage.php @@ -1001,7 +1001,7 @@ JS; $sHtml .= "
\n"; $sHtml .= "
{$aAttrib['label']}
\n"; - $sHtml .= "
\n"; + // $sHtml .= "
\n"; // By Rom, for csv import, proposed to show several values for column selection if (is_array($aAttrib['value'])) { @@ -1016,13 +1016,13 @@ JS; $sInfo = (isset($aAttrib['infos'])) ? $aAttrib['infos'] : ''; if ($sComment !== '') { - $sHtml .= "
$sComment
\n"; + $sHtml .= "
$sComment
\n"; } if ($sInfo !== '') { - $sHtml .= "
$sInfo
\n"; + $sHtml .= "
$sInfo
\n"; } - $sHtml .= "
\n"; + // $sHtml .= "
\n"; $sHtml .= "
\n"; }