dolibarr  17.0.4
list.php
Go to the documentation of this file.
1 <?php
2 /* Copyright (C) 2001-2004 Rodolphe Quiedeville <rodolphe@quiedeville.org>
3  * Copyright (C) 2004-2016 Laurent Destailleur <eldy@users.sourceforge.net>
4  * Copyright (C) 2005-2014 Regis Houssin <regis.houssin@inodbox.com>
5  * Copyright (C) 2015 Juanjo Menent <jmenent@2byte.es>
6  * Copyright (C) 2020 Tobias Sekan <tobias.sekan@startmail.com>
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
29 require '../../main.inc.php';
30 require_once DOL_DOCUMENT_ROOT.'/product/stock/class/entrepot.class.php';
31 
32 if (isModEnabled('categorie')) {
33  require_once DOL_DOCUMENT_ROOT.'/core/class/html.formcategory.class.php';
34  require_once DOL_DOCUMENT_ROOT.'/categories/class/categorie.class.php';
35 }
36 
37 // Load translation files required by the page
38 $langs->loadLangs(array("stocks", "other"));
39 
40 $action = GETPOST('action', 'aZ09') ?GETPOST('action', 'aZ09') : 'view'; // The action 'add', 'create', 'edit', 'update', 'view', ...
41 $massaction = GETPOST('massaction', 'alpha'); // The bulk action (combo box choice into lists)
42 $show_files = GETPOST('show_files', 'int'); // Show files area generated by bulk actions ?
43 $confirm = GETPOST('confirm', 'alpha'); // Result of a confirmation
44 $cancel = GETPOST('cancel', 'alpha'); // We click on a Cancel button
45 $toselect = GETPOST('toselect', 'array'); // Array of ids of elements selected into a list
46 $contextpage = GETPOST('contextpage', 'aZ') ?GETPOST('contextpage', 'aZ') : 'stocklist'; // To manage different context of search
47 $backtopage = GETPOST('backtopage', 'alpha'); // Go back to a dedicated page
48 $optioncss = GETPOST('optioncss', 'aZ'); // Option for the css output (always '' except when 'print')
49 $toselect = GETPOST('toselect', 'array');
50 
51 
52 $search_all = trim((GETPOST('search_all', 'alphanohtml') != '') ?GETPOST('search_all', 'alphanohtml') : GETPOST('sall', 'alphanohtml'));
53 $search_ref = GETPOST("sref", "alpha") ?GETPOST("sref", "alpha") : GETPOST("search_ref", "alpha");
54 $search_label = GETPOST("snom", "alpha") ?GETPOST("snom", "alpha") : GETPOST("search_label", "alpha");
55 $search_status = GETPOST("search_status", "int");
56 
57 if (isModEnabled('categorie')) {
58  $search_category_list = GETPOST("search_category_".Categorie::TYPE_WAREHOUSE."_list", "array");
59 }
60 
61 // Load variable for pagination
62 $limit = GETPOST('limit', 'int') ?GETPOST('limit', 'int') : $conf->liste_limit;
63 $sortfield = GETPOST('sortfield', 'aZ09comma');
64 $sortorder = GETPOST('sortorder', 'aZ09comma');
65 $page = GETPOSTISSET('pageplusone') ? (GETPOST('pageplusone') - 1) : GETPOST("page", 'int');
66 if (empty($page) || $page == -1 || GETPOST('button_search', 'alpha') || GETPOST('button_removefilter', 'alpha') || (empty($toselect) && $massaction === '0')) {
67  $page = 0;
68 } // If $page is not defined, or '' or -1 or if we click on clear filters or if we select empty mass action
69 $offset = $limit * $page;
70 $pageprev = $page - 1;
71 $pagenext = $page + 1;
72 if (!$sortfield) {
73  $sortfield = "t.ref";
74 }
75 if (!$sortorder) {
76  $sortorder = "ASC";
77 }
78 
79 // Initialize technical object to manage hooks of page. Note that conf->hooks_modules contains array of hook context
80 $object = new Entrepot($db);
81 $extrafields = new ExtraFields($db);
82 $diroutputmassaction = $conf->stock->dir_output.'/temp/massgeneration/'.$user->id;
83 $hookmanager->initHooks(array('stocklist'));
84 
85 // Fetch optionals attributes and labels
86 $extrafields->fetch_name_optionals_label($object->table_element);
87 
88 $search_array_options = $extrafields->getOptionalsFromPost($object->table_element, '', 'search_');
89 
90 
91 // Initialize array of search criterias
92 $search_all = GETPOST("search_all", 'alpha');
93 $search = array();
94 foreach ($object->fields as $key => $val) {
95  $search_key = $key;
96  if ($search_key == 'statut') {
97  $search_key = 'status'; // remove this after refactor entrepot.class property statut to status
98  }
99  if (GETPOST('search_'.$search_key, 'alpha') !== '') {
100  $search[$search_key] = GETPOST('search_'.$search_key, 'alpha');
101  }
102 }
103 
104 // List of fields to search into when doing a "search in all"
105 $fieldstosearchall = array();
106 foreach ($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(
114  'stockqty'=>array('type'=>'float', 'label'=>'PhysicalStock', 'enabled'=>1, 'visible'=>-2, 'checked'=>0, 'position'=>170),
115  'estimatedvalue'=>array('type'=>'float', 'label'=>'EstimatedStockValue', 'enabled'=>1, 'visible'=>1, 'checked'=>1, 'position'=>171),
116  'estimatedstockvaluesell'=>array('type'=>'float', 'label'=>'EstimatedStockValueSell', 'enabled'=>1, 'checked'=>1, 'visible'=>2, 'position'=>172),
117 );
118 foreach ($object->fields as $key => $val) {
119  // If $val['visible']==0, then we never show the field
120  if (!empty($val['visible'])) {
121  $visible = (int) dol_eval($val['visible'], 1, 1, '1');
122  $arrayfields['t.'.$key] = array(
123  'label'=>$val['label'],
124  'checked'=>(($visible < 0) ? 0 : 1),
125  'enabled'=>($visible != 3 && dol_eval($val['enabled'], 1, 1, '1')),
126  'position'=>$val['position'],
127  'help'=> isset($val['help']) ? $val['help'] : 'help'
128  );
129  }
130 }
131 // Extra fields
132 include DOL_DOCUMENT_ROOT.'/core/tpl/extrafields_list_array_fields.tpl.php';
133 
134 $object->fields = dol_sort_array($object->fields, 'position');
135 $arrayfields = dol_sort_array($arrayfields, 'position');
136 
137 // Security check
138 $result = restrictedArea($user, 'stock');
139 
140 
141 /*
142  * Actions
143  */
144 
145 if (GETPOST('cancel', 'alpha')) {
146  $action = 'list'; $massaction = '';
147 }
148 if (!GETPOST('confirmmassaction', 'alpha') && $massaction != 'presend' && $massaction != 'confirm_presend') {
149  $massaction = '';
150 }
151 
152 $parameters = array();
153 $reshook = $hookmanager->executeHooks('doActions', $parameters, $object, $action); // Note that $action and $object may have been modified by some hooks
154 if ($reshook < 0) {
155  setEventMessages($hookmanager->error, $hookmanager->errors, 'errors');
156 }
157 
158 if (empty($reshook)) {
159  // Selection of new fields
160  include DOL_DOCUMENT_ROOT.'/core/actions_changeselectedfields.inc.php';
161 
162  // Purge search criteria
163  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
164  foreach ($object->fields as $key => $val) {
165  $search[$key] = '';
166  }
167  $toselect = array();
168  $search_array_options = array();
169  $search_category_list = array();
170  }
171  if (GETPOST('button_removefilter_x', 'alpha') || GETPOST('button_removefilter.x', 'alpha') || GETPOST('button_removefilter', 'alpha')
172  || GETPOST('button_search_x', 'alpha') || GETPOST('button_search.x', 'alpha') || GETPOST('button_search', 'alpha')) {
173  $massaction = ''; // Protection to avoid mass action if we force a new search during a mass action confirmation
174  }
175 
176  // Mass actions
177  $objectclass = 'Entrepot';
178  $objectlabel = 'Warehouse';
179  $permissiontoread = $user->rights->stock->lire;
180  $permissiontodelete = $user->rights->stock->supprimer;
181  $permissiontoadd = $user->rights->stock->creer;
182  $uploaddir = $conf->stock->dir_output;
183  include DOL_DOCUMENT_ROOT.'/core/actions_massactions.inc.php';
184 }
185 
186 
187 /*
188  * View
189  */
190 
191 $form = new Form($db);
192 $warehouse = new Entrepot($db);
193 
194 $now = dol_now();
195 
196 $help_url = 'EN:Module_Stocks_En|FR:Module_Stock|ES:M&oacute;dulo_Stocks';
197 $title = $langs->trans("Warehouses");
198 
199 $totalarray = array();
200 $totalarray['nbfield'] = 0;
201 
202 // Build and execute select
203 // --------------------------------------------------------------------
204 $sql = 'SELECT ';
205 foreach ($object->fields as $key => $val) {
206  $sql .= "t.".$key.", ";
207 }
208 // Add fields from extrafields
209 if (!empty($extrafields->attributes[$object->table_element]['label'])) {
210  foreach ($extrafields->attributes[$object->table_element]['label'] as $key => $val) {
211  $sql .= ($extrafields->attributes[$object->table_element]['type'][$key] != 'separate' ? "ef.".$key." as options_".$key.', ' : '');
212  }
213 }
214 
215 //For Multicompany PMP per entity
216 $separatedPMP = false;
217 if (!empty($conf->global->MULTICOMPANY_PRODUCT_SHARING_ENABLED) && !empty($conf->global->MULTICOMPANY_PMP_PER_ENTITY_ENABLED)) {
218  $separatedPMP = true;
219  $sql .= " SUM(pa.pmp * ps.reel) as estimatedvalue, SUM(p.price * ps.reel) as sellvalue, SUM(ps.reel) as stockqty";
220 } else {
221  $sql .= " SUM(p.pmp * ps.reel) as estimatedvalue, SUM(p.price * ps.reel) as sellvalue, SUM(ps.reel) as stockqty";
222 }
223 
224 // Add fields from hooks
225 $parameters = array();
226 $reshook = $hookmanager->executeHooks('printFieldListSelect', $parameters, $object); // Note that $action and $object may have been modified by hook
227 $sql .= $hookmanager->resPrint;
228 $sql = preg_replace('/,\s*$/', '', $sql);
229 $sql .= " FROM ".MAIN_DB_PREFIX.$object->table_element." as t";
230 if (!empty($extrafields->attributes[$object->table_element]['label']) && is_array($extrafields->attributes[$object->table_element]['label']) && count($extrafields->attributes[$object->table_element]['label'])) {
231  $sql .= " LEFT JOIN ".MAIN_DB_PREFIX.$object->table_element."_extrafields as ef on (t.rowid = ef.fk_object)";
232 }
233 $sql .= " LEFT JOIN ".MAIN_DB_PREFIX."product_stock as ps ON t.rowid = ps.fk_entrepot";
234 $sql .= " LEFT JOIN ".MAIN_DB_PREFIX."product as p ON ps.fk_product = p.rowid";
235 $sql .= " LEFT JOIN ".MAIN_DB_PREFIX."c_departements as c_dep ON c_dep.rowid = t.fk_departement";
236 $sql .= " LEFT JOIN ".MAIN_DB_PREFIX."c_country as ccount ON ccount.rowid = t.fk_pays";
237 if ($separatedPMP) {
238  $sql .= " LEFT JOIN ".MAIN_DB_PREFIX."product_perentity as pa ON pa.fk_product = p.rowid AND pa.fk_product = ps.fk_product AND pa.entity = ". (int) $conf->entity;
239 }
240 $sql .= " WHERE t.entity IN (".getEntity('stock').")";
241 foreach ($search as $key => $val) {
242  $class_key = $key;
243  if ($class_key == 'status') {
244  $class_key = 'statut'; // remove this after refactoring entrepot.class property statut to status
245  }
246  if (($key == 'status' && $search[$key] == -1) || $key == 'entity') {
247  continue;
248  }
249  $mode_search = (($object->isInt($object->fields[$key]) || $object->isFloat($object->fields[$key])) ? 1 : 0);
250  if (strpos($object->fields[$key]['type'], 'integer:') === 0) {
251  if ($search[$key] == '-1') {
252  $search[$key] = '';
253  }
254  $mode_search = 2;
255  }
256  if ($search[$key] != '') {
257  $sql .= natural_search((($key == "ref") ? "t.ref" : "t.".$class_key), $search[$key], (($key == 'status') ? 2 : $mode_search));
258  }
259 }
260 if ($search_all) {
261  $sql .= natural_search(array_keys($fieldstosearchall), $search_all);
262 }
263 // Search for tag/category ($searchCategoryWarehouseList is an array of ID)
264 $searchCategoryWarehouseList = $search_category_list;
265 $searchCategoryWarehouseOperator = 0;
266 if (!empty($searchCategoryWarehouseList)) {
267  $searchCategoryWarehouseSqlList = array();
268  $listofcategoryid = '';
269  foreach ($searchCategoryWarehouseList as $searchCategoryWarehouse) {
270  if (intval($searchCategoryWarehouse) == -2) {
271  $searchCategoryWarehouseSqlList[] = "NOT EXISTS (SELECT ck.fk_warehouse FROM ".MAIN_DB_PREFIX."categorie_warehouse as ck WHERE t.rowid = ck.fk_warehouse)";
272  } elseif (intval($searchCategoryWarehouse) > 0) {
273  if ($searchCategoryWarehouseOperator == 0) {
274  $searchCategoryWarehouseSqlList[] = " EXISTS (SELECT ck.fk_warehouse FROM ".MAIN_DB_PREFIX."categorie_warehouse as ck WHERE t.rowid = ck.fk_warehouse AND ck.fk_categorie = ".((int) $searchCategoryWarehouse).")";
275  } else {
276  $listofcategoryid .= ($listofcategoryid ? ', ' : '') .((int) $searchCategoryWarehouse);
277  }
278  }
279  }
280  if ($listofcategoryid) {
281  $searchCategoryWarehouseSqlList[] = " EXISTS (SELECT ck.fk_warehouse FROM ".MAIN_DB_PREFIX."categorie_warehouse as ck WHERE t.rowid = ck.fk_warehouse AND ck.fk_categorie IN (".$db->sanitize($listofcategoryid)."))";
282  }
283  if ($searchCategoryWarehouseOperator == 1) {
284  if (!empty($searchCategoryWarehouseSqlList)) {
285  $sql .= " AND (".implode(' OR ', $searchCategoryWarehouseSqlList).")";
286  }
287  } else {
288  if (!empty($searchCategoryWarehouseSqlList)) {
289  $sql .= " AND (".implode(' AND ', $searchCategoryWarehouseSqlList).")";
290  }
291  }
292 }
293 
294 // Add where from extra fields
295 include DOL_DOCUMENT_ROOT.'/core/tpl/extrafields_list_search_sql.tpl.php';
296 // Add where from hooks
297 $parameters = array();
298 $reshook = $hookmanager->executeHooks('printFieldListWhere', $parameters, $object); // Note that $action and $object may have been modified by hook
299 $sql .= $hookmanager->resPrint;
300 $sql .= " GROUP BY ";
301 foreach ($object->fields as $key => $val) {
302  $sql .= "t.".$key.", ";
303 }
304 // Add fields from extrafields
305 if (!empty($extrafields->attributes[$object->table_element]['label'])) {
306  foreach ($extrafields->attributes[$object->table_element]['label'] as $key => $val) {
307  $sql .= ($extrafields->attributes[$object->table_element]['type'][$key] != 'separate' ? "ef.".$key.', ' : '');
308  }
309 }
310 // Add where from hooks
311 $parameters = array();
312 $reshook = $hookmanager->executeHooks('printFieldListGroupBy', $parameters); // Note that $action and $object may have been modified by hook
313 $sql .= $hookmanager->resPrint;
314 $sql = preg_replace('/,\s*$/', '', $sql);
315 $totalnboflines = 0;
316 
317 $result = $db->query($sql);
318 if ($result) {
319  $totalnboflines = $db->num_rows($result);
320  // fetch totals
321  $line = $total = $totalsell = $totalStock = 0;
322  while ($line < $totalnboflines) {
323  $objp = $db->fetch_object($result);
324  $total += $objp->estimatedvalue;
325  $totalsell += $objp->sellvalue;
326  $totalStock += $objp->stockqty;
327  $line++;
328  }
329  $totalarray['val']['stockqty'] = price2num($totalStock, 'MS');
330  $totalarray['val']['estimatedvalue'] = price2num($total, 'MT');
331  $totalarray['val']['estimatedstockvaluesell'] = price2num($totalsell, 'MT');
332 }
333 $sql .= $db->order($sortfield, $sortorder);
334 
335 // Count total nb of records
336 $nbtotalofrecords = '';
337 if (empty($conf->global->MAIN_DISABLE_FULL_SCANLIST)) {
338  $resql = $db->query($sql);
339  $nbtotalofrecords = $db->num_rows($resql);
340  if (($page * $limit) > $nbtotalofrecords) { // if total of record found is smaller than page * limit, goto and load page 0
341  $page = 0;
342  $offset = 0;
343  }
344 }
345 // if total of record found is smaller than limit, no need to do paging and to restart another select with limits set.
346 if (is_numeric($nbtotalofrecords) && ($limit > $nbtotalofrecords || empty($limit))) {
347  $num = $nbtotalofrecords;
348 } else {
349  if ($limit) {
350  $sql .= $db->plimit($limit + 1, $offset);
351  }
352 
353  $resql = $db->query($sql);
354  if (!$resql) {
355  dol_print_error($db);
356  exit;
357  }
358 
359  $num = $db->num_rows($resql);
360 }
361 
362 // Direct jump if only one record found
363 if ($num == 1 && !empty($conf->global->MAIN_SEARCH_DIRECT_OPEN_IF_ONLY_ONE) && $search_all && !$page) {
364  $obj = $db->fetch_object($resql);
365  $id = $obj->rowid;
366  header("Location: ".DOL_URL_ROOT.'/product/stock/card.php?id='.$id);
367  exit;
368 }
369 
370 
371 // Output page
372 // --------------------------------------------------------------------
373 
374 llxHeader('', $title, $help_url);
375 
376 $arrayofselected = is_array($toselect) ? $toselect : array();
377 
378 $param = '';
379 if (!empty($contextpage) && $contextpage != $_SERVER["PHP_SELF"]) {
380  $param .= '&contextpage='.urlencode($contextpage);
381 }
382 if ($limit > 0 && $limit != $conf->liste_limit) {
383  $param .= '&limit='.urlencode($limit);
384 }
385 foreach ($search as $key => $val) {
386  if (is_array($search[$key]) && count($search[$key])) {
387  foreach ($search[$key] as $skey) {
388  $param .= '&search_'.$key.'[]='.urlencode($skey);
389  }
390  } else {
391  $param .= '&search_'.$key.'='.urlencode($search[$key]);
392  }
393 }
394 if ($optioncss != '') {
395  $param .= '&optioncss='.urlencode($optioncss);
396 }
397 // Add $param from extra fields
398 include DOL_DOCUMENT_ROOT.'/core/tpl/extrafields_list_search_param.tpl.php';
399 
400 // List of mass actions available
401 $arrayofmassactions = array(
402  //'presend'=>img_picto('', 'email', 'class="pictofixedwidth"').$langs->trans("SendByMail"),
403  //'builddoc'=>img_picto('', 'pdf', 'class="pictofixedwidth"').$langs->trans("PDFMerge"),
404 );
405 //if ($user->rights->stock->supprimer) $arrayofmassactions['predelete']=img_picto('', 'delete', 'class="pictofixedwidth"').$langs->trans("Delete");
406 if (GETPOST('nomassaction', 'int') || in_array($massaction, array('presend', 'predelete','preaffecttag'))) {
407  $arrayofmassactions = array();
408 }
409 if (isModEnabled('category') && $user->rights->stock->creer) {
410  $arrayofmassactions['preaffecttag'] = img_picto('', 'label', 'class="pictofixedwidth"').$langs->trans("AffectTag");
411 }
412 $massactionbutton = $form->selectMassAction('', $arrayofmassactions);
413 
414 print '<form action="'.$_SERVER["PHP_SELF"].'" id="searchFormList" method="POST" name="formulaire">';
415 if ($optioncss != '') {
416  print '<input type="hidden" name="optioncss" value="'.$optioncss.'">';
417 }
418 print '<input type="hidden" name="token" value="'.newToken().'">';
419 print '<input type="hidden" name="formfilteraction" id="formfilteraction" value="list">';
420 print '<input type="hidden" name="action" value="list">';
421 print '<input type="hidden" name="sortfield" value="'.$sortfield.'">';
422 print '<input type="hidden" name="sortorder" value="'.$sortorder.'">';
423 print '<input type="hidden" name="contextpage" value="'.$contextpage.'">';
424 
425 $newcardbutton = dolGetButtonTitle($langs->trans('MenuNewWarehouse'), '', 'fa fa-plus-circle', DOL_URL_ROOT.'/product/stock/card.php?action=create&backtopage='.urlencode($_SERVER['PHP_SELF']), '', $user->rights->stock->creer);
426 
427 print_barre_liste($title, $page, $_SERVER["PHP_SELF"], $param, $sortfield, $sortorder, $massactionbutton, $num, $nbtotalofrecords, 'stock', 0, $newcardbutton, '', $limit, 0, 0, 1);
428 
429 // Add code for pre mass action (confirmation or email presend form)
430 $topicmail = "Information";
431 $modelmail = "warehouse";
432 $objecttmp = new Entrepot($db);
433 $trackid = 'ware'.$object->id;
434 include DOL_DOCUMENT_ROOT.'/core/tpl/massactions_pre.tpl.php';
435 
436 
437 if ($search_all) {
438  foreach ($fieldstosearchall as $key => $val) {
439  $fieldstosearchall[$key] = $langs->trans($val);
440  }
441  print '<div class="divsearchfieldfilter">'.$langs->trans("FilterOnInto", $sall).join(', ', $fieldstosearchall).'</div>';
442 }
443 
444 $moreforfilter = '';
445 
446 if (isModEnabled('categorie') && $user->rights->categorie->lire) {
447  $formcategory = new FormCategory($db);
448  $moreforfilter .= $formcategory->getFilterBox(Categorie::TYPE_WAREHOUSE, $search_category_list);
449 }
450 
451 /*$moreforfilter.='<div class="divsearchfield">';
452  $moreforfilter.= $langs->trans('MyFilter') . ': <input type="text" name="search_myfield" value="'.dol_escape_htmltag($search_myfield).'">';
453  $moreforfilter.= '</div>';*/
454 
455 $parameters = array();
456 $reshook = $hookmanager->executeHooks('printFieldPreListTitle', $parameters, $object); // Note that $action and $object may have been modified by hook
457 if (empty($reshook)) {
458  $moreforfilter .= $hookmanager->resPrint;
459 } else {
460  $moreforfilter = $hookmanager->resPrint;
461 }
462 
463 if (!empty($moreforfilter)) {
464  print '<div class="liste_titre liste_titre_bydiv centpercent">';
465  print $moreforfilter;
466  print '</div>';
467 }
468 
469 $varpage = empty($contextpage) ? $_SERVER["PHP_SELF"] : $contextpage;
470 $selectedfields = $form->multiSelectArrayWithCheckbox('selectedfields', $arrayfields, $varpage, getDolGlobalString('MAIN_CHECKBOX_LEFT_COLUMN', '')); // This also change content of $arrayfields
471 $selectedfields .= (count($arrayofmassactions) ? $form->showCheckAddButtons('checkforselect', 1) : '');
472 
473 print '<div class="div-table-responsive">';
474 print '<table class="tagtable nobottomiftotal liste'.($moreforfilter ? " listwithfilterbefore" : "").'">'."\n";
475 
476 // Fields title search
477 // --------------------------------------------------------------------
478 print '<tr class="liste_titre_filter">';
479 // Action column
480 if (!empty($conf->global->MAIN_CHECKBOX_LEFT_COLUMN)) {
481  print '<td class="liste_titre maxwidthsearch">';
482  $searchpicto = $form->showFilterButtons('left');
483  print $searchpicto;
484  print '</td>';
485 }
486 foreach ($object->fields as $key => $val) {
487  if ($key == 'statut') {
488  continue;
489  }
490  $cssforfield = (empty($val['csslist']) ? (empty($val['css']) ? '' : $val['css']) : $val['csslist']);
491  if ($key == 'status') {
492  $cssforfield .= ($cssforfield ? ' ' : '').'center';
493  } elseif (in_array($val['type'], array('date', 'datetime', 'timestamp'))) {
494  $cssforfield .= ($cssforfield ? ' ' : '').'center';
495  } elseif (in_array($val['type'], array('timestamp'))) {
496  $cssforfield .= ($cssforfield ? ' ' : '').'nowrap';
497  } elseif (in_array($val['type'], array('double(24,8)', 'double(6,3)', 'integer', 'real', 'price')) && $val['label'] != 'TechnicalID' && empty($val['arrayofkeyval'])) {
498  $cssforfield .= ($cssforfield ? ' ' : '').'right';
499  }
500  if (!empty($arrayfields['t.'.$key]['checked'])) {
501  print '<td class="liste_titre'.($cssforfield ? ' '.$cssforfield : '').'">';
502  if (!empty($val['arrayofkeyval']) && is_array($val['arrayofkeyval'])) {
503  print $form->selectarray('search_'.$key, $val['arrayofkeyval'], $search[$key], $val['notnull'], 0, 0, '', 1, 0, 0, '', 'maxwidth100', 1);
504  } elseif ((strpos($val['type'], 'integer:') === 0) || (strpos($val['type'], 'sellist:') === 0)) {
505  print $object->showInputField($val, $key, $search[$key], '', '', 'search_', 'maxwidth125', 1);
506  } elseif (!preg_match('/^(date|timestamp)/', $val['type'])) {
507  print '<input type="text" class="flat maxwidth75" name="search_'.$key.'" value="'.dol_escape_htmltag(!empty($search[$key])?$search[$key]:'').'">';
508  }
509  print '</td>';
510  }
511 }
512 
513 if (!empty($arrayfields["stockqty"]['checked'])) {
514  print '<td class="liste_titre"></td>';
515 }
516 
517 if (!empty($arrayfields["estimatedvalue"]['checked'])) {
518  print '<td class="liste_titre"></td>';
519 }
520 
521 if (!empty($arrayfields["estimatedstockvaluesell"]['checked'])) {
522  print '<td class="liste_titre"></td>';
523 }
524 
525 // Extra fields
526 include DOL_DOCUMENT_ROOT.'/core/tpl/extrafields_list_search_input.tpl.php';
527 
528 // Fields from hook
529 $parameters = array('arrayfields'=>$arrayfields);
530 $reshook = $hookmanager->executeHooks('printFieldListOption', $parameters, $object); // Note that $action and $object may have been modified by hook
531 print $hookmanager->resPrint;
532 
533 // Status
534 if (!empty($arrayfields['t.statut']['checked'])) {
535  print '<td class="liste_titre center">';
536  print $form->selectarray('search_status', $warehouse->statuts, $search_status, 1, 0, 0, '', 1, 0, 0, '', 'onrightofpage');
537  print '</td>';
538 }
539 
540 // Action column
541 if (empty($conf->global->MAIN_CHECKBOX_LEFT_COLUMN)) {
542  print '<td class="liste_titre maxwidthsearch">';
543  $searchpicto = $form->showFilterButtons();
544  print $searchpicto;
545  print '</td>';
546 }
547 print '</tr>'."\n";
548 
549 // Fields title label
550 // --------------------------------------------------------------------
551 print '<tr class="liste_titre">';
552 
553 // Action column
554 if (!empty($conf->global->MAIN_CHECKBOX_LEFT_COLUMN)) {
555  print getTitleFieldOfList($selectedfields, 0, $_SERVER["PHP_SELF"], '', '', '', '', $sortfield, $sortorder, 'center maxwidthsearch ')."\n";
556 }
557 foreach ($object->fields as $key => $val) {
558  if ($key == 'statut') {
559  continue;
560  }
561  $cssforfield = (empty($val['csslist']) ? (empty($val['css']) ? '' : $val['css']) : $val['csslist']);
562  if ($key == 'status') {
563  $cssforfield .= ($cssforfield ? ' ' : '').'center';
564  } elseif (in_array($val['type'], array('date', 'datetime', 'timestamp'))) {
565  $cssforfield .= ($cssforfield ? ' ' : '').'center';
566  } elseif (in_array($val['type'], array('timestamp'))) {
567  $cssforfield .= ($cssforfield ? ' ' : '').'nowrap';
568  } elseif (in_array($val['type'], array('double(24,8)', 'double(6,3)', 'integer', 'real', 'price')) && $val['label'] != 'TechnicalID' && empty($val['arrayofkeyval'])) {
569  $cssforfield .= ($cssforfield ? ' ' : '').'right';
570  }
571  if (!empty($arrayfields['t.'.$key]['checked'])) {
572  print getTitleFieldOfList($arrayfields['t.'.$key]['label'], 0, $_SERVER['PHP_SELF'], 't.'.$key, '', $param, ($cssforfield ? 'class="'.$cssforfield.'"' : ''), $sortfield, $sortorder, ($cssforfield ? $cssforfield.' ' : ''))."\n";
573  }
574 }
575 
576 if (!empty($arrayfields["stockqty"]['checked'])) {
577  print_liste_field_titre("PhysicalStock", $_SERVER["PHP_SELF"], "stockqty", '', $param, '', $sortfield, $sortorder, 'right ');
578 }
579 
580 if (!empty($arrayfields["estimatedvalue"]['checked'])) {
581  print_liste_field_titre("EstimatedStockValue", $_SERVER["PHP_SELF"], "estimatedvalue", '', $param, '', $sortfield, $sortorder, 'right ');
582 }
583 
584 if (!empty($arrayfields["estimatedstockvaluesell"]['checked'])) {
585  print_liste_field_titre("EstimatedStockValueSell", $_SERVER["PHP_SELF"], "", '', $param, '', $sortfield, $sortorder, 'right ');
586 }
587 
588 // Extra fields
589 include DOL_DOCUMENT_ROOT.'/core/tpl/extrafields_list_search_title.tpl.php';
590 
591 // Hook fields
592 $parameters = array('arrayfields'=>$arrayfields, 'param'=>$param, 'sortfield'=>$sortfield, 'sortorder'=>$sortorder);
593 $reshook = $hookmanager->executeHooks('printFieldListTitle', $parameters, $object); // Note that $action and $object may have been modified by hook
594 print $hookmanager->resPrint;
595 
596 if (!empty($arrayfields['t.statut']['checked'])) {
597  print_liste_field_titre($arrayfields['t.statut']['label'], $_SERVER["PHP_SELF"], "t.statut", '', $param, '', $sortfield, $sortorder, 'center ');
598 }
599 
600 // Action column
601 if (empty($conf->global->MAIN_CHECKBOX_LEFT_COLUMN)) {
602  print getTitleFieldOfList($selectedfields, 0, $_SERVER["PHP_SELF"], '', '', '', '', $sortfield, $sortorder, 'center maxwidthsearch ')."\n";
603 }
604 print '</tr>'."\n";
605 
606 // Loop on record
607 // --------------------------------------------------------------------
608 $i = 0;
609 
610 $warehouse = new Entrepot($db);
611 
612 while ($i < min($num, $limit)) {
613  $obj = $db->fetch_object($resql);
614  if (empty($obj)) {
615  break; // Should not happen
616  }
617 
618  // Store properties in $object
619  $warehouse->setVarsFromFetchObj($obj);
620 
621  $warehouse->label = $warehouse->ref;
622 
623  // Show here line of result
624  print '<tr class="oddeven">';
625 
626  // Action column
627  if (!empty($conf->global->MAIN_CHECKBOX_LEFT_COLUMN)) {
628  print '<td class="nowrap center">';
629  if ($massactionbutton || $massaction) { // If we are in select mode (massactionbutton defined) or if we have already selected and sent an action ($massaction) defined
630  $selected = 0;
631  if (in_array($obj->rowid, $arrayofselected)) {
632  $selected = 1;
633  }
634  print '<input id="cb'.$obj->rowid.'" class="flat checkforselect" type="checkbox" name="toselect[]" value="'.$obj->rowid.'"'.($selected ? ' checked="checked"' : '').'>';
635  }
636  print '</td>';
637  }
638  foreach ($warehouse->fields as $key => $val) {
639  if ($key == 'statut') {
640  continue;
641  }
642  $cssforfield = (empty($val['csslist']) ? (empty($val['css']) ? '' : $val['css']) : $val['csslist']);
643  if (in_array($val['type'], array('date', 'datetime', 'timestamp'))) {
644  $cssforfield .= ($cssforfield ? ' ' : '').'center';
645  } elseif ($key == 'status') {
646  $cssforfield .= ($cssforfield ? ' ' : '').'center';
647  }
648 
649  if (in_array($val['type'], array('timestamp'))) {
650  $cssforfield .= ($cssforfield ? ' ' : '').'nowrap';
651  } elseif ($key == 'ref') {
652  $cssforfield .= ($cssforfield ? ' ' : '').'nowrap';
653  }
654 
655  if (in_array($val['type'], array('double(24,8)', 'double(6,3)', 'integer', 'real', 'price')) && $key != 'status' && empty($val['arrayofkeyval'])) {
656  $cssforfield .= ($cssforfield ? ' ' : '').'right';
657  }
658  if (in_array($key, array('fk_soc', 'fk_user', 'fk_warehouse'))) {
659  $cssforfield = 'tdoverflowmax100';
660  }
661 
662  if (!empty($arrayfields['t.'.$key]['checked'])) {
663  print '<td'.($cssforfield ? ' class="'.$cssforfield.'"' : '').'>';
664  if ($key == 'statut') {
665  print $warehouse->getLibStatut(5);
666  }
667  if ($key == 'phone') {
668  print dol_print_phone($obj->phone, '', 0, $obj->rowid, 'AC_TEL');
669  } elseif ($key == 'fax') {
670  print dol_print_phone($obj->fax, '', 0, $obj->rowid, 'AC_FAX');
671  } else {
672  print $warehouse->showOutputField($val, $key, $warehouse->$key, '');
673  }
674  print '</td>';
675  if (!$i) {
676  $totalarray['nbfield']++;
677  }
678  if (!empty($val['isameasure']) && $val['isameasure'] == 1) {
679  if (!$i) {
680  $totalarray['pos'][$totalarray['nbfield']] = 't.'.$key;
681  }
682  if (!isset($totalarray['val'])) {
683  $totalarray['val'] = array();
684  }
685  if (!isset($totalarray['val']['t.'.$key])) {
686  $totalarray['val']['t.'.$key] = 0;
687  }
688  $totalarray['val']['t.'.$key] += $warehouse->$key;
689  }
690  }
691  }
692 
693  // Stock qty
694  if (!empty($arrayfields["stockqty"]['checked'])) {
695  print '<td class="right">'.price2num($obj->stockqty, 5).'</td>';
696  if (!$i) {
697  $totalarray['nbfield']++;
698  }
699  if (!$i) {
700  $totalarray['pos'][$totalarray['nbfield']] = 'stockqty';
701  }
702  }
703 
704  // PMP value
705  if (!empty($arrayfields["estimatedvalue"]['checked'])) {
706  print '<td class="right">';
707  if (price2num($obj->estimatedvalue, 'MT')) {
708  print '<span class="amount">'.price(price2num($obj->estimatedvalue, 'MT'), 1).'</span>';
709  } else {
710  print '';
711  }
712  print '</td>';
713  if (!$i) {
714  $totalarray['nbfield']++;
715  }
716  if (!$i) {
717  $totalarray['pos'][$totalarray['nbfield']] = 'estimatedvalue';
718  }
719  }
720 
721  // Selling value
722  if (!empty($arrayfields["estimatedstockvaluesell"]['checked'])) {
723  print '<td class="right">';
724  if (empty($conf->global->PRODUIT_MULTIPRICES)) {
725  if ($obj->sellvalue) {
726  print '<span class="amount">'.price(price2num($obj->sellvalue, 'MT'), 1).'</span>';
727  }
728  } else {
729  $htmltext = $langs->trans("OptionMULTIPRICESIsOn");
730  print $form->textwithtooltip('<span class="opacitymedium">'.$langs->trans("Variable").'</span>', $htmltext);
731  }
732  print '</td>';
733  if (!$i) {
734  $totalarray['nbfield']++;
735  }
736  if (!$i) {
737  $totalarray['pos'][$totalarray['nbfield']] = 'estimatedstockvaluesell';
738  }
739  }
740 
741  // Extra fields
742  include DOL_DOCUMENT_ROOT.'/core/tpl/extrafields_list_print_fields.tpl.php';
743  // Fields from hook
744  $parameters = array('arrayfields'=>$arrayfields, 'object'=>$object, 'obj'=>$obj, 'i'=>$i, 'totalarray'=>&$totalarray);
745  $reshook = $hookmanager->executeHooks('printFieldListValue', $parameters, $object); // Note that $action and $object may have been modified by hook
746  print $hookmanager->resPrint;
747 
748  // Status
749  if (!empty($arrayfields['t.statut']['checked'])) {
750  print '<td class="center">'.$warehouse->LibStatut($obj->statut, 5).'</td>';
751  if (!$i) {
752  $totalarray['nbfield']++;
753  }
754  }
755 
756  // Action column
757  if (empty($conf->global->MAIN_CHECKBOX_LEFT_COLUMN)) {
758  print '<td class="nowrap center">';
759  if ($massactionbutton || $massaction) { // If we are in select mode (massactionbutton defined) or if we have already selected and sent an action ($massaction) defined
760  $selected = 0;
761  if (in_array($obj->rowid, $arrayofselected)) {
762  $selected = 1;
763  }
764  print '<input id="cb'.$obj->rowid.'" class="flat checkforselect" type="checkbox" name="toselect[]" value="'.$obj->rowid.'"'.($selected ? ' checked="checked"' : '').'>';
765  }
766  print '</td>';
767  }
768  if (!$i) {
769  $totalarray['nbfield']++;
770  }
771 
772  print '</tr>'."\n";
773 
774 
775  $i++;
776 }
777 
778 if ($totalnboflines - $offset <= $limit) {
779  // Show total line
780  include DOL_DOCUMENT_ROOT.'/core/tpl/list_print_total.tpl.php';
781 }
782 
783 // If no record found
784 if ($num == 0) {
785  $colspan = 1;
786  foreach ($arrayfields as $key => $val) {
787  if (!empty($val['checked'])) {
788  $colspan++;
789  }
790  }
791  print '<tr><td colspan="'.$colspan.'" class="opacitymedium">'.$langs->trans("NoRecordFound").'</td></tr>';
792 }
793 
794 $db->free($resql);
795 
796 $parameters = array('arrayfields'=>$arrayfields, 'sql'=>$sql);
797 $reshook = $hookmanager->executeHooks('printFieldListFooter', $parameters, $object); // Note that $action and $object may have been modified by hook
798 print $hookmanager->resPrint;
799 
800 print '</table>'."\n";
801 print '</div>'."\n";
802 
803 print '</form>'."\n";
804 
805 if (in_array('builddoc', $arrayofmassactions) && ($nbtotalofrecords === '' || $nbtotalofrecords)) {
806  $hidegeneratedfilelistifempty = 1;
807  if ($massaction == 'builddoc' || $action == 'remove_file' || $show_files) {
808  $hidegeneratedfilelistifempty = 0;
809  }
810 
811  require_once DOL_DOCUMENT_ROOT.'/core/class/html.formfile.class.php';
812  $formfile = new FormFile($db);
813 
814  // Show list of available documents
815  $urlsource = $_SERVER['PHP_SELF'].'?sortfield='.$sortfield.'&sortorder='.$sortorder;
816  $urlsource .= str_replace('&amp;', '&', $param);
817 
818  $filedir = $diroutputmassaction;
819  $genallowed = $user->rights->stock->lire;
820  $delallowed = $user->rights->stock->creer;
821 
822  print $formfile->showdocuments('massfilesarea_stock', '', $filedir, $urlsource, 0, $delallowed, '', 1, 1, 0, 48, 1, $param, $title, '', '', '', null, $hidegeneratedfilelistifempty);
823 }
824 
825 // End of page
826 llxFooter();
827 $db->close();
if(GETPOST('button_removefilter_x', 'alpha')||GETPOST('button_removefilter.x', 'alpha')||GETPOST('button_removefilter', 'alpha')) if(GETPOST('button_search_x', 'alpha')||GETPOST('button_search.x', 'alpha')||GETPOST('button_search', 'alpha')) if($action=="save" &&empty($cancel)) $help_url
View.
Definition: agenda.php:118
if(!defined('NOREQUIRESOC')) if(!defined('NOREQUIRETRAN')) if(!defined('NOTOKENRENEWAL')) if(!defined('NOREQUIREMENU')) if(!defined('NOREQUIREHTML')) if(!defined('NOREQUIREAJAX')) llxHeader()
Empty header.
Definition: wrapper.php:56
llxFooter()
Empty footer.
Definition: wrapper.php:70
Class to manage warehouses.
Class to manage standard extra fields.
Class to manage forms for categories.
Class to offer components to list and upload files.
Class to manage generation of HTML components Only common components must be here.
if(isModEnabled('facture') &&!empty($user->rights->facture->lire)) if((isModEnabled('fournisseur') &&empty($conf->global->MAIN_USE_NEW_SUPPLIERMOD) && $user->hasRight("fournisseur", "facture", "lire"))||(isModEnabled('supplier_invoice') && $user->hasRight("supplier_invoice", "lire"))) if(isModEnabled('don') &&!empty($user->rights->don->lire)) if(isModEnabled('tax') &&!empty($user->rights->tax->charges->lire)) if(isModEnabled('facture') &&isModEnabled('commande') && $user->hasRight("commande", "lire") &&empty($conf->global->WORKFLOW_DISABLE_CREATE_INVOICE_FROM_ORDER)) $resql
Social contributions to pay.
Definition: index.php:745
if($cancel &&! $id) if($action=='add' &&! $cancel) if($action=='delete') if($id) $form
Actions.
Definition: card.php:143
dol_escape_htmltag($stringtoescape, $keepb=0, $keepn=0, $noescapetags='', $escapeonlyhtmltags=0)
Returns text escaped for inclusion in HTML alt or title tags, or into values of HTML input fields.
price2num($amount, $rounding='', $option=0)
Function that return a number with universal decimal format (decimal separator is '.
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...
setEventMessages($mesg, $mesgs, $style='mesgs', $messagekey='')
Set event messages in dol_events session object.
dol_print_phone($phone, $countrycode='', $cid=0, $socid=0, $addlink='', $separ="&nbsp;", $withpicto='', $titlealt='', $adddivfloat=0)
Format phone numbers according to country.
dol_now($mode='auto')
Return date for now.
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.
print_liste_field_titre($name, $file="", $field="", $begin="", $moreparam="", $moreattrib="", $sortfield="", $sortorder="", $prefix="", $tooltip="", $forcenowrapcolumntitle=0)
Show title line of an array.
getTitleFieldOfList($name, $thead=0, $file="", $field="", $begin="", $moreparam="", $moreattrib="", $sortfield="", $sortorder="", $prefix="", $disablesortlink=0, $tooltip='', $forcenowrapcolumntitle=0)
Get title line of an array.
GETPOST($paramname, $check='alphanohtml', $method=0, $filter=null, $options=null, $noreplace=0)
Return value of a param into GET or POST supervariable.
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.
if(!function_exists('utf8_encode')) if(!function_exists('utf8_decode')) getDolGlobalString($key, $default='')
Return dolibarr global constant string value.
GETPOSTISSET($paramname)
Return true if we are in a context of submitting the parameter $paramname from a POST of a form.
isModEnabled($module)
Is Dolibarr module enabled.
$nbtotalofrecords
Count total nb of records.
Definition: list.php:329
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.