dolibarr 21.0.3
availabilities_list.php
Go to the documentation of this file.
1<?php
2/* Copyright (C) 2007-2017 Laurent Destailleur <eldy@users.sourceforge.net>
3 * Copyright (C) 2022 Alice Adminson <aadminson@example.com>
4 * Copyright (C) 2024 Frédéric France <frederic.france@free.fr>
5 * Copyright (C) 2024 MDW <mdeweerd@users.noreply.github.com>
6 *
7 * This program is free software; you can redistribute it and/or modify
8 * it under the terms of the GNU General Public License as published by
9 * the Free Software Foundation; either version 3 of the License, or
10 * (at your option) any later version.
11 *
12 * This program is distributed in the hope that it will be useful,
13 * but WITHOUT ANY WARRANTY; without even the implied warranty of
14 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15 * GNU General Public License for more details.
16 *
17 * You should have received a copy of the GNU General Public License
18 * along with this program. If not, see <https://www.gnu.org/licenses/>.
19 */
20
27// Load Dolibarr environment
28require '../main.inc.php';
29require_once DOL_DOCUMENT_ROOT.'/core/class/html.formcompany.class.php';
30require_once DOL_DOCUMENT_ROOT.'/core/lib/date.lib.php';
31require_once DOL_DOCUMENT_ROOT.'/core/lib/company.lib.php';
32
33// load module libraries
34require_once __DIR__.'/class/availabilities.class.php';
35
44// Load translation files required by the page
45$langs->loadLangs(array("agenda", "other"));
46
47$id = GETPOSTINT('id');
48$ref = GETPOST('ref', 'alpha');
49
50$action = GETPOST('action', 'aZ09') ? GETPOST('action', 'aZ09') : 'view'; // The action 'add', 'create', 'edit', 'update', 'view', ...
51$massaction = GETPOST('massaction', 'alpha'); // The bulk action (combo box choice into lists)
52$show_files = GETPOSTINT('show_files'); // Show files area generated by bulk actions ?
53$confirm = GETPOST('confirm', 'alpha'); // Result of a confirmation
54$cancel = GETPOST('cancel', 'alpha'); // We click on a Cancel button
55$toselect = GETPOST('toselect', 'array'); // Array of ids of elements selected into a list
56$contextpage = GETPOST('contextpage', 'aZ') ? GETPOST('contextpage', 'aZ') : str_replace('_', '', basename(dirname(__FILE__)).basename(__FILE__, '.php')); // To manage different context of search
57$backtopage = GETPOST('backtopage', 'alpha'); // Go back to a dedicated page
58$optioncss = GETPOST('optioncss', 'aZ'); // Option for the css output (always '' except when 'print')
59$mode = GETPOST('mode', 'aZ'); // The output mode ('list', 'kanban', 'hierarchy', 'calendar', ...)
60
61// Load variable for pagination
62$limit = GETPOSTINT('limit') ? GETPOSTINT('limit') : $conf->liste_limit;
63$sortfield = GETPOST('sortfield', 'aZ09comma');
64$sortorder = GETPOST('sortorder', 'aZ09comma');
65$page = GETPOSTISSET('pageplusone') ? (GETPOSTINT('pageplusone') - 1) : GETPOSTINT("page");
66if (empty($page) || $page < 0 || GETPOST('button_search', 'alpha') || GETPOST('button_removefilter', 'alpha')) {
67 // If $page is not defined, or '' or -1 or if we click on clear filters
68 $page = 0;
69}
70$offset = $limit * $page;
71$pageprev = $page - 1;
72$pagenext = $page + 1;
73
74// Initialize a technical objects
75$object = new Availabilities($db);
76$extrafields = new ExtraFields($db);
77$diroutputmassaction = $conf->bookcal->dir_output.'/temp/massgeneration/'.$user->id;
78$hookmanager->initHooks(array($contextpage)); // Note that conf->hooks_modules contains array
79
80// Fetch optionals attributes and labels
81$extrafields->fetch_name_optionals_label($object->table_element);
82//$extrafields->fetch_name_optionals_label($object->table_element_line);
83
84$search_array_options = $extrafields->getOptionalsFromPost($object->table_element, '', 'search_');
85
86// Default sort order (if not yet defined by previous GETPOST)
87if (!$sortfield) {
88 reset($object->fields); // Reset is required to avoid key() to return null.
89 $sortfield = "t.".key($object->fields); // Set here default search field. By default 1st field in definition.
90}
91if (!$sortorder) {
92 $sortorder = "ASC";
93}
94
95// Initialize array of search criteria
96$search_all = GETPOST('search_all', 'alphanohtml');
97$search = array();
98foreach ($object->fields as $key => $val) {
99 if (GETPOST('search_'.$key, 'alpha') !== '') {
100 $search[$key] = GETPOST('search_'.$key, 'alpha');
101 }
102 if (preg_match('/^(date|timestamp|datetime)/', $val['type'])) {
103 $search[$key.'_dtstart'] = dol_mktime(0, 0, 0, GETPOSTINT('search_'.$key.'_dtstartmonth'), GETPOSTINT('search_'.$key.'_dtstartday'), GETPOSTINT('search_'.$key.'_dtstartyear'));
104 $search[$key.'_dtend'] = dol_mktime(23, 59, 59, GETPOSTINT('search_'.$key.'_dtendmonth'), GETPOSTINT('search_'.$key.'_dtendday'), GETPOSTINT('search_'.$key.'_dtendyear'));
105 }
106}
107
108// List of fields to search into when doing a "search in all"
109$fieldstosearchall = array();
110// foreach ($object->fields as $key => $val) {
111// if (!empty($val['searchall'])) {
112// $fieldstosearchall['t.'.$key] = $val['label'];
113// }
114// }
115// $parameters = array('fieldstosearchall'=>$fieldstosearchall);
116// $reshook = $hookmanager->executeHooks('completeFieldsToSearchAll', $parameters, $object, $action); // Note that $action and $object may have been modified by some hooks
117// if ($reshook > 0) {
118// $fieldstosearchall = empty($hookmanager->resArray['fieldstosearchall']) ? array() : $hookmanager->resArray['fieldstosearchall'];
119// } elseif ($reshook == 0) {
120// $fieldstosearchall = array_merge($fieldstosearchall, empty($hookmanager->resArray['fieldstosearchall']) ? array() : $hookmanager->resArray['fieldstosearchall']);
121// }
122
123
124'
125 @phan-var-force array<string,string> $fieldstosearchall
126';
127
128
129// Definition of array of fields for columns
130$arrayfields = array();
131foreach ($object->fields as $key => $val) {
132 // If $val['visible']==0, then we never show the field
133 if (!empty($val['visible'])) {
134 $visible = (int) dol_eval((string) $val['visible'], 1);
135 $arrayfields['t.'.$key] = array(
136 'label' => $val['label'],
137 'checked' => (($visible < 0) ? 0 : 1),
138 'enabled' => (abs($visible) != 3 && (bool) dol_eval($val['enabled'], 1)),
139 'position' => $val['position'],
140 'help' => isset($val['help']) ? $val['help'] : ''
141 );
142 }
143}
144// Extra fields
145include DOL_DOCUMENT_ROOT.'/core/tpl/extrafields_list_array_fields.tpl.php';
146
147$object->fields = dol_sort_array($object->fields, 'position');
148//$arrayfields['anotherfield'] = array('type'=>'integer', 'label'=>'AnotherField', 'checked'=>1, 'enabled'=>1, 'position'=>90, 'csslist'=>'right');
149$arrayfields = dol_sort_array($arrayfields, 'position');
150
151// There is several ways to check permission.
152// Set $enablepermissioncheck to 1 to enable a minimum low level of checks
153$enablepermissioncheck = 0;
154if ($enablepermissioncheck) {
155 $permissiontoread = $user->hasRight('bookcal', 'availabilities', 'read');
156 $permissiontoadd = $user->hasRight('bookcal', 'availabilities', 'write');
157 $permissiontodelete = $user->hasRight('bookcal', 'availabilities', 'delete');
158} else {
159 $permissiontoread = 1;
160 $permissiontoadd = 1;
161 $permissiontodelete = 1;
162}
163
164// Security check (enable the most restrictive one)
165if ($user->socid > 0) {
167}
168//if ($user->socid > 0) accessforbidden();
169//$socid = 0; if ($user->socid > 0) $socid = $user->socid;
170//$isdraft = (($object->status == $object::STATUS_DRAFT) ? 1 : 0);
171//restrictedArea($user, $object->element, 0, $object->table_element, '', 'fk_soc', 'rowid', $isdraft);
172if (!isModEnabled('bookcal')) {
173 accessforbidden('Module bookcal not enabled');
174}
175if (!$permissiontoread) {
177}
178
179
180/*
181 * Actions
182 */
183
184if (GETPOST('cancel', 'alpha')) {
185 $action = 'list';
186 $massaction = '';
187}
188if (!GETPOST('confirmmassaction', 'alpha') && $massaction != 'presend' && $massaction != 'confirm_presend') {
189 $massaction = '';
190}
191
192$parameters = array();
193$reshook = $hookmanager->executeHooks('doActions', $parameters, $object, $action); // Note that $action and $object may have been modified by some hooks
194if ($reshook < 0) {
195 setEventMessages($hookmanager->error, $hookmanager->errors, 'errors');
196}
197
198if (empty($reshook)) {
199 // Selection of new fields
200 include DOL_DOCUMENT_ROOT.'/core/actions_changeselectedfields.inc.php';
201
202 // Purge search criteria
203 if (GETPOST('button_removefilter_x', 'alpha') || GETPOST('button_removefilter.x', 'alpha') || GETPOST('button_removefilter', 'alpha')) { // All tests are required to be compatible with all browsers
204 foreach ($object->fields as $key => $val) {
205 $search[$key] = '';
206 if (preg_match('/^(date|timestamp|datetime)/', $val['type'])) {
207 $search[$key.'_dtstart'] = '';
208 $search[$key.'_dtend'] = '';
209 }
210 }
211 $toselect = array();
212 $search_array_options = array();
213 }
214 if (GETPOST('button_removefilter_x', 'alpha') || GETPOST('button_removefilter.x', 'alpha') || GETPOST('button_removefilter', 'alpha')
215 || GETPOST('button_search_x', 'alpha') || GETPOST('button_search.x', 'alpha') || GETPOST('button_search', 'alpha')) {
216 $massaction = ''; // Protection to avoid mass action if we force a new search during a mass action confirmation
217 }
218
219 // Mass actions
220 $objectclass = 'Availabilities';
221 $objectlabel = 'Availabilities';
222 $uploaddir = $conf->bookcal->dir_output;
223 include DOL_DOCUMENT_ROOT.'/core/actions_massactions.inc.php';
224
225 // You can add more action here
226 // if ($action == 'xxx' && $permissiontoxxx) ...
227}
228
229
230
231/*
232 * View
233 */
234
235$form = new Form($db);
236
237$now = dol_now();
238
239$title = $langs->trans("Availabilities");
240//$help_url = "EN:Module_Availabilities|FR:Module_Availabilities_FR|ES:Módulo_Availabilities";
241$help_url = '';
242$morejs = array();
243$morecss = array();
244
245
246// Build and execute select
247// --------------------------------------------------------------------
248$sql = 'SELECT ';
249$sql .= $object->getFieldList('t');
250// Add fields from extrafields
251if (!empty($extrafields->attributes[$object->table_element]['label'])) {
252 foreach ($extrafields->attributes[$object->table_element]['label'] as $key => $val) {
253 $sql .= ($extrafields->attributes[$object->table_element]['type'][$key] != 'separate' ? ", ef.".$key." as options_".$key : '');
254 }
255}
256// Add fields from hooks
257$parameters = array();
258$reshook = $hookmanager->executeHooks('printFieldListSelect', $parameters, $object, $action); // Note that $action and $object may have been modified by hook
259$sql .= $hookmanager->resPrint;
260$sql = preg_replace('/,\s*$/', '', $sql);
261//$sql .= ", COUNT(rc.rowid) as anotherfield";
262
263$sqlfields = $sql; // $sql fields to remove for count total
264
265$sql .= " FROM ".MAIN_DB_PREFIX.$object->table_element." as t";
266if ($object->ismultientitymanaged == 1 || $object->ismultientitymanaged != '') { // value is fk_bookcal_calendar@bookcal_calendar
267 $sql .= ", ".MAIN_DB_PREFIX."bookcal_calendar as bc";
268}
269//$sql .= " LEFT JOIN ".MAIN_DB_PREFIX."anothertable as rc ON rc.parent = t.rowid";
270if (isset($extrafields->attributes[$object->table_element]['label']) && is_array($extrafields->attributes[$object->table_element]['label']) && count($extrafields->attributes[$object->table_element]['label'])) {
271 $sql .= " LEFT JOIN ".MAIN_DB_PREFIX.$object->table_element."_extrafields as ef on (t.rowid = ef.fk_object)";
272}
273// Add table from hooks
274$parameters = array();
275$reshook = $hookmanager->executeHooks('printFieldListFrom', $parameters, $object, $action); // Note that $action and $object may have been modified by hook
276$sql .= $hookmanager->resPrint;
277if ($object->ismultientitymanaged == 1 || $object->ismultientitymanaged != '') { // value is fk_bookcal_calendar@bookcal_calendar
278 $sql .= " WHERE bc.rowid = t.fk_bookcal_calendar";
279 $sql .= " AND bc.entity IN (".getEntity('calendar', (GETPOSTINT('search_current_entity') ? 0 : 1)).")";
280} else {
281 $sql .= " WHERE 1 = 1";
282}
283foreach ($search as $key => $val) {
284 if (array_key_exists($key, $object->fields)) {
285 if ($key == 'status' && $search[$key] == -1) {
286 continue;
287 }
288 $mode_search = (($object->isInt($object->fields[$key]) || $object->isFloat($object->fields[$key])) ? 1 : 0);
289 if ((strpos($object->fields[$key]['type'], 'integer:') === 0) || (strpos($object->fields[$key]['type'], 'sellist:') === 0) || !empty($object->fields[$key]['arrayofkeyval'])) {
290 if ($search[$key] == '-1' || ($search[$key] === '0' && (empty($object->fields[$key]['arrayofkeyval']) || !array_key_exists('0', $object->fields[$key]['arrayofkeyval'])))) {
291 $search[$key] = '';
292 }
293 $mode_search = 2;
294 }
295 if ($search[$key] != '') {
296 $sql .= natural_search("t.".$db->escape($key), $search[$key], (($key == 'status') ? 2 : $mode_search));
297 }
298 } else {
299 if (preg_match('/(_dtstart|_dtend)$/', $key) && $search[$key] != '') {
300 $columnName = preg_replace('/(_dtstart|_dtend)$/', '', $key);
301 if (preg_match('/^(date|timestamp|datetime)/', $object->fields[$columnName]['type'])) {
302 if (preg_match('/_dtstart$/', $key)) {
303 $sql .= " AND t.".$db->escape($columnName)." >= '".$db->idate($search[$key])."'";
304 }
305 if (preg_match('/_dtend$/', $key)) {
306 $sql .= " AND t.".$db->escape($columnName)." <= '".$db->idate($search[$key])."'";
307 }
308 }
309 }
310 }
311}
312if ($search_all) {
313 $sql .= natural_search(array_keys($fieldstosearchall), $search_all);
314}
315//$sql.= dolSqlDateFilter("t.field", $search_xxxday, $search_xxxmonth, $search_xxxyear);
316// Add where from extra fields
317include DOL_DOCUMENT_ROOT.'/core/tpl/extrafields_list_search_sql.tpl.php';
318// Add where from hooks
319$parameters = array();
320$reshook = $hookmanager->executeHooks('printFieldListWhere', $parameters, $object, $action); // Note that $action and $object may have been modified by hook
321$sql .= $hookmanager->resPrint;
322
323/* If a group by is required
324$sql .= " GROUP BY ";
325foreach($object->fields as $key => $val) {
326 $sql .= "t.".$db->escape($key).", ";
327}
328// Add fields from extrafields
329if (!empty($extrafields->attributes[$object->table_element]['label'])) {
330 foreach ($extrafields->attributes[$object->table_element]['label'] as $key => $val) {
331 $sql .= ($extrafields->attributes[$object->table_element]['type'][$key] != 'separate' ? "ef.".$key.', ' : '');
332 }
333}
334// Add groupby from hooks
335$parameters = array();
336$reshook = $hookmanager->executeHooks('printFieldListGroupBy', $parameters, $object, $action); // Note that $action and $object may have been modified by hook
337$sql .= $hookmanager->resPrint;
338$sql = preg_replace('/,\s*$/', '', $sql);
339*/
340
341// Add HAVING from hooks
342/*
343$parameters = array();
344$reshook = $hookmanager->executeHooks('printFieldListHaving', $parameters, $object, $action); // Note that $action and $object may have been modified by hook
345$sql .= empty($hookmanager->resPrint) ? "" : " HAVING 1=1 ".$hookmanager->resPrint;
346*/
347
348// Count total nb of records
349$nbtotalofrecords = '';
350if (!getDolGlobalInt('MAIN_DISABLE_FULL_SCANLIST')) {
351 /* The fast and low memory method to get and count full list converts the sql into a sql count */
352 $sqlforcount = preg_replace('/^'.preg_quote($sqlfields, '/').'/', 'SELECT COUNT(*) as nbtotalofrecords', $sql);
353 $sqlforcount = preg_replace('/GROUP BY .*$/', '', $sqlforcount);
354 $resql = $db->query($sqlforcount);
355 if ($resql) {
356 $objforcount = $db->fetch_object($resql);
357 $nbtotalofrecords = $objforcount->nbtotalofrecords;
358 } else {
359 dol_print_error($db);
360 }
361
362 if (($page * $limit) > $nbtotalofrecords) { // if total resultset is smaller than the paging size (filtering), goto and load page 0
363 $page = 0;
364 $offset = 0;
365 }
366 $db->free($resql);
367}
368
369// Complete request and execute it with limit
370$sql .= $db->order($sortfield, $sortorder);
371if ($limit) {
372 $sql .= $db->plimit($limit + 1, $offset);
373}
374
375$resql = $db->query($sql);
376if (!$resql) {
377 dol_print_error($db);
378 exit;
379}
380
381$num = $db->num_rows($resql);
382
383
384// Direct jump if only one record found
385if ($num == 1 && getDolGlobalInt('MAIN_SEARCH_DIRECT_OPEN_IF_ONLY_ONE') && $search_all && !$page) {
386 $obj = $db->fetch_object($resql);
387 $id = $obj->rowid;
388 header("Location: ".dol_buildpath('/bookcal/availabilities_card.php', 1).'?id='.$id);
389 exit;
390}
391
392
393// Output page
394// --------------------------------------------------------------------
395
396llxHeader('', $title, $help_url, '', 0, 0, $morejs, $morecss, '', 'bodyforlist mod-bookcal page-list_availabilities'); // Can use also classforhorizontalscrolloftabs instead of bodyforlist for no horizontal scroll
397
398// Example : Adding jquery code
399// print '<script type="text/javascript">
400// jQuery(document).ready(function() {
401// function init_myfunc()
402// {
403// jQuery("#myid").removeAttr(\'disabled\');
404// jQuery("#myid").attr(\'disabled\',\'disabled\');
405// }
406// init_myfunc();
407// jQuery("#mybutton").click(function() {
408// init_myfunc();
409// });
410// });
411// </script>';
412
413$arrayofselected = is_array($toselect) ? $toselect : array();
414
415$param = '';
416if (!empty($mode)) {
417 $param .= '&mode='.urlencode($mode);
418}
419if (!empty($contextpage) && $contextpage != $_SERVER["PHP_SELF"]) {
420 $param .= '&contextpage='.urlencode($contextpage);
421}
422if ($limit > 0 && $limit != $conf->liste_limit) {
423 $param .= '&limit='.((int) $limit);
424}
425if ($optioncss != '') {
426 $param .= '&optioncss='.urlencode($optioncss);
427}
428foreach ($search as $key => $val) {
429 if (is_array($search[$key])) {
430 foreach ($search[$key] as $skey) {
431 if ($skey != '') {
432 $param .= '&search_'.$key.'[]='.urlencode($skey);
433 }
434 }
435 } elseif (preg_match('/(_dtstart|_dtend)$/', $key) && !empty($val)) {
436 $param .= '&search_'.$key.'month='.(GETPOSTINT('search_'.$key.'month'));
437 $param .= '&search_'.$key.'day='.(GETPOSTINT('search_'.$key.'day'));
438 $param .= '&search_'.$key.'year='.(GETPOSTINT('search_'.$key.'year'));
439 } elseif ($search[$key] != '') {
440 $param .= '&search_'.$key.'='.urlencode($search[$key]);
441 }
442}
443// Add $param from extra fields
444include DOL_DOCUMENT_ROOT.'/core/tpl/extrafields_list_search_param.tpl.php';
445// Add $param from hooks
446$parameters = array('param' => &$param);
447$reshook = $hookmanager->executeHooks('printFieldListSearchParam', $parameters, $object, $action); // Note that $action and $object may have been modified by hook
448$param .= $hookmanager->resPrint;
449
450// List of mass actions available
451$arrayofmassactions = array(
452 //'validate'=>img_picto('', 'check', 'class="pictofixedwidth"').$langs->trans("Validate"),
453 //'generate_doc'=>img_picto('', 'pdf', 'class="pictofixedwidth"').$langs->trans("ReGeneratePDF"),
454 //'builddoc'=>img_picto('', 'pdf', 'class="pictofixedwidth"').$langs->trans("PDFMerge"),
455 //'presend'=>img_picto('', 'email', 'class="pictofixedwidth"').$langs->trans("SendByMail"),
456);
457if (!empty($permissiontodelete)) {
458 $arrayofmassactions['predelete'] = img_picto('', 'delete', 'class="pictofixedwidth"').$langs->trans("Delete");
459}
460if (GETPOSTINT('nomassaction') || in_array($massaction, array('presend', 'predelete'))) {
461 $arrayofmassactions = array();
462}
463$massactionbutton = $form->selectMassAction('', $arrayofmassactions);
464
465print '<form method="POST" id="searchFormList" action="'.$_SERVER["PHP_SELF"].'">'."\n";
466if ($optioncss != '') {
467 print '<input type="hidden" name="optioncss" value="'.$optioncss.'">';
468}
469print '<input type="hidden" name="token" value="'.newToken().'">';
470print '<input type="hidden" name="formfilteraction" id="formfilteraction" value="list">';
471print '<input type="hidden" name="action" value="list">';
472print '<input type="hidden" name="sortfield" value="'.$sortfield.'">';
473print '<input type="hidden" name="sortorder" value="'.$sortorder.'">';
474print '<input type="hidden" name="page" value="'.$page.'">';
475print '<input type="hidden" name="contextpage" value="'.$contextpage.'">';
476print '<input type="hidden" name="mode" value="'.$mode.'">';
477
478
479$newcardbutton = '';
480$newcardbutton .= dolGetButtonTitle($langs->trans('ViewList'), '', 'fa fa-bars imgforviewmode', $_SERVER["PHP_SELF"].'?mode=common'.preg_replace('/(&|\?)*mode=[^&]+/', '', $param), '', ((empty($mode) || $mode == 'common') ? 2 : 1), array('morecss' => 'reposition'));
481$newcardbutton .= dolGetButtonTitle($langs->trans('ViewKanban'), '', 'fa fa-th-list imgforviewmode', $_SERVER["PHP_SELF"].'?mode=kanban'.preg_replace('/(&|\?)*mode=[^&]+/', '', $param), '', ($mode == 'kanban' ? 2 : 1), array('morecss' => 'reposition'));
482$newcardbutton .= dolGetButtonTitleSeparator();
483$newcardbutton .= dolGetButtonTitle($langs->trans('New'), '', 'fa fa-plus-circle', dol_buildpath('/bookcal/availabilities_card.php', 1).'?action=create&backtopage='.urlencode($_SERVER['PHP_SELF']), '', $permissiontoadd);
484
485print_barre_liste($title, $page, $_SERVER["PHP_SELF"], $param, $sortfield, $sortorder, $massactionbutton, $num, $nbtotalofrecords, 'object_'.$object->picto, 0, $newcardbutton, '', $limit, 0, 0, 1);
486
487// Add code for pre mass action (confirmation or email presend form)
488$topicmail = "SendAvailabilitiesRef";
489$modelmail = "availabilities";
490$objecttmp = new Availabilities($db);
491$trackid = 'xxxx'.$object->id;
492include DOL_DOCUMENT_ROOT.'/core/tpl/massactions_pre.tpl.php';
493
494if ($search_all) {
495 $setupstring = '';
496 foreach ($fieldstosearchall as $key => $val) {
497 $fieldstosearchall[$key] = $langs->trans($val);
498 $setupstring .= $key."=".$val.";";
499 }
500 print '<!-- Search done like if BOOKCAL_QUICKSEARCH_ON_FIELDS = '.$setupstring.' -->'."\n";
501 print '<div class="divsearchfieldfilter">'.$langs->trans("FilterOnInto", $search_all).implode(', ', $fieldstosearchall).'</div>'."\n";
502}
503
504$moreforfilter = '';
505/*$moreforfilter.='<div class="divsearchfield">';
506$moreforfilter.= $langs->trans('MyFilter') . ': <input type="text" name="search_myfield" value="'.dol_escape_htmltag($search_myfield).'">';
507$moreforfilter.= '</div>';*/
508
509$parameters = array();
510$reshook = $hookmanager->executeHooks('printFieldPreListTitle', $parameters, $object, $action); // Note that $action and $object may have been modified by hook
511if (empty($reshook)) {
512 $moreforfilter .= $hookmanager->resPrint;
513} else {
514 $moreforfilter = $hookmanager->resPrint;
515}
516
517if (!empty($moreforfilter)) {
518 print '<div class="liste_titre liste_titre_bydiv centpercent">';
519 print $moreforfilter;
520 print '</div>';
521}
522
523$varpage = empty($contextpage) ? $_SERVER["PHP_SELF"] : $contextpage;
524$htmlofselectarray = $form->multiSelectArrayWithCheckbox('selectedfields', $arrayfields, $varpage, getDolGlobalString('MAIN_CHECKBOX_LEFT_COLUMN')); // This also change content of $arrayfields with user setup
525$selectedfields = ($mode != 'kanban' ? $htmlofselectarray : '');
526$selectedfields .= (count($arrayofmassactions) ? $form->showCheckAddButtons('checkforselect', 1) : '');
527
528print '<div class="div-table-responsive">'; // You can use div-table-responsive-no-min if you don't need reserved height for your table
529print '<table class="tagtable nobottomiftotal liste'.($moreforfilter ? " listwithfilterbefore" : "").'">'."\n";
530
531
532// Fields title search
533// --------------------------------------------------------------------
534print '<tr class="liste_titre_filter">';
535// Action column
536if (getDolGlobalString('MAIN_CHECKBOX_LEFT_COLUMN')) {
537 print '<td class="liste_titre center maxwidthsearch">';
538 $searchpicto = $form->showFilterButtons('left');
539 print $searchpicto;
540 print '</td>';
541}
542foreach ($object->fields as $key => $val) {
543 $searchkey = empty($search[$key]) ? '' : $search[$key];
544 $cssforfield = (empty($val['csslist']) ? (empty($val['css']) ? '' : $val['css']) : $val['csslist']);
545 if ($key == 'status') {
546 $cssforfield .= ($cssforfield ? ' ' : '').'center';
547 } elseif (in_array($val['type'], array('date', 'datetime', 'timestamp'))) {
548 $cssforfield .= ($cssforfield ? ' ' : '').'center';
549 } elseif (in_array($val['type'], array('timestamp'))) {
550 $cssforfield .= ($cssforfield ? ' ' : '').'nowrap';
551 } elseif (in_array($val['type'], array('double(24,8)', 'double(6,3)', 'integer', 'real', 'price')) && $key != 'rowid' && $val['label'] != 'TechnicalID' && empty($val['arrayofkeyval'])) {
552 $cssforfield .= ($cssforfield ? ' ' : '').'right';
553 }
554 if (!empty($arrayfields['t.'.$key]['checked'])) {
555 print '<td class="liste_titre'.($cssforfield ? ' '.$cssforfield : '').($key == 'status' ? ' parentonrightofpage' : '').'">';
556 if (!empty($val['arrayofkeyval']) && is_array($val['arrayofkeyval'])) {
557 print $form->selectarray('search_'.$key, $val['arrayofkeyval'], (isset($search[$key]) ? $search[$key] : ''), $val['notnull'], 0, 0, '', 1, 0, 0, '', 'maxwidth100'.($key == 'status' ? ' search_status width100 onrightofpage' : ''), 1);
558 } elseif ((strpos($val['type'], 'integer:') === 0) || (strpos($val['type'], 'sellist:') === 0)) {
559 print $object->showInputField($val, $key, (isset($search[$key]) ? $search[$key] : ''), '', '', 'search_', $cssforfield.' maxwidth250', 1);
560 } elseif (preg_match('/^(date|timestamp|datetime)/', $val['type'])) {
561 print '<div class="nowrap">';
562 print $form->selectDate($search[$key.'_dtstart'] ? $search[$key.'_dtstart'] : '', "search_".$key."_dtstart", 0, 0, 1, '', 1, 0, 0, '', '', '', '', 1, '', $langs->trans('From'));
563 print '</div>';
564 print '<div class="nowrap">';
565 print $form->selectDate($search[$key.'_dtend'] ? $search[$key.'_dtend'] : '', "search_".$key."_dtend", 0, 0, 1, '', 1, 0, 0, '', '', '', '', 1, '', $langs->trans('to'));
566 print '</div>';
567 } elseif ($key == 'lang') {
568 require_once DOL_DOCUMENT_ROOT.'/core/class/html.formadmin.class.php';
569 $formadmin = new FormAdmin($db);
570 print $formadmin->select_language($search[$key], 'search_lang', 0, array(), 1, 0, 0, 'minwidth100imp maxwidth125', 2);
571 } else {
572 print '<input type="text" class="flat maxwidth'.($val['type'] == 'integer' ? '50' : '75').'" name="search_'.$key.'" value="'.dol_escape_htmltag(isset($search[$key]) ? $search[$key] : '').'">';
573 }
574 print '</td>';
575 }
576}
577// Extra fields
578include DOL_DOCUMENT_ROOT.'/core/tpl/extrafields_list_search_input.tpl.php';
579
580// Fields from hook
581$parameters = array('arrayfields' => $arrayfields);
582$reshook = $hookmanager->executeHooks('printFieldListOption', $parameters, $object, $action); // Note that $action and $object may have been modified by hook
583print $hookmanager->resPrint;
584/*if (!empty($arrayfields['anotherfield']['checked'])) {
585 print '<td class="liste_titre"></td>';
586}*/
587// Action column
588if (!getDolGlobalString('MAIN_CHECKBOX_LEFT_COLUMN')) {
589 print '<td class="liste_titre center maxwidthsearch">';
590 $searchpicto = $form->showFilterButtons();
591 print $searchpicto;
592 print '</td>';
593}
594print '</tr>'."\n";
595
596$totalarray = array();
597$totalarray['nbfield'] = 0;
598
599// Fields title label
600// --------------------------------------------------------------------
601print '<tr class="liste_titre">';
602// Action column
603if (getDolGlobalString('MAIN_CHECKBOX_LEFT_COLUMN')) {
604 print getTitleFieldOfList($selectedfields, 0, $_SERVER["PHP_SELF"], '', '', '', '', $sortfield, $sortorder, 'center maxwidthsearch ')."\n";
605 $totalarray['nbfield']++;
606}
607foreach ($object->fields as $key => $val) {
608 $cssforfield = (empty($val['csslist']) ? (empty($val['css']) ? '' : $val['css']) : $val['csslist']);
609 if ($key == 'status') {
610 $cssforfield .= ($cssforfield ? ' ' : '').'center';
611 } elseif (in_array($val['type'], array('date', 'datetime', 'timestamp'))) {
612 $cssforfield .= ($cssforfield ? ' ' : '').'center';
613 } elseif (in_array($val['type'], array('timestamp'))) {
614 $cssforfield .= ($cssforfield ? ' ' : '').'nowrap';
615 } elseif (in_array($val['type'], array('double(24,8)', 'double(6,3)', 'integer', 'real', 'price')) && $key != 'rowid' && $val['label'] != 'TechnicalID' && empty($val['arrayofkeyval'])) {
616 $cssforfield .= ($cssforfield ? ' ' : '').'right';
617 }
618 $cssforfield = preg_replace('/small\s*/', '', $cssforfield); // the 'small' css must not be used for the title label
619 if (!empty($arrayfields['t.'.$key]['checked'])) {
620 print getTitleFieldOfList($arrayfields['t.'.$key]['label'], 0, $_SERVER['PHP_SELF'], 't.'.$key, '', $param, ($cssforfield ? 'class="'.$cssforfield.'"' : ''), $sortfield, $sortorder, ($cssforfield ? $cssforfield.' ' : ''), 0, (empty($val['helplist']) ? '' : $val['helplist']))."\n";
621 $totalarray['nbfield']++;
622 }
623}
624// Extra fields
625include DOL_DOCUMENT_ROOT.'/core/tpl/extrafields_list_search_title.tpl.php';
626// Hook fields
627$parameters = array('arrayfields' => $arrayfields, 'param' => $param, 'sortfield' => $sortfield, 'sortorder' => $sortorder, 'totalarray' => &$totalarray);
628$reshook = $hookmanager->executeHooks('printFieldListTitle', $parameters, $object, $action); // Note that $action and $object may have been modified by hook
629print $hookmanager->resPrint;
630/*if (!empty($arrayfields['anotherfield']['checked'])) {
631 print '<th class="liste_titre right">'.$langs->trans("AnotherField").'</th>';
632 $totalarray['nbfield']++;
633}*/
634// Action column
635if (!getDolGlobalString('MAIN_CHECKBOX_LEFT_COLUMN')) {
636 print getTitleFieldOfList($selectedfields, 0, $_SERVER["PHP_SELF"], '', '', '', '', $sortfield, $sortorder, 'center maxwidthsearch ')."\n";
637 $totalarray['nbfield']++;
638}
639print '</tr>'."\n";
640
641
642// Detect if we need a fetch on each output line
643$needToFetchEachLine = 0;
644if (isset($extrafields->attributes[$object->table_element]['computed']) && is_array($extrafields->attributes[$object->table_element]['computed']) && count($extrafields->attributes[$object->table_element]['computed']) > 0) {
645 foreach ($extrafields->attributes[$object->table_element]['computed'] as $key => $val) {
646 if (!is_null($val) && preg_match('/\$object/', $val)) {
647 $needToFetchEachLine++; // There is at least one compute field that use $object
648 }
649 }
650}
651
652
653// Loop on record
654// --------------------------------------------------------------------
655$i = 0;
656$savnbfield = $totalarray['nbfield'];
657$totalarray = array();
658$totalarray['nbfield'] = 0;
659$imaxinloop = ($limit ? min($num, $limit) : $num);
660while ($i < $imaxinloop) {
661 $obj = $db->fetch_object($resql);
662 if (empty($obj)) {
663 break; // Should not happen
664 }
665
666 // Store properties in $object
667 $object->setVarsFromFetchObj($obj);
668
669 if ($mode == 'kanban') {
670 if ($i == 0) {
671 print '<tr class="trkanban"><td colspan="'.$savnbfield.'">';
672 print '<div class="box-flex-container kanban">';
673 }
674 // Output Kanban
675 $selected = -1;
676 if ($massactionbutton || $massaction) { // If we are in select mode (massactionbutton defined) or if we have already selected and sent an action ($massaction) defined
677 $selected = 0;
678 if (in_array($object->id, $arrayofselected)) {
679 $selected = 1;
680 }
681 }
682 print $object->getKanbanView('', array('selected' => $selected));
683 if ($i == ($imaxinloop - 1)) {
684 print '</div>';
685 print '</td></tr>';
686 }
687 } else {
688 // Show line of result
689 $j = 0;
690 print '<tr data-rowid="'.$object->id.'" class="oddeven">';
691 // Action column
692 if (getDolGlobalString('MAIN_CHECKBOX_LEFT_COLUMN')) {
693 print '<td class="nowrap center">';
694 if ($massactionbutton || $massaction) { // If we are in select mode (massactionbutton defined) or if we have already selected and sent an action ($massaction) defined
695 $selected = 0;
696 if (in_array($object->id, $arrayofselected)) {
697 $selected = 1;
698 }
699 print '<input id="cb'.$object->id.'" class="flat checkforselect" type="checkbox" name="toselect[]" value="'.$object->id.'"'.($selected ? ' checked="checked"' : '').'>';
700 }
701 print '</td>';
702 if (!$i) {
703 $totalarray['nbfield']++;
704 }
705 }
706 foreach ($object->fields as $key => $val) {
707 $cssforfield = (empty($val['csslist']) ? (empty($val['css']) ? '' : $val['css']) : $val['csslist']);
708 if (in_array($val['type'], array('date', 'datetime', 'timestamp'))) {
709 $cssforfield .= ($cssforfield ? ' ' : '').'center';
710 } elseif ($key == 'status') {
711 $cssforfield .= ($cssforfield ? ' ' : '').'center';
712 }
713
714 if (in_array($val['type'], array('timestamp'))) {
715 $cssforfield .= ($cssforfield ? ' ' : '').'nowraponall';
716 } elseif ($key == 'ref') {
717 $cssforfield .= ($cssforfield ? ' ' : '').'nowraponall';
718 }
719
720 if (in_array($val['type'], array('double(24,8)', 'double(6,3)', 'integer', 'real', 'price')) && !in_array($key, array('rowid', 'status')) && empty($val['arrayofkeyval'])) {
721 $cssforfield .= ($cssforfield ? ' ' : '').'right';
722 }
723 //if (in_array($key, array('fk_soc', 'fk_user', 'fk_warehouse'))) $cssforfield = 'tdoverflowmax100';
724
725 if (!empty($arrayfields['t.'.$key]['checked'])) {
726 print '<td'.($cssforfield ? ' class="'.$cssforfield.(preg_match('/tdoverflow/', $cssforfield) ? ' classfortooltip' : '').'"' : '');
727 if (preg_match('/tdoverflow/', $cssforfield) && !is_numeric($object->$key)) {
728 print ' title="'.dol_escape_htmltag($object->$key).'"';
729 }
730 print '>';
731 if ($key == 'status') {
732 print $object->getLibStatut(5);
733 } elseif ($key == 'rowid') {
734 print $object->showOutputField($val, $key, $object->id, '');
735 } else {
736 print $object->showOutputField($val, $key, $object->$key, '');
737 }
738 print '</td>';
739 if (!$i) {
740 $totalarray['nbfield']++;
741 }
742 if (!empty($val['isameasure']) && $val['isameasure'] == 1) {
743 if (!$i) {
744 $totalarray['pos'][$totalarray['nbfield']] = 't.'.$key;
745 }
746 if (!isset($totalarray['val'])) {
747 $totalarray['val'] = array();
748 }
749 if (!isset($totalarray['val']['t.'.$key])) {
750 $totalarray['val']['t.'.$key] = 0;
751 }
752 $totalarray['val']['t.'.$key] += $object->$key;
753 }
754 }
755 }
756 // Extra fields
757 include DOL_DOCUMENT_ROOT.'/core/tpl/extrafields_list_print_fields.tpl.php';
758 // Fields from hook
759 $parameters = array('arrayfields' => $arrayfields, 'object' => $object, 'obj' => $obj, 'i' => $i, 'totalarray' => &$totalarray);
760 $reshook = $hookmanager->executeHooks('printFieldListValue', $parameters, $object, $action); // Note that $action and $object may have been modified by hook
761 print $hookmanager->resPrint;
762 /*if (!empty($arrayfields['anotherfield']['checked'])) {
763 print '<td class="right">'.$obj->anotherfield.'</td>';
764 }*/
765 // Action column
766 if (!getDolGlobalString('MAIN_CHECKBOX_LEFT_COLUMN')) {
767 print '<td class="nowrap center">';
768 if ($massactionbutton || $massaction) { // If we are in select mode (massactionbutton defined) or if we have already selected and sent an action ($massaction) defined
769 $selected = 0;
770 if (in_array($object->id, $arrayofselected)) {
771 $selected = 1;
772 }
773 print '<input id="cb'.$object->id.'" class="flat checkforselect" type="checkbox" name="toselect[]" value="'.$object->id.'"'.($selected ? ' checked="checked"' : '').'>';
774 }
775 print '</td>';
776 if (!$i) {
777 $totalarray['nbfield']++;
778 }
779 }
780
781 print '</tr>'."\n";
782 }
783
784 $i++;
785}
786
787// Show total line
788include DOL_DOCUMENT_ROOT.'/core/tpl/list_print_total.tpl.php';
789
790// If no record found
791if ($num == 0) {
792 $colspan = 1;
793 foreach ($arrayfields as $key => $val) {
794 if (!empty($val['checked'])) {
795 $colspan++;
796 }
797 }
798 print '<tr><td colspan="'.$colspan.'"><span class="opacitymedium">'.$langs->trans("NoRecordFound").'</span></td></tr>';
799}
800
801
802$db->free($resql);
803
804$parameters = array('arrayfields' => $arrayfields, 'sql' => $sql);
805$reshook = $hookmanager->executeHooks('printFieldListFooter', $parameters, $object, $action); // Note that $action and $object may have been modified by hook
806print $hookmanager->resPrint;
807
808print '</table>'."\n";
809print '</div>'."\n";
810
811print '</form>'."\n";
812
813if (in_array('builddoc', array_keys($arrayofmassactions)) && ($nbtotalofrecords === '' || $nbtotalofrecords)) {
814 $hidegeneratedfilelistifempty = 1;
815 if ($massaction == 'builddoc' || $action == 'remove_file' || $show_files) {
816 $hidegeneratedfilelistifempty = 0;
817 }
818
819 require_once DOL_DOCUMENT_ROOT.'/core/class/html.formfile.class.php';
820 $formfile = new FormFile($db);
821
822 // Show list of available documents
823 $urlsource = $_SERVER['PHP_SELF'].'?sortfield='.$sortfield.'&sortorder='.$sortorder;
824 $urlsource .= str_replace('&amp;', '&', $param);
825
826 $filedir = $diroutputmassaction;
827 $genallowed = $permissiontoread;
828 $delallowed = $permissiontoadd;
829
830 print $formfile->showdocuments('massfilesarea_'.$object->module, '', $filedir, $urlsource, 0, $delallowed, '', 1, 1, 0, 48, 1, $param, $title, '', '', '', null, $hidegeneratedfilelistifempty);
831}
832
833// End of page
834llxFooter();
835$db->close();
$id
Definition account.php:48
if( $user->socid > 0) if(! $user->hasRight('accounting', 'chartofaccount')) $object
Definition card.php:66
llxFooter($comment='', $zone='private', $disabledoutputofmessages=0)
Empty footer.
Definition wrapper.php:87
if(!defined('NOREQUIRESOC')) if(!defined( 'NOREQUIRETRAN')) if(!defined('NOTOKENRENEWAL')) if(!defined( 'NOREQUIREMENU')) if(!defined('NOREQUIREHTML')) if(!defined( 'NOREQUIREAJAX')) llxHeader($head='', $title='', $help_url='', $target='', $disablejs=0, $disablehead=0, $arrayofjs='', $arrayofcss='', $morequerystring='', $morecssonbody='', $replacemainareaby='', $disablenofollow=0, $disablenoindex=0)
Empty header.
Definition wrapper.php:71
Class for Availabilities.
Class to manage standard extra fields.
Class to generate html code for admin pages.
Class to offer components to list and upload files.
Class to manage generation of HTML components Only common components must be here.
dol_mktime($hour, $minute, $second, $month, $day, $year, $gm='auto', $check=1)
Return a timestamp date built from detailed information (by default a local PHP server timestamp) Rep...
setEventMessages($mesg, $mesgs, $style='mesgs', $messagekey='', $noduplicate=0, $attop=0)
Set event messages in dol_events session object.
print_barre_liste($title, $page, $file, $options='', $sortfield='', $sortorder='', $morehtmlcenter='', $num=-1, $totalnboflines='', $picto='generic', $pictoisfullpath=0, $morehtmlright='', $morecss='', $limit=-1, $selectlimitsuffix=0, $hidenavigation=0, $pagenavastextinput=0, $morehtmlrightbeforearrow='')
Print a title with navigation controls for pagination.
img_picto($titlealt, $picto, $moreatt='', $pictoisfullpath=0, $srconly=0, $notitle=0, $alt='', $morecss='', $marginleftonlyshort=2, $allowothertags=array())
Show picto whatever it's its name (generic function)
GETPOSTINT($paramname, $method=0)
Return the value of a $_GET or $_POST supervariable, converted into integer.
dolGetButtonTitle($label, $helpText='', $iconClass='fa fa-file', $url='', $id='', $status=1, $params=array())
Function dolGetButtonTitle : this kind of buttons are used in title in list.
dol_eval($s, $returnvalue=1, $hideerrors=1, $onlysimplestring='1')
Replace eval function to add more security.
natural_search($fields, $value, $mode=0, $nofirstand=0)
Generate natural SQL search string for a criteria (this criteria can be tested on one or several fiel...
dol_now($mode='auto')
Return date for now.
getDolGlobalInt($key, $default=0)
Return a Dolibarr global constant int value.
dol_sort_array(&$array, $index, $order='asc', $natsort=0, $case_sensitive=0, $keepindex=0)
Advanced sort array by the value of a given key, which produces ascending (default) or descending out...
getTitleFieldOfList($name, $thead=0, $file="", $field="", $begin="", $moreparam="", $moreattrib="", $sortfield="", $sortorder="", $prefix="", $disablesortlink=0, $tooltip='', $forcenowrapcolumntitle=0)
Get title line of an array.
dolGetButtonTitleSeparator($moreClass="")
Add space between dolGetButtonTitle.
GETPOST($paramname, $check='alphanohtml', $method=0, $filter=null, $options=null, $noreplace=0)
Return value of a param into GET or POST supervariable.
dol_buildpath($path, $type=0, $returnemptyifnotfound=0)
Return path of url or filesystem.
dol_print_error($db=null, $error='', $errors=null)
Displays error message system with all the information to facilitate the diagnosis and the escalation...
getDolGlobalString($key, $default='')
Return a Dolibarr global constant string value.
dol_escape_htmltag($stringtoescape, $keepb=0, $keepn=0, $noescapetags='', $escapeonlyhtmltags=0, $cleanalsojavascript=0)
Returns text escaped for inclusion in HTML alt or title or value tags, or into values of HTML input f...
global $conf
The following vars must be defined: $type2label $form $conf, $lang, The following vars may also be de...
Definition member.php:79
accessforbidden($message='', $printheader=1, $printfooter=1, $showonlymessage=0, $params=null)
Show a message to say access is forbidden and stop program.