dolibarr 22.0.5
workstation_list.php
Go to the documentation of this file.
1<?php
2
3/* Copyright (C) 2007-2017 Laurent Destailleur <eldy@users.sourceforge.net>
4 * Copyright (C) 2020 Gauthier VERDOL <gauthier.verdol@atm-consulting.fr>
5 * Copyright (C) 2024-2025 MDW <mdeweerd@users.noreply.github.com>
6 * Copyright (C) 2024 Frédéric France <frederic.france@free.fr>
7 *
8 * This program is free software; you can redistribute it and/or modify
9 * it under the terms of the GNU General Public License as published by
10 * the Free Software Foundation; either version 3 of the License, or
11 * (at your option) any later version.
12 *
13 * This program is distributed in the hope that it will be useful,
14 * but WITHOUT ANY WARRANTY; without even the implied warranty of
15 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
16 * GNU General Public License for more details.
17 *
18 * You should have received a copy of the GNU General Public License
19 * along with this program. If not, see <https://www.gnu.org/licenses/>.
20 */
21
28// Load Dolibarr environment
29require '../main.inc.php';
30require_once DOL_DOCUMENT_ROOT.'/core/class/html.formcompany.class.php';
31require_once DOL_DOCUMENT_ROOT.'/core/lib/company.lib.php';
32require_once DOL_DOCUMENT_ROOT.'/core/lib/date.lib.php';
33require_once DOL_DOCUMENT_ROOT.'/resource/class/html.formresource.class.php';
34require_once DOL_DOCUMENT_ROOT.'/workstation/class/workstation.class.php';
35
44// Load translation files required by the page
45$langs->loadLangs(array('mrp', 'other'));
46
47$action = GETPOST('action', 'aZ09') ? GETPOST('action', 'aZ09') : 'view'; // The action 'create'/'add', 'edit'/'update', 'view', ...
48$massaction = GETPOST('massaction', 'alpha'); // The bulk action (combo box choice into lists)
49$show_files = GETPOSTINT('show_files'); // Show files area generated by bulk actions ?
50$confirm = GETPOST('confirm', 'alpha'); // Result of a confirmation
51$cancel = GETPOST('cancel', 'alpha'); // We click on a Cancel button
52$toselect = GETPOST('toselect', 'array'); // Array of ids of elements selected into a list
53$contextpage = GETPOST('contextpage', 'aZ') ? GETPOST('contextpage', 'aZ') : str_replace('_', '', basename(dirname(__FILE__)).basename(__FILE__, '.php')); // To manage different context of search
54$backtopage = GETPOST('backtopage', 'alpha'); // Go back to a dedicated page
55$optioncss = GETPOST('optioncss', 'aZ'); // Option for the css output (always '' except when 'print')
56$mode = GETPOST('mode', 'aZ'); // The output mode ('list', 'kanban', 'hierarchy', 'calendar', ...)
57
58
59// Load variables for pagination
60$id = GETPOSTINT('id');
61$ref = GETPOST('ref', 'alpha');
62
63// Load variable for pagination
64$limit = GETPOSTINT('limit') ? GETPOSTINT('limit') : $conf->liste_limit;
65$sortfield = GETPOST('sortfield', 'aZ09comma');
66$sortorder = GETPOST('sortorder', 'aZ09comma');
67$page = GETPOSTISSET('pageplusone') ? (GETPOSTINT('pageplusone') - 1) : GETPOSTINT("page");
68if (empty($page) || $page < 0 || GETPOST('button_search', 'alpha') || GETPOST('button_removefilter', 'alpha')) {
69 // If $page is not defined, or '' or -1 or if we click on clear filters
70 $page = 0;
71}
72$offset = $limit * $page;
73$pageprev = $page - 1;
74$pagenext = $page + 1;
75
76// Initialize a technical objects
77$object = new Workstation($db);
78$extrafields = new ExtraFields($db);
79$diroutputmassaction = $conf->workstation->dir_output.'/temp/massgeneration/'.$user->id;
80$hookmanager->initHooks(array('workstationlist')); // Note that conf->hooks_modules contains array
81
82// Fetch optionals attributes and labels
83$extrafields->fetch_name_optionals_label($object->table_element);
84//$extrafields->fetch_name_optionals_label($object->table_element_line);
85
86$search_array_options = $extrafields->getOptionalsFromPost($object->table_element, '', 'search_');
87
88// Default sort order (if not yet defined by previous GETPOST)
89if (!$sortfield) {
90 $sortfield = "t.ref"; // Set here default search field. By default 1st field in definition.
91}
92if (!$sortorder) {
93 $sortorder = "ASC";
94}
95
96// Initialize array of search criteria
97$search_all = trim(GETPOST('search_all', 'alphanohtml'));
98$search = array();
99
100foreach ($object->fields as $key => $val) {
101 if (GETPOST('search_'.$key, 'alpha') !== '') {
102 $search[$key] = GETPOST('search_'.$key, 'alpha');
103 }
104 if (preg_match('/^(date|timestamp|datetime)/', $val['type'])) {
105 $search[$key.'_dtstart'] = dol_mktime(0, 0, 0, GETPOSTINT('search_'.$key.'_dtstartmonth'), GETPOSTINT('search_'.$key.'_dtstartday'), GETPOSTINT('search_'.$key.'_dtstartyear'));
106 $search[$key.'_dtend'] = dol_mktime(23, 59, 59, GETPOSTINT('search_'.$key.'_dtendmonth'), GETPOSTINT('search_'.$key.'_dtendday'), GETPOSTINT('search_'.$key.'_dtendyear'));
107 }
108}
109
110$groups = GETPOST('groups', 'array:int');
111$resources = GETPOST('resources', 'array:int');
112
113// List of fields to search into when doing a "search in all"
114$fieldstosearchall = array();
115foreach ($object->fields as $key => $val) {
116 if (!empty($val['searchall'])) {
117 $fieldstosearchall['t.'.$key] = $val['label'];
118 }
119}
120
121// Definition of array of fields for columns
122$arrayfields = array();
123foreach ($object->fields as $key => $val) {
124 // If $val['visible']==0, then we never show the field
125 if (!empty($val['visible'])) {
126 $visible = (int) dol_eval((string) $val['visible'], 1);
127 $arrayfields['t.'.$key] = array(
128 'label' => $val['label'],
129 'checked' => (($visible < 0) ? '0' : '1'),
130 'enabled' => (string) (int) (abs($visible) != 3 && (bool) dol_eval((string) $val['enabled'], 1)),
131 'position' => $val['position'],
132 'help' => isset($val['help']) ? $val['help'] : ''
133 );
134 }
135}
136
137$arrayfields['wug.fk_usergroup'] = array(
138 'label' => $langs->trans('UserGroups'),
139 'checked' => (($visible < 0) ? '0' : '1'),
140 'enabled' => (string) (int) (abs($visible) != 3 && (bool) dol_eval((string) $val['enabled'], 1)),
141 'position' => 1000,
142 'help' => empty($val['help']) ? '' : $val['help'],
143 'csslist' => 'minwidth100'
144);
145
146/* disabled because adding resources to workstation seems not yet available in GUI
147$arrayfields['wr.fk_resource'] = array(
148 'label'=>$langs->trans('Resources'),
149 'checked'=>(($visible < 0) ? '0' : '1'),
150 'enabled'=>(string)(int)(abs($visible) != 3 && (bool) dol_eval((string) $val['enabled'], 1)),
151 'position'=>1001,
152 'help' => empty($val['help']) ? '' : $val['help']
153);
154*/
155
156// Extra fields
157include DOL_DOCUMENT_ROOT.'/core/tpl/extrafields_list_array_fields.tpl.php';
158
159$object->fields = dol_sort_array($object->fields, 'position');
160$arrayfields = dol_sort_array($arrayfields, 'position');
161
162// Permissions
163$permissiontoread = $user->hasRight('workstation', 'workstation', 'read');
164$permissiontoadd = $user->hasRight('workstation', 'workstation', 'write');
165$permissiontodelete = $user->hasRight('workstation', 'workstation', 'delete');
166
167// Security check
168restrictedArea($user, $object->element, 0, $object->table_element, 'workstation');
169
170
171
172/*
173 * Actions
174 */
175
176if (GETPOST('cancel', 'alpha')) {
177 $action = 'list';
178 $massaction = '';
179}
180if (!GETPOST('confirmmassaction', 'alpha') && $massaction != 'presend' && $massaction != 'confirm_presend') {
181 $massaction = '';
182}
183
184$parameters = array();
185$reshook = $hookmanager->executeHooks('doActions', $parameters, $object, $action); // Note that $action and $object may have been modified by some hooks
186if ($reshook < 0) {
187 setEventMessages($hookmanager->error, $hookmanager->errors, 'errors');
188}
189
190if (empty($reshook)) {
191 // Selection of new fields
192 include DOL_DOCUMENT_ROOT.'/core/actions_changeselectedfields.inc.php';
193
194 // Purge search criteria
195 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
196 foreach ($object->fields as $key => $val) {
197 $search[$key] = '';
198 if (preg_match('/^(date|timestamp|datetime)/', $val['type'])) {
199 $search[$key.'_dtstart'] = '';
200 $search[$key.'_dtend'] = '';
201 }
202 }
203 $groups = $resources = array();
204 $toselect = array();
205 $search_array_options = array();
206 }
207 if (GETPOST('button_removefilter_x', 'alpha') || GETPOST('button_removefilter.x', 'alpha') || GETPOST('button_removefilter', 'alpha')
208 || GETPOST('button_search_x', 'alpha') || GETPOST('button_search.x', 'alpha') || GETPOST('button_search', 'alpha')) {
209 $massaction = ''; // Protection to avoid mass action if we force a new search during a mass action confirmation
210 }
211
212 // Mass actions
213 $objectclass = 'Workstation';
214 $objectlabel = 'Workstation';
215 $uploaddir = $conf->workstation->dir_output;
216 include DOL_DOCUMENT_ROOT.'/core/actions_massactions.inc.php';
217}
218
219
220
221/*
222 * View
223 */
224
225$form = new Form($db);
226$formresource = new FormResource($db);
227
228$now = dol_now();
229
230$title = $langs->trans("Workstations");
231$help_url = 'EN:Module_Workstation';
232$morejs = array();
233$morecss = array();
234// llxHeader -> look down at section Output page
235
236
237// Build and execute select
238// --------------------------------------------------------------------
239$sql = 'SELECT ';
240$sql .= $object->getFieldList('t');
241// Add fields from extrafields
242if (!empty($extrafields->attributes[$object->table_element]['label'])) {
243 foreach ($extrafields->attributes[$object->table_element]['label'] as $key => $val) {
244 // @phan-suppress-next-line PhanTypeArraySuspiciousNullable
245 $sql .= ($extrafields->attributes[$object->table_element]['type'][$key] != 'separate' ? ", ef.".$key." as options_".$key : '');
246 }
247}
248
249// Add fields from hooks
250$parameters = array();
251$reshook = $hookmanager->executeHooks('printFieldListSelect', $parameters, $object, $action); // Note that $action and $object may have been modified by hook
252$sql .= $hookmanager->resPrint;
253$sql = preg_replace('/,\s*$/', '', $sql);
254
255$sqlfields = $sql; // $sql fields to remove for count total
256
257$sql .= " FROM ".MAIN_DB_PREFIX.$object->table_element." as t";
258if (isset($extrafields->attributes[$object->table_element]['label']) && is_array($extrafields->attributes[$object->table_element]['label']) && count($extrafields->attributes[$object->table_element]['label'])) {
259 $sql .= " LEFT JOIN ".MAIN_DB_PREFIX.$object->table_element."_extrafields as ef on (t.rowid = ef.fk_object)";
260}
261if (!empty($groups)) {
262 $sql .= ' LEFT JOIN '.MAIN_DB_PREFIX.'workstation_workstation_usergroup wug ON (wug.fk_workstation = t.rowid)';
263}
264if (!empty($resources)) {
265 $sql .= ' LEFT JOIN '.MAIN_DB_PREFIX.'workstation_workstation_resource wr ON (wr.fk_workstation = t.rowid)';
266}
267
268// Add table from hooks
269$parameters = array();
270$reshook = $hookmanager->executeHooks('printFieldListFrom', $parameters, $object, $action); // Note that $action and $object may have been modified by hook
271$sql .= $hookmanager->resPrint;
272if ($object->ismultientitymanaged == 1) {
273 $sql .= " WHERE t.entity IN (".getEntity($object->element, (GETPOSTINT('search_current_entity') ? 0 : 1)).")";
274} else {
275 $sql .= " WHERE 1 = 1";
276}
277foreach ($search as $key => $val) {
278 if (array_key_exists($key, $object->fields)) {
279 if ($key == 'status' && $search[$key] == -1) {
280 continue;
281 }
282 $mode_search = (($object->isInt($object->fields[$key]) || $object->isFloat($object->fields[$key])) ? 1 : 0);
283 if ((strpos($object->fields[$key]['type'], 'integer:') === 0) || (strpos($object->fields[$key]['type'], 'sellist:') === 0) || !empty($object->fields[$key]['arrayofkeyval'])) {
284 if ($search[$key] == '-1' || ($search[$key] === '0' && (empty($object->fields[$key]['arrayofkeyval']) || !array_key_exists('0', $object->fields[$key]['arrayofkeyval'])))) {
285 $search[$key] = '';
286 }
287 $mode_search = 2;
288 }
289 if ($search[$key] != '') {
290 $sql .= natural_search("t.".$db->escape($key), $search[$key], (($key == 'status') ? 2 : $mode_search));
291 }
292 } else {
293 if (preg_match('/(_dtstart|_dtend)$/', $key) && $search[$key] != '') {
294 $columnName = preg_replace('/(_dtstart|_dtend)$/', '', $key);
295 if (preg_match('/^(date|timestamp|datetime)/', $object->fields[$columnName]['type'])) {
296 if (preg_match('/_dtstart$/', $key)) {
297 $sql .= " AND t.".$db->escape($columnName)." >= '".$db->idate($search[$key])."'";
298 }
299 if (preg_match('/_dtend$/', $key)) {
300 $sql .= " AND t.".$db->escape($columnName)." <= '".$db->idate($search[$key])."'";
301 }
302 }
303 }
304 }
305}
306if ($search_all) {
307 $sql .= natural_search(array_keys($fieldstosearchall), $search_all);
308}
309//$sql.= dolSqlDateFilter("t.field", $search_xxxday, $search_xxxmonth, $search_xxxyear);
310// Add where from extra fields
311
312// usergroups
313if (!empty($groups)) {
314 $sql .= ' AND wug.fk_usergroup IN('.$db->sanitize(implode(',', $groups)).')';
315}
316
317// resources
318if (!empty($resources)) {
319 $sql .= ' AND wr.fk_resource IN('.$db->sanitize(implode(',', $resources)).')';
320}
321
322include DOL_DOCUMENT_ROOT.'/core/tpl/extrafields_list_search_sql.tpl.php';
323// Add where from hooks
324$parameters = array();
325$reshook = $hookmanager->executeHooks('printFieldListWhere', $parameters, $object, $action); // Note that $action and $object may have been modified by hook
326$sql .= $hookmanager->resPrint;
327
328$sql .= " GROUP BY ";
329foreach ($object->fields as $key => $val) {
330 $sql .= "t.".$db->escape($key).", ";
331}
332// Add fields from extrafields
333if (! empty($extrafields->attributes[$object->table_element]['label'])) {
334 foreach ($extrafields->attributes[$object->table_element]['label'] as $key => $val) {
335 // @phan-suppress-next-line PhanTypeArraySuspiciousNullable
336 $sql .= ($extrafields->attributes[$object->table_element]['type'][$key] != 'separate' ? "ef.".$key.', ' : '');
337 }
338}
339// Add groupby from hooks
340$parameters = array();
341$reshook = $hookmanager->executeHooks('printFieldListGroupBy', $parameters, $object); // Note that $action and $object may have been modified by hook
342$sql .= $hookmanager->resPrint;
343$sql = preg_replace('/,\s*$/', '', $sql);
344
345// Count total nb of records
346$nbtotalofrecords = '';
347if (!getDolGlobalInt('MAIN_DISABLE_FULL_SCANLIST')) {
348 /* The fast and low memory method to get and count full list converts the sql into a sql count */
349 $sqlforcount = preg_replace('/^'.preg_quote($sqlfields, '/').'/', 'SELECT COUNT(*) as nbtotalofrecords', $sql);
350 $sqlforcount = preg_replace('/GROUP BY .*$/', '', $sqlforcount);
351
352 $resql = $db->query($sqlforcount);
353 if ($resql) {
354 $objforcount = $db->fetch_object($resql);
355 $nbtotalofrecords = $objforcount->nbtotalofrecords;
356 } else {
357 dol_print_error($db);
358 }
359
360 if (($page * $limit) > $nbtotalofrecords) { // if total resultset is smaller than the paging size (filtering), goto and load page 0
361 $page = 0;
362 $offset = 0;
363 }
364 $db->free($resql);
365}
366
367// Complete request and execute it with limit
368$sql .= $db->order($sortfield, $sortorder);
369if ($limit) {
370 $sql .= $db->plimit($limit + 1, $offset);
371}
372
373$resql = $db->query($sql);
374if (!$resql) {
375 dol_print_error($db);
376 exit;
377}
378
379$num = $db->num_rows($resql);
380
381
382// Direct jump if only one record found
383if ($num == 1 && getDolGlobalInt('MAIN_SEARCH_DIRECT_OPEN_IF_ONLY_ONE') && $search_all && !$page) {
384 $obj = $db->fetch_object($resql);
385 $id = $obj->rowid;
386 header("Location: ".DOL_URL_ROOT.'/workstation/workstation_card.php?id='.((int) $id));
387 exit;
388}
389
390
391// Output page
392// --------------------------------------------------------------------
393
394llxHeader('', $title, $help_url, '', 0, 0, $morejs, $morecss, '', 'classforhorizontalscrolloftabs');
395
396$arrayofselected = is_array($toselect) ? $toselect : array();
397
398$param = '';
399if (!empty($mode)) {
400 $param .= '&mode='.urlencode($mode);
401}
402if (!empty($contextpage) && $contextpage != $_SERVER["PHP_SELF"]) {
403 $param .= '&contextpage='.urlencode($contextpage);
404}
405if ($limit > 0 && $limit != $conf->liste_limit) {
406 $param .= '&limit='.((int) $limit);
407}
408if ($optioncss != '') {
409 $param .= '&optioncss='.urlencode($optioncss);
410}
411foreach ($search as $key => $val) {
412 if (is_array($search[$key])) {
413 foreach ($search[$key] as $skey) {
414 if ($skey != '') {
415 $param .= '&search_'.$key.'[]='.urlencode($skey);
416 }
417 }
418 } elseif (preg_match('/(_dtstart|_dtend)$/', $key) && !empty($val)) {
419 $param .= '&search_'.$key.'month='.(GETPOSTINT('search_'.$key.'month'));
420 $param .= '&search_'.$key.'day='.(GETPOSTINT('search_'.$key.'day'));
421 $param .= '&search_'.$key.'year='.(GETPOSTINT('search_'.$key.'year'));
422 } elseif ($search[$key] != '') {
423 $param .= '&search_'.$key.'='.urlencode($search[$key]);
424 }
425}
426// Add $param from extra fields
427include DOL_DOCUMENT_ROOT.'/core/tpl/extrafields_list_search_param.tpl.php';
428// Add $param from hooks
429$parameters = array('param' => &$param);
430$reshook = $hookmanager->executeHooks('printFieldListSearchParam', $parameters, $object, $action); // Note that $action and $object may have been modified by hook
431$param .= $hookmanager->resPrint;
432
433// List of mass actions available
434$arrayofmassactions = array(
435 //'validate'=>img_picto('', 'check', 'class="pictofixedwidth"').$langs->trans("Validate"),
436 //'generate_doc'=>img_picto('', 'pdf', 'class="pictofixedwidth"').$langs->trans("ReGeneratePDF"),
437 //'builddoc'=>img_picto('', 'pdf', 'class="pictofixedwidth"').$langs->trans("PDFMerge"),
438 //'presend'=>img_picto('', 'email', 'class="pictofixedwidth"').$langs->trans("SendByMail"),
439);
440if (!empty($permissiontodelete)) {
441 $arrayofmassactions['predelete'] = img_picto('', 'delete', 'class="pictofixedwidth"').$langs->trans("Delete");
442}
443if (GETPOSTINT('nomassaction') || in_array($massaction, array('presend', 'predelete'))) {
444 $arrayofmassactions = array();
445}
446$massactionbutton = $form->selectMassAction('', $arrayofmassactions);
447
448print '<form method="POST" id="searchFormList" action="'.$_SERVER["PHP_SELF"].'">'."\n";
449if ($optioncss != '') {
450 print '<input type="hidden" name="optioncss" value="'.$optioncss.'">';
451}
452print '<input type="hidden" name="token" value="'.newToken().'">';
453print '<input type="hidden" name="formfilteraction" id="formfilteraction" value="list">';
454print '<input type="hidden" name="action" value="list">';
455print '<input type="hidden" name="sortfield" value="'.$sortfield.'">';
456print '<input type="hidden" name="sortorder" value="'.$sortorder.'">';
457print '<input type="hidden" name="page" value="'.$page.'">';
458print '<input type="hidden" name="contextpage" value="'.$contextpage.'">';
459print '<input type="hidden" name="page_y" value="">';
460print '<input type="hidden" name="mode" value="'.$mode.'">';
461
462$newcardbutton = '';
463$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'));
464$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'));
465$newcardbutton .= dolGetButtonTitleSeparator();
466$newcardbutton .= dolGetButtonTitle($langs->trans('New'), '', 'fa fa-plus-circle', dol_buildpath('/workstation/workstation_card.php', 1).'?action=create&backtopage='.urlencode($_SERVER['PHP_SELF']), '', $permissiontoadd);
467
468print_barre_liste($title, $page, $_SERVER["PHP_SELF"], $param, $sortfield, $sortorder, $massactionbutton, $num, $nbtotalofrecords, 'object_'.$object->picto, 0, $newcardbutton, '', $limit, 0, 0, 1);
469
470// Add code for pre mass action (confirmation or email presend form)
471$topicmail = "SendWorkstationRef";
472$modelmail = "workstation";
473$objecttmp = new Workstation($db);
474$trackid = 'xxxx'.$object->id;
475include DOL_DOCUMENT_ROOT.'/core/tpl/massactions_pre.tpl.php';
476
477if ($search_all) {
478 $setupstring = '';
479 foreach ($fieldstosearchall as $key => $val) {
480 $fieldstosearchall[$key] = $langs->trans($val);
481 $setupstring .= $key."=".$val.";";
482 }
483 print '<!-- Search done like if WORKSTATION_QUICKSEARCH_ON_FIELDS = '.$setupstring.' -->'."\n";
484 print '<div class="divsearchfieldfilter">'.$langs->trans("FilterOnInto", $search_all).implode(', ', $fieldstosearchall).'</div>';
485}
486
487$moreforfilter = '';
488/*$moreforfilter.='<div class="divsearchfield">';
489$moreforfilter.= $langs->trans('MyFilter') . ': <input type="text" name="search_myfield" value="'.dol_escape_htmltag($search_myfield).'">';
490$moreforfilter.= '</div>';*/
491
492$parameters = array();
493$reshook = $hookmanager->executeHooks('printFieldPreListTitle', $parameters, $object, $action); // Note that $action and $object may have been modified by hook
494if (empty($reshook)) {
495 $moreforfilter .= $hookmanager->resPrint;
496} else {
497 $moreforfilter = $hookmanager->resPrint;
498}
499
500if (!empty($moreforfilter)) {
501 print '<div class="liste_titre liste_titre_bydiv centpercent">';
502 print $moreforfilter;
503 print '</div>';
504}
505
506$varpage = empty($contextpage) ? $_SERVER["PHP_SELF"] : $contextpage;
507$htmlofselectarray = $form->multiSelectArrayWithCheckbox('selectedfields', $arrayfields, $varpage, getDolGlobalString('MAIN_CHECKBOX_LEFT_COLUMN')); // This also change content of $arrayfields with user setup
508$selectedfields = ($mode != 'kanban' ? $htmlofselectarray : '');
509$selectedfields .= (count($arrayofmassactions) ? $form->showCheckAddButtons('checkforselect', 1) : '');
510
511print '<div class="div-table-responsive">'; // You can use div-table-responsive-no-min if you don't need reserved height for your table
512print '<table class="tagtable nobottomiftotal liste'.($moreforfilter ? " listwithfilterbefore" : "").'">'."\n";
513
514
515// Fields title search
516// --------------------------------------------------------------------
517
518print '<tr class="liste_titre_filter">';
519// Action column
520if (getDolGlobalString('MAIN_CHECKBOX_LEFT_COLUMN')) {
521 print '<td class="liste_titre center maxwidthsearch">';
522 $searchpicto = $form->showFilterButtons('left');
523 print $searchpicto;
524 print '</td>';
525}
526foreach ($object->fields as $key => $val) {
527 $searchkey = empty($search[$key]) ? '' : $search[$key];
528 $cssforfield = (empty($val['csslist']) ? (empty($val['css']) ? '' : $val['css']) : $val['csslist']);
529 if ($key == 'status') {
530 $cssforfield .= ($cssforfield ? ' ' : '').'center';
531 } elseif (in_array($val['type'], array('date', 'datetime', 'timestamp'))) {
532 $cssforfield .= ($cssforfield ? ' ' : '').'center';
533 } elseif (in_array($val['type'], array('timestamp'))) {
534 $cssforfield .= ($cssforfield ? ' ' : '').'nowrap';
535 } elseif (in_array($val['type'], array('double(24,8)', 'double(6,3)', 'integer', 'real', 'price')) && !in_array($key, array('id', 'rowid', 'ref', 'status')) && $val['label'] != 'TechnicalID' && empty($val['arrayofkeyval'])) {
536 $cssforfield .= ($cssforfield ? ' ' : '').'right';
537 }
538 if (!empty($arrayfields['t.'.$key]['checked'])) {
539 print '<td class="liste_titre'.($cssforfield ? ' '.$cssforfield : '').($key == 'status' ? ' parentonrightofpage' : '').'">';
540 if (!empty($val['arrayofkeyval']) && is_array($val['arrayofkeyval'])) {
541 print $form->selectarray('search_'.$key, $val['arrayofkeyval'], (isset($search[$key]) ? $search[$key] : ''), 1, 0, 0, '', 1, 0, 0, '', 'maxwidth100'.($key == 'status' ? ' search_status width100 onrightofpage' : ''), 1);
542 } elseif ((strpos($val['type'], 'integer:') === 0) || (strpos($val['type'], 'sellist:') === 0)) {
543 print $object->showInputField($val, $key, (isset($search[$key]) ? $search[$key] : ''), '', '', 'search_', $cssforfield.' maxwidth250', 1);
544 } elseif (preg_match('/^(date|timestamp|datetime)/', $val['type'])) {
545 print '<div class="nowrap">';
546 print $form->selectDate($search[$key.'_dtstart'] ? $search[$key.'_dtstart'] : '', "search_".$key."_dtstart", 0, 0, 1, '', 1, 0, 0, '', '', '', '', 1, '', $langs->trans('From'));
547 print '</div>';
548 print '<div class="nowrap">';
549 print $form->selectDate($search[$key.'_dtend'] ? $search[$key.'_dtend'] : '', "search_".$key."_dtend", 0, 0, 1, '', 1, 0, 0, '', '', '', '', 1, '', $langs->trans('to'));
550 print '</div>';
551 } elseif ($key == 'lang') {
552 require_once DOL_DOCUMENT_ROOT.'/core/class/html.formadmin.class.php';
553 $formadmin = new FormAdmin($db);
554 print $formadmin->select_language($search[$key], 'search_lang', 0, array(), 1, 0, 0, 'minwidth100imp maxwidth125', 2);
555 } else {
556 print '<input type="text" class="flat maxwidth'.($val['type'] == 'integer' ? '50' : '75').'" name="search_'.$key.'" value="'.dol_escape_htmltag(isset($search[$key]) ? $search[$key] : '').'">';
557 }
558 print '</td>';
559 }
560}
561
562// usergroups
563if (!empty($arrayfields['wug.fk_usergroup']['checked'])) {
564 print '<td class="liste_titre minwidth100">';
565 print $form->select_dolgroups($groups, 'groups', 1, '', 0, '', array(), (string) $conf->entity, true);
566 print '</td>';
567}
568
569// resources
570if (!empty($arrayfields['wr.fk_resource']['checked'])) {
571 print '<td class="liste_titre">';
572 print $formresource->select_resource_list($resources, 'resources', '', 0, 0, 0, array(), (string) $conf->entity, 1, 0, '', true);
573 print '</td>';
574}
575
576// Extra fields
577include DOL_DOCUMENT_ROOT.'/core/tpl/extrafields_list_search_input.tpl.php';
578
579// Fields from hook
580$parameters = array('arrayfields' => $arrayfields);
581$reshook = $hookmanager->executeHooks('printFieldListOption', $parameters, $object, $action); // Note that $action and $object may have been modified by hook
582print $hookmanager->resPrint;
583// Action column
584if (!getDolGlobalString('MAIN_CHECKBOX_LEFT_COLUMN')) {
585 print '<td class="liste_titre center maxwidthsearch">';
586 $searchpicto = $form->showFilterButtons();
587 print $searchpicto;
588 print '</td>';
589}
590print '</tr>'."\n";
591
592$totalarray = array();
593$totalarray['nbfield'] = 0;
594
595// Fields title label
596// --------------------------------------------------------------------
597print '<tr class="liste_titre">';
598// Action column
599if (getDolGlobalString('MAIN_CHECKBOX_LEFT_COLUMN')) {
600 print getTitleFieldOfList($selectedfields, 0, $_SERVER["PHP_SELF"], '', '', '', '', $sortfield, $sortorder, 'center maxwidthsearch ')."\n";
601 $totalarray['nbfield']++;
602}
603foreach ($object->fields as $key => $val) {
604 $cssforfield = (empty($val['csslist']) ? (empty($val['css']) ? '' : $val['css']) : $val['csslist']);
605 if ($key == 'status') {
606 $cssforfield .= ($cssforfield ? ' ' : '').'center';
607 } elseif (in_array($val['type'], array('date', 'datetime', 'timestamp'))) {
608 $cssforfield .= ($cssforfield ? ' ' : '').'center';
609 } elseif (in_array($val['type'], array('timestamp'))) {
610 $cssforfield .= ($cssforfield ? ' ' : '').'nowrap';
611 } elseif (in_array($val['type'], array('double(24,8)', 'double(6,3)', 'integer', 'real', 'price')) && !in_array($key, array('id', 'rowid', 'ref', 'status')) && $val['label'] != 'TechnicalID' && empty($val['arrayofkeyval'])) {
612 $cssforfield .= ($cssforfield ? ' ' : '').'right';
613 }
614 $cssforfield = preg_replace('/small\s*/', '', $cssforfield); // the 'small' css must not be used for the title label
615 if (!empty($arrayfields['t.'.$key]['checked'])) {
616 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";
617 $totalarray['nbfield']++;
618 }
619}
620
621// usergroups
622if (!empty($arrayfields['wug.fk_usergroup']['checked'])) {
623 // @phan-suppress-next-line PhanTypeInvalidDimOffset
624 print getTitleFieldOfList($arrayfields['wug.fk_usergroup']['label'], 0, $_SERVER['PHP_SELF'], '', '', $param, '', $sortfield, $sortorder, '') . "\n";
625}
626
627// resources
628if (!empty($arrayfields['wr.fk_resource']['checked'])) {
629 print getTitleFieldOfList($arrayfields['wr.fk_resource']['label'], 0, $_SERVER['PHP_SELF'], '', '', $param, '', $sortfield, $sortorder, '') . "\n";
630}
631
632// Extra fields
633include DOL_DOCUMENT_ROOT.'/core/tpl/extrafields_list_search_title.tpl.php';
634// Hook fields
635$parameters = array('arrayfields' => $arrayfields, 'param' => $param, 'sortfield' => $sortfield, 'sortorder' => $sortorder, 'totalarray' => &$totalarray);
636$reshook = $hookmanager->executeHooks('printFieldListTitle', $parameters, $object, $action); // Note that $action and $object may have been modified by hook
637print $hookmanager->resPrint;
638// Action column
639if (!getDolGlobalString('MAIN_CHECKBOX_LEFT_COLUMN')) {
640 print getTitleFieldOfList($selectedfields, 0, $_SERVER["PHP_SELF"], '', '', '', '', $sortfield, $sortorder, 'center maxwidthsearch ')."\n";
641 $totalarray['nbfield']++;
642}
643print '</tr>'."\n";
644
645
646// Detect if we need a fetch on each output line
647$needToFetchEachLine = 0;
648if (isset($extrafields->attributes[$object->table_element]['computed']) && is_array($extrafields->attributes[$object->table_element]['computed']) && count($extrafields->attributes[$object->table_element]['computed']) > 0) {
649 foreach ($extrafields->attributes[$object->table_element]['computed'] as $key => $val) {
650 if (!is_null($val) && preg_match('/\$object/', $val)) {
651 $needToFetchEachLine++; // There is at least one compute field that use $object
652 }
653 }
654}
655
656
657// Loop on record
658// --------------------------------------------------------------------
659$i = 0;
660$savnbfield = $totalarray['nbfield'];
661$totalarray = array();
662$totalarray['nbfield'] = 0;
663$imaxinloop = ($limit ? min($num, $limit) : $num);
664while ($i < $imaxinloop) {
665 $obj = $db->fetch_object($resql);
666 if (empty($obj)) {
667 break; // Should not happen
668 }
669
670 // Store properties in $object
671 $object->setVarsFromFetchObj($obj);
672
675
676 if ($mode == 'kanban') {
677 if ($i == 0) {
678 print '<tr class="trkanban"><td colspan="'.($savnbfield + 1).'">';
679 print '<div class="box-flex-container kanban">';
680 }
681 // Output Kanban
682 $selected = -1;
683 if ($massactionbutton || $massaction) { // If we are in select mode (massactionbutton defined) or if we have already selected and sent an action ($massaction) defined
684 $selected = 0;
685 if (in_array($object->id, $arrayofselected)) {
686 $selected = 1;
687 }
688 }
689 print $object->getKanbanView('', array('selected' => $selected));
690 if ($i == ($imaxinloop - 1)) {
691 print '</div>';
692 print '</td></tr>';
693 }
694 } else {
695 // Show line of result
696 $j = 0;
697 print '<tr data-rowid="'.$object->id.'" class="oddeven">';
698 // Action column
699 if (getDolGlobalString('MAIN_CHECKBOX_LEFT_COLUMN')) {
700 print '<td class="nowrap center">';
701 if ($massactionbutton || $massaction) { // If we are in select mode (massactionbutton defined) or if we have already selected and sent an action ($massaction) defined
702 $selected = 0;
703 if (in_array($object->id, $arrayofselected)) {
704 $selected = 1;
705 }
706 print '<input id="cb'.$object->id.'" class="flat checkforselect" type="checkbox" name="toselect[]" value="'.$object->id.'"'.($selected ? ' checked="checked"' : '').'>';
707 }
708 print '</td>';
709 if (!$i) {
710 $totalarray['nbfield']++;
711 }
712 }
713 foreach ($object->fields as $key => $val) {
714 $cssforfield = (empty($val['csslist']) ? (empty($val['css']) ? '' : $val['css']) : $val['csslist']);
715 if (in_array($val['type'], array('date', 'datetime', 'timestamp'))) {
716 $cssforfield .= ($cssforfield ? ' ' : '').'center';
717 } elseif ($key == 'status') {
718 $cssforfield .= ($cssforfield ? ' ' : '').'center';
719 }
720
721 if (in_array($val['type'], array('timestamp'))) {
722 $cssforfield .= ($cssforfield ? ' ' : '').'nowraponall';
723 } elseif ($key == 'ref') {
724 $cssforfield .= ($cssforfield ? ' ' : '').'nowraponall';
725 }
726
727 if (in_array($val['type'], array('double(24,8)', 'double(6,3)', 'integer', 'real', 'price')) && !in_array($key, array('id', 'rowid', 'ref', 'status')) && empty($val['arrayofkeyval'])) {
728 $cssforfield .= ($cssforfield ? ' ' : '').'right';
729 }
730 //if (in_array($key, array('fk_soc', 'fk_user', 'fk_warehouse'))) $cssforfield = 'tdoverflowmax100';
731
732 if (!empty($arrayfields['t.'.$key]['checked'])) {
733 print '<td'.($cssforfield ? ' class="'.$cssforfield.(preg_match('/tdoverflow/', $cssforfield) ? ' classfortooltip' : '').'"' : '');
734 if (preg_match('/tdoverflow/', $cssforfield) && !in_array($val['type'], array('ip', 'url')) && !is_numeric($object->$key)) {
735 print ' title="'.dol_escape_htmltag((string) $object->$key).'"';
736 }
737 print '>';
738 if ($key == 'status') {
739 print $object->getLibStatut(5);
740 } elseif ($key == 'rowid') {
741 print $object->showOutputField($val, $key, (string) $object->id, '');
742 } else {
743 print $object->showOutputField($val, $key, $object->$key, '');
744 }
745 print '</td>';
746 if (!$i) {
747 $totalarray['nbfield']++;
748 }
749 if (!empty($val['isameasure']) && $val['isameasure'] == 1) {
750 if (!$i) {
751 $totalarray['pos'][$totalarray['nbfield']] = 't.'.$key;
752 }
753 if (!isset($totalarray['val'])) {
754 $totalarray['val'] = array();
755 }
756 if (!isset($totalarray['val']['t.'.$key])) {
757 $totalarray['val']['t.'.$key] = 0;
758 }
759 $totalarray['val']['t.'.$key] += $object->$key;
760 }
761 }
762 }
763
764 if (!empty($arrayfields['wug.fk_usergroup']['checked'])) {
765 $toprint = array();
766 $cssforli = '';
767 if (count($object->usergroups) >= 4) {
768 $cssforli = 'tdoverflowmax60';
769 } elseif (count($object->usergroups) >= 2) {
770 $cssforli = 'tdoverflowmax80';
771 }
772 foreach ($object->usergroups as $id_group) {
773 $g = new UserGroup($db);
774 $g->fetch($id_group);
775 $toprint[] = '<li class="select2-search-choice-dolibarr noborderoncategories'.($cssforli ? ' '.$cssforli : '').'" style="background: #bbb">' . $g->getNomUrl(1, '', 0, 'categtextwhite') . '</li>';
776 }
777
778 print '<td class="minwidth300imp nowraponall">';
779 print '<div class="select2-container-multi-dolibarr"><ul class="select2-choices-dolibarr">' . implode(' ', $toprint) . '</ul></div>';
780 print '</td>';
781 }
782
783 if (!empty($arrayfields['wr.fk_resource']['checked'])) {
784 $toprint = array();
785 $cssforli = '';
786 if (count($object->resources) >= 4) {
787 $cssforli = 'tdoverflowmax60';
788 } elseif (count($object->resources) >= 2) {
789 $cssforli = 'tdoverflowmax80';
790 }
791 foreach ($object->resources as $id_resource) {
792 $r = new Dolresource($db);
793 $r->fetch($id_resource);
794 $toprint[] = '<li class="select2-search-choice-dolibarr noborderoncategories'.($cssforli ? ' '.$cssforli : '').'" style="background: #bbb">' . $r->getNomUrl(1, '', '', 0, 'categtextwhite') . '</li>';
795 }
796
797 print '<td class="minwidth300imp">';
798 print '<div class="select2-container-multi-dolibarr"><ul class="select2-choices-dolibarr">' . implode(' ', $toprint) . '</ul></div>';
799 print '</td>';
800 }
801
802 // Extra fields
803 include DOL_DOCUMENT_ROOT.'/core/tpl/extrafields_list_print_fields.tpl.php';
804
805 // Fields from hook
806 $parameters = array('arrayfields' => $arrayfields, 'object' => $object, 'obj' => $obj, 'i' => $i, 'totalarray' => &$totalarray);
807 $reshook = $hookmanager->executeHooks('printFieldListValue', $parameters, $object, $action); // Note that $action and $object may have been modified by hook
808 print $hookmanager->resPrint;
809
810 // Action column
811 if (!getDolGlobalString('MAIN_CHECKBOX_LEFT_COLUMN')) {
812 print '<td class="nowrap center">';
813 if ($massactionbutton || $massaction) { // If we are in select mode (massactionbutton defined) or if we have already selected and sent an action ($massaction) defined
814 $selected = 0;
815 if (in_array($object->id, $arrayofselected)) {
816 $selected = 1;
817 }
818 print '<input id="cb'.$object->id.'" class="flat checkforselect" type="checkbox" name="toselect[]" value="'.$object->id.'"'.($selected ? ' checked="checked"' : '').'>';
819 }
820 print '</td>';
821 if (!$i) {
822 $totalarray['nbfield']++;
823 }
824 }
825
826 print '</tr>'."\n";
827 }
828
829 $i++;
830}
831
832// Show total line
833include DOL_DOCUMENT_ROOT.'/core/tpl/list_print_total.tpl.php';
834
835// If no record found
836if ($num == 0) {
837 $colspan = 1;
838 foreach ($arrayfields as $key => $val) {
839 if (!empty($val['checked'])) {
840 $colspan++;
841 }
842 }
843 print '<tr><td colspan="'.$colspan.'"><span class="opacitymedium">'.$langs->trans("NoRecordFound").'</span></td></tr>';
844}
845
846
847$db->free($resql);
848
849$parameters = array('arrayfields' => $arrayfields, 'sql' => $sql);
850$reshook = $hookmanager->executeHooks('printFieldListFooter', $parameters, $object, $action); // Note that $action and $object may have been modified by hook
851print $hookmanager->resPrint;
852
853print '</table>'."\n";
854print '</div>'."\n";
855
856print '</form>'."\n";
857
858if (in_array('builddoc', array_keys($arrayofmassactions)) && ($nbtotalofrecords === '' || $nbtotalofrecords)) {
859 $hidegeneratedfilelistifempty = 1;
860 if ($massaction == 'builddoc' || $action == 'remove_file' || $show_files) {
861 $hidegeneratedfilelistifempty = 0;
862 }
863
864 require_once DOL_DOCUMENT_ROOT.'/core/class/html.formfile.class.php';
865 $formfile = new FormFile($db);
866
867 // Show list of available documents
868 $urlsource = $_SERVER['PHP_SELF'].'?sortfield='.$sortfield.'&sortorder='.$sortorder;
869 $urlsource .= str_replace('&amp;', '&', $param);
870
871 $filedir = $diroutputmassaction;
872 $genallowed = $permissiontoread;
873 $delallowed = $permissiontoadd;
874
875 print $formfile->showdocuments('massfilesarea_'.$object->module, '', $filedir, $urlsource, 0, $delallowed, '', 1, 1, 0, 48, 1, $param, $title, '', '', '', null, $hidegeneratedfilelistifempty);
876}
877
878// End of page
879llxFooter();
880$db->close();
$id
Support class for third parties, contacts, members, users or resources.
Definition account.php:48
if( $user->socid > 0) if(! $user->hasRight('accounting', 'chartofaccount')) $object
Definition card.php:67
$totalarray
Definition export.php:1206
llxFooter($comment='', $zone='private', $disabledoutputofmessages=0)
Empty footer.
Definition wrapper.php:91
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:73
DAO Resource object.
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.
Class to manage forms for the module resource.
Class to manage user groups.
Class for Workstation.
static getAllResourcesOfWorkstation($fk_workstation)
Function used to get an array with all resources linked to a workstation.
static getAllGroupsOfWorkstation($fk_workstation)
Function used to get an array with all usergroups linked to a workstation.
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
restrictedArea(User $user, $features, $object=0, $tableandshare='', $feature2='', $dbt_keyfield='fk_soc', $dbt_select='rowid', $isdraft=0, $mode=0)
Check permissions of a user to show a page and an object.