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