dolibarr  13.0.2
card.php
Go to the documentation of this file.
1 <?php
2 /* Copyright (C) 2003-2008 Rodolphe Quiedeville <rodolphe@quiedeville.org>
3  * Copyright (C) 2005-2016 Laurent Destailleur <eldy@users.sourceforge.net>
4  * Copyright (C) 2005 Simon TOSSER <simon@kornog-computing.com>
5  * Copyright (C) 2005-2012 Regis Houssin <regis.houssin@capnetworks.com>
6  * Copyright (C) 2011-2017 Juanjo Menent <jmenent@2byte.es>
7  * Copyright (C) 2013 Florian Henry <florian.henry@open-concept.pro>
8  * Copyright (C) 2013 Marcos García <marcosgdf@gmail.com>
9  * Copyright (C) 2014 Cedric GROSS <c.gross@kreiz-it.fr>
10  * Copyright (C) 2014-2017 Francis Appels <francis.appels@yahoo.com>
11  * Copyright (C) 2015 Claudio Aschieri <c.aschieri@19.coop>
12  * Copyright (C) 2016 Ferran Marcet <fmarcet@2byte.es>
13  * Copyright (C) 2016 Yasser Carreón <yacasia@gmail.com>
14  * Copyright (C) 2018 Quentin Vial-Gouteyron <quentin.vial-gouteyron@atm-consulting.fr>
15  *
16  * This program is free software; you can redistribute it and/or modify
17  * it under the terms of the GNU General Public License as published by
18  * the Free Software Foundation; either version 3 of the License, or
19  * (at your option) any later version.
20  *
21  * This program is distributed in the hope that it will be useful,
22  * but WITHOUT ANY WARRANTY; without even the implied warranty of
23  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
24  * GNU General Public License for more details.
25  *
26  * You should have received a copy of the GNU General Public License
27  * along with this program. If not, see <https://www.gnu.org/licenses/>.
28  */
29 
36 require '../main.inc.php';
37 require_once DOL_DOCUMENT_ROOT.'/core/class/html.formfile.class.php';
38 require_once DOL_DOCUMENT_ROOT.'/reception/class/reception.class.php';
39 require_once DOL_DOCUMENT_ROOT.'/product/class/html.formproduct.class.php';
40 require_once DOL_DOCUMENT_ROOT.'/core/lib/product.lib.php';
41 require_once DOL_DOCUMENT_ROOT.'/core/lib/reception.lib.php';
42 require_once DOL_DOCUMENT_ROOT.'/core/modules/reception/modules_reception.php';
43 require_once DOL_DOCUMENT_ROOT.'/core/class/doleditor.class.php';
44 require_once DOL_DOCUMENT_ROOT.'/core/class/extrafields.class.php';
45 require_once DOL_DOCUMENT_ROOT.'/product/stock/class/entrepot.class.php';
46 require_once DOL_DOCUMENT_ROOT.'/product/stock/class/productlot.class.php';
47 if (!empty($conf->product->enabled) || !empty($conf->service->enabled)) require_once DOL_DOCUMENT_ROOT.'/product/class/product.class.php';
48 if (!empty($conf->propal->enabled)) require_once DOL_DOCUMENT_ROOT.'/comm/propal/class/propal.class.php';
49 if (!empty($conf->fournisseur->enabled)) {
50  require_once DOL_DOCUMENT_ROOT.'/fourn/class/fournisseur.commande.class.php';
51  require_once DOL_DOCUMENT_ROOT.'/fourn/class/fournisseur.commande.dispatch.class.php';
52 }
53 if (!empty($conf->productbatch->enabled)) require_once DOL_DOCUMENT_ROOT.'/product/class/productbatch.class.php';
54 if (!empty($conf->projet->enabled)) {
55  require_once DOL_DOCUMENT_ROOT.'/projet/class/project.class.php';
56  require_once DOL_DOCUMENT_ROOT.'/core/class/html.formprojet.class.php';
57 }
58 
59 $langs->loadLangs(array("receptions", "companies", "bills", 'deliveries', 'orders', 'stocks', 'other', 'propal', 'sendings'));
60 
61 if (!empty($conf->incoterm->enabled)) $langs->load('incoterm');
62 if (!empty($conf->productbatch->enabled)) $langs->load('productbatch');
63 
64 $origin = GETPOST('origin', 'alpha') ?GETPOST('origin', 'alpha') : 'reception'; // Example: commande, propal
65 $origin_id = GETPOST('id', 'int') ?GETPOST('id', 'int') : '';
66 $id = $origin_id;
67 if (empty($origin_id)) $origin_id = GETPOST('origin_id', 'int'); // Id of order or propal
68 if (empty($origin_id)) $origin_id = GETPOST('object_id', 'int'); // Id of order or propal
69 if (empty($origin_id)) $origin_id = GETPOST('originid', 'int'); // Id of order or propal
70 $ref = GETPOST('ref', 'alpha');
71 $line_id = GETPOST('lineid', 'int') ?GETPOST('lineid', 'int') : '';
72 
73 // Security check
74 $socid = '';
75 if ($user->socid) $socid = $user->socid;
76 
77 if ($origin == 'reception') $result = restrictedArea($user, $origin, $id);
78 else {
79  $result = restrictedArea($user, 'reception');
80  if ($origin == 'supplierorder') {
81  if (empty($user->rights->fournisseur->commande->lire) && empty($user->rights->fournisseur->commande->read)) accessforbidden();
82  } elseif (empty($user->rights->{$origin}->lire) && empty($user->rights->{$origin}->read)) accessforbidden();
83 }
84 
85 $action = GETPOST('action', 'alpha');
86 //Select mail models is same action as presend
87 if (GETPOST('modelselected')) {
88  $action = 'presend';
89 }
90 $confirm = GETPOST('confirm', 'alpha');
91 $cancel = GETPOST('cancel', 'alpha');
92 
93 //PDF
94 $hidedetails = (GETPOST('hidedetails', 'int') ? GETPOST('hidedetails', 'int') : (!empty($conf->global->MAIN_GENERATE_DOCUMENTS_HIDE_DETAILS) ? 1 : 0));
95 $hidedesc = (GETPOST('hidedesc', 'int') ? GETPOST('hidedesc', 'int') : (!empty($conf->global->MAIN_GENERATE_DOCUMENTS_HIDE_DESC) ? 1 : 0));
96 $hideref = (GETPOST('hideref', 'int') ? GETPOST('hideref', 'int') : (!empty($conf->global->MAIN_GENERATE_DOCUMENTS_HIDE_REF) ? 1 : 0));
97 
98 $object = new Reception($db);
99 $extrafields = new ExtraFields($db);
100 
101 // fetch optionals attributes and labels
102 $extrafields->fetch_name_optionals_label($object->table_element);
103 $extrafields->fetch_name_optionals_label($object->table_element_line);
104 
105 // Load object. Make an object->fetch
106 include DOL_DOCUMENT_ROOT.'/core/actions_fetchobject.inc.php'; // Must be include, not include_once
107 
108 // Initialize technical object to manage hooks of page. Note that conf->hooks_modules contains array of hook context
109 $hookmanager->initHooks(array('receptioncard', 'globalcard'));
110 
111 $permissiondellink = $user->rights->reception->creer; // Used by the include of actions_dellink.inc.php
112 //var_dump($object->lines[0]->detail_batch);
113 
114 $date_delivery = dol_mktime(GETPOST('date_deliveryhour', 'int'), GETPOST('date_deliverymin', 'int'), 0, GETPOST('date_deliverymonth', 'int'), GETPOST('date_deliveryday', 'int'), GETPOST('date_deliveryyear', 'int'));
115 
116 
117 /*
118  * Actions
119  */
120 
121 $parameters = array();
122 $reshook = $hookmanager->executeHooks('doActions', $parameters, $object, $action); // Note that $action and $object may have been modified by some hooks
123 if ($reshook < 0) setEventMessages($hookmanager->error, $hookmanager->errors, 'errors');
124 
125 if (empty($reshook))
126 {
127  if ($cancel)
128  {
129  $action = '';
130  $object->fetch($id); // show reception also after canceling modification
131  }
132 
133  include DOL_DOCUMENT_ROOT.'/core/actions_dellink.inc.php'; // Must be include, not include_once
134 
135  // Reopen
136  if ($action == 'reopen' && $user->rights->reception->creer)
137  {
138  $object->fetch($id);
139  $result = $object->reOpen();
140  }
141 
142  // Confirm back to draft status
143  if ($action == 'modif' && $user->rights->reception->creer)
144  {
145  $result = $object->setDraft($user);
146  if ($result >= 0)
147  {
148  // Define output language
149  if (empty($conf->global->MAIN_DISABLE_PDF_AUTOUPDATE))
150  {
151  $outputlangs = $langs;
152  $newlang = '';
153  if ($conf->global->MAIN_MULTILANGS && empty($newlang) && GETPOST('lang_id', 'aZ09')) $newlang = GETPOST('lang_id', 'aZ09');
154  if ($conf->global->MAIN_MULTILANGS && empty($newlang)) $newlang = $object->thirdparty->default_lang;
155  if (!empty($newlang)) {
156  $outputlangs = new Translate("", $conf);
157  $outputlangs->setDefaultLang($newlang);
158  }
159  $model = $object->model_pdf;
160  $ret = $object->fetch($id); // Reload to get new records
161  $object->generateDocument($model, $outputlangs, $hidedetails, $hidedesc, $hideref);
162  }
163  }
164  }
165 
166  // Set incoterm
167  if ($action == 'set_incoterms' && !empty($conf->incoterm->enabled))
168  {
169  $result = $object->setIncoterms(GETPOST('incoterm_id', 'int'), GETPOST('location_incoterms', 'alpha'));
170  }
171 
172  if ($action == 'setref_supplier')
173  {
174  $result = $object->fetch($id);
175  if ($result < 0) {
176  setEventMessages($object->error, $object->errors, 'errors');
177  }
178 
179  $result = $object->setValueFrom('ref_supplier', GETPOST('ref_supplier', 'alpha'), '', null, 'text', '', $user, 'RECEPTION_MODIFY');
180  if ($result < 0) {
181  setEventMessages($object->error, $object->errors, 'errors');
182  $action = 'editref_supplier';
183  } else {
184  header("Location: ".$_SERVER['PHP_SELF']."?id=".$object->id);
185  exit;
186  }
187  }
188 
189  if ($action == 'update_extras')
190  {
191  $object->oldcopy = dol_clone($object);
192 
193  // Fill array 'array_options' with data from update form
194  $ret = $extrafields->setOptionalsFromPost(null, $object, GETPOST('attribute', 'restricthtml'));
195  if ($ret < 0) $error++;
196 
197  if (!$error)
198  {
199  // Actions on extra fields
200  $result = $object->insertExtraFields('RECEPTION_MODIFY');
201  if ($result < 0)
202  {
203  setEventMessages($object->error, $object->errors, 'errors');
204  $error++;
205  }
206  }
207 
208  if ($error)
209  $action = 'edit_extras';
210  }
211 
212  // Create reception
213  if ($action == 'add' && $user->rights->reception->creer)
214  {
215  $error = 0;
216  $predef = '';
217 
218  $db->begin();
219 
220  $object->note = GETPOST('note', 'alpha');
221  $object->origin = $origin;
222  $object->origin_id = $origin_id;
223  $object->fk_project = GETPOST('projectid', 'int');
224  $object->weight = GETPOST('weight', 'int') == '' ? "NULL" : GETPOST('weight', 'int');
225  $object->sizeH = GETPOST('sizeH', 'int') == '' ? "NULL" : GETPOST('sizeH', 'int');
226  $object->sizeW = GETPOST('sizeW', 'int') == '' ? "NULL" : GETPOST('sizeW', 'int');
227  $object->sizeS = GETPOST('sizeS', 'int') == '' ? "NULL" : GETPOST('sizeS', 'int');
228  $object->size_units = GETPOST('size_units', 'int');
229  $object->weight_units = GETPOST('weight_units', 'int');
230 
231  // On va boucler sur chaque ligne du document d'origine pour completer objet reception
232  // avec info diverses + qte a livrer
233 
234  if ($object->origin == "supplierorder")
235  $classname = 'CommandeFournisseur';
236  else $classname = ucfirst($object->origin);
237  $objectsrc = new $classname($db);
238  $objectsrc->fetch($object->origin_id);
239 
240 
241 
242  $object->socid = $objectsrc->socid;
243  $object->ref_supplier = GETPOST('ref_supplier', 'alpha');
244  $object->model_pdf = GETPOST('model');
245  $object->date_delivery = $date_delivery; // Date delivery planed
246  $object->fk_delivery_address = $objectsrc->fk_delivery_address;
247  $object->shipping_method_id = GETPOST('shipping_method_id', 'int');
248  $object->tracking_number = GETPOST('tracking_number', 'alpha');
249  $object->note_private = GETPOST('note_private', 'restricthtml');
250  $object->note_public = GETPOST('note_public', 'restricthtml');
251  $object->fk_incoterms = GETPOST('incoterm_id', 'int');
252  $object->location_incoterms = GETPOST('location_incoterms', 'alpha');
253 
254  $batch_line = array();
255  $stockLine = array();
256  $array_options = array();
257 
258  $totalqty = 0;
259 
260  $num = 0;
261  foreach ($_POST as $key => $value)
262  {
263  // without batch module enabled
264 
265  if (strpos($key, 'qtyasked') !== false)
266  {
267  $num++;
268  }
269  }
270 
271  for ($i = 1; $i <= $num; $i++)
272  {
273  $idl = "idl".$i;
274 
275  $sub_qty = array();
276  $subtotalqty = 0;
277 
278  $j = 0;
279  $batch = "batchl".$i."_0";
280  $stockLocation = "ent1".$i."_0";
281  $qty = "qtyl".$i;
282 
283 
284 
285  //var_dump(GETPOST($qty,'int')); var_dump($_POST); var_dump($batch);exit;
286  //reception line for product with no batch management and no multiple stock location
287  if (GETPOST($qty, 'int') > 0)
288  $totalqty += GETPOST($qty, 'int');
289 
290 
291  // Extrafields
292  $array_options[$i] = $extrafields->getOptionalsFromPost($object->table_element_line, $i);
293  }
294 
295 
296  if ($totalqty > 0) // There is at least one thing to ship
297  {
298  //var_dump($_POST);exit;
299  for ($i = 1; $i <= $num; $i++)
300  {
301  $lineToTest = '';
302  foreach ($objectsrc->lines as $linesrc) {
303  if ($linesrc->id == GETPOST($idl, 'int')) $lineToTest = $linesrc;
304  }
305  $qty = "qtyl".$i;
306  $comment = "comment".$i;
307  $eatby = "dlc".$i;
308  $sellby = "dluo".$i;
309  $batch = "batch".$i;
310 
311  $timeFormat = '%d/%m/%Y';
312 
313  if (GETPOST($qty, 'int') > 0 || (GETPOST($qty, 'int') == 0 && $conf->global->RECEPTION_GETS_ALL_ORDER_PRODUCTS))
314  {
315  $ent = "entl".$i;
316 
317  $idl = "idl".$i;
318 
319  $entrepot_id = is_numeric(GETPOST($ent, 'int')) ? GETPOST($ent, 'int') : GETPOST('entrepot_id', 'int');
320 
321  if ($entrepot_id < 0)
322  $entrepot_id = '';
323  if (!($linesrc->fk_product > 0) && empty($conf->global->STOCK_SUPPORTS_SERVICES))
324  $entrepot_id = 0;
325  $eatby = GETPOST($eatby, 'alpha');
326  $sellby = GETPOST($sellby, 'alpha');
327  $eatbydate = str_replace('/', '-', $eatby);
328  $sellbydate = str_replace('/', '-', $sellby);
329 
330 
331  $ret = $object->addline($entrepot_id, GETPOST($idl, 'int'), GETPOST($qty, 'int'), $array_options[$i], GETPOST($comment, 'alpha'), strtotime($eatbydate), strtotime($sellbydate), GETPOST($batch, 'alpha'));
332  if ($ret < 0)
333  {
334  setEventMessages($object->error, $object->errors, 'errors');
335  $error++;
336  }
337  }
338  }
339 
340 
341  // Fill array 'array_options' with data from add form
342  $ret = $extrafields->setOptionalsFromPost(null, $object);
343  if ($ret < 0) $error++;
344  if (!$error)
345  {
346  $ret = $object->create($user); // This create reception (like Odoo picking) and line of receptions. Stock movement will when validating reception.
347 
348  if ($ret <= 0)
349  {
350  setEventMessages($object->error, $object->errors, 'errors');
351  $error++;
352  }
353  }
354  } else {
355  setEventMessages($langs->trans("ErrorFieldRequired", $langs->transnoentitiesnoconv("QtyToReceive").'/'.$langs->transnoentitiesnoconv("Warehouse")), null, 'errors');
356  $error++;
357  }
358 
359  if (!$error)
360  {
361  $db->commit();
362  header("Location: card.php?id=".$object->id);
363  exit;
364  } else {
365  $db->rollback();
366  $_GET["commande_id"] = GETPOST('commande_id', 'int');
367  $action = 'create';
368  }
369  } elseif ($action == 'confirm_valid' && $confirm == 'yes' &&
370  ((empty($conf->global->MAIN_USE_ADVANCED_PERMS) && !empty($user->rights->reception->creer))
371  || (!empty($conf->global->MAIN_USE_ADVANCED_PERMS) && !empty($user->rights->reception->reception_advance->validate)))
372  )
373  {
374  $object->fetch_thirdparty();
375 
376  $result = $object->valid($user);
377 
378  if ($result < 0)
379  {
380  $langs->load("errors");
381  setEventMessages($langs->trans($object->error), null, 'errors');
382  } else {
383  // Define output language
384  if (empty($conf->global->MAIN_DISABLE_PDF_AUTOUPDATE))
385  {
386  $outputlangs = $langs;
387  $newlang = '';
388  if ($conf->global->MAIN_MULTILANGS && empty($newlang) && GETPOST('lang_id', 'aZ09')) $newlang = GETPOST('lang_id', 'aZ09');
389  if ($conf->global->MAIN_MULTILANGS && empty($newlang)) $newlang = $object->thirdparty->default_lang;
390  if (!empty($newlang)) {
391  $outputlangs = new Translate("", $conf);
392  $outputlangs->setDefaultLang($newlang);
393  }
394  $model = $object->model_pdf;
395  $ret = $object->fetch($id); // Reload to get new records
396 
397  $result = $object->generateDocument($model, $outputlangs, $hidedetails, $hidedesc, $hideref);
398  if ($result < 0) dol_print_error($db, $result);
399  }
400  }
401  } elseif ($action == 'confirm_delete' && $confirm == 'yes' && $user->rights->reception->supprimer)
402  {
403  $result = $object->delete($user);
404  if ($result > 0)
405  {
406  header("Location: ".DOL_URL_ROOT.'/reception/index.php');
407  exit;
408  } else {
409  setEventMessages($object->error, $object->errors, 'errors');
410  }
411  }
412  // TODO add alternative status
413  /*elseif ($action == 'reopen' && (! empty($user->rights->reception->creer) || ! empty($user->rights->reception->reception_advance->validate)))
414  {
415  $result = $object->setStatut(0);
416  if ($result < 0)
417  {
418  setEventMessages($object->error, $object->errors, 'errors');
419  }
420  }*/
421 
422  elseif ($action == 'setdate_livraison' && $user->rights->reception->creer)
423  {
424  //print "x ".$_POST['liv_month'].", ".$_POST['liv_day'].", ".$_POST['liv_year'];
425  $datedelivery = dol_mktime(GETPOST('liv_hour', 'int'), GETPOST('liv_min', 'int'), 0, GETPOST('liv_month', 'int'), GETPOST('liv_day', 'int'), GETPOST('liv_year', 'int'));
426 
427  $object->fetch($id);
428  $result = $object->setDeliveryDate($user, $datedelivery);
429  if ($result < 0)
430  {
431  setEventMessages($object->error, $object->errors, 'errors');
432  }
433  }
434 
435  // Action update
436  elseif ($action == 'settracking_number' || $action == 'settracking_url'
437  || $action == 'settrueWeight'
438  || $action == 'settrueWidth'
439  || $action == 'settrueHeight'
440  || $action == 'settrueDepth'
441  || $action == 'setshipping_method_id')
442  {
443  $error = 0;
444 
445  if ($action == 'settracking_number') $object->tracking_number = trim(GETPOST('tracking_number', 'alpha'));
446  if ($action == 'settracking_url') $object->tracking_url = trim(GETPOST('tracking_url', 'int'));
447  if ($action == 'settrueWeight') {
448  $object->trueWeight = trim(GETPOST('trueWeight', 'int'));
449  $object->weight_units = GETPOST('weight_units', 'int');
450  }
451  if ($action == 'settrueWidth') $object->trueWidth = trim(GETPOST('trueWidth', 'int'));
452  if ($action == 'settrueHeight') {
453  $object->trueHeight = trim(GETPOST('trueHeight', 'int'));
454  $object->size_units = GETPOST('size_units', 'int');
455  }
456  if ($action == 'settrueDepth') $object->trueDepth = trim(GETPOST('trueDepth', 'int'));
457  if ($action == 'setshipping_method_id') $object->shipping_method_id = trim(GETPOST('shipping_method_id', 'int'));
458 
459  if (!$error)
460  {
461  if ($object->update($user) >= 0)
462  {
463  header("Location: card.php?id=".$object->id);
464  exit;
465  }
466  setEventMessages($object->error, $object->errors, 'errors');
467  }
468 
469  $action = "";
470  }
471 
472  // Build document
473  elseif ($action == 'builddoc') // En get ou en post
474  {
475  // Save last template used to generate document
476  if (GETPOST('model')) $object->setDocModel($user, GETPOST('model', 'alpha'));
477 
478  // Define output language
479  $outputlangs = $langs;
480  $newlang = '';
481  if ($conf->global->MAIN_MULTILANGS && empty($newlang) && GETPOST('lang_id', 'aZ09')) $newlang = GETPOST('lang_id', 'aZ09');
482  if ($conf->global->MAIN_MULTILANGS && empty($newlang)) $newlang = $reception->thirdparty->default_lang;
483  if (!empty($newlang))
484  {
485  $outputlangs = new Translate("", $conf);
486  $outputlangs->setDefaultLang($newlang);
487  }
488  $result = $object->generateDocument($object->model_pdf, $outputlangs, $hidedetails, $hidedesc, $hideref);
489  if ($result <= 0)
490  {
491  setEventMessages($object->error, $object->errors, 'errors');
492  $action = '';
493  }
494  }
495 
496  // Delete file in doc form
497  elseif ($action == 'remove_file')
498  {
499  require_once DOL_DOCUMENT_ROOT.'/core/lib/files.lib.php';
500 
501  $upload_dir = $conf->reception->dir_output;
502  $file = $upload_dir.'/'.GETPOST('file');
503  $ret = dol_delete_file($file, 0, 0, 0, $object);
504  if ($ret) setEventMessages($langs->trans("FileWasRemoved", GETPOST('urlfile')), null, 'mesgs');
505  else setEventMessages($langs->trans("ErrorFailToDeleteFile", GETPOST('urlfile')), null, 'errors');
506  } elseif ($action == 'classifybilled')
507  {
508  $object->fetch($id);
509  $result = $object->set_billed();
510  if ($result >= 0) {
511  header('Location: '.$_SERVER["PHP_SELF"].'?id='.$object->id);
512  exit();
513  }
514  } elseif ($action == 'classifyclosed')
515  {
516  $object->fetch($id);
517  $result = $object->setClosed();
518  if ($result >= 0) {
519  header('Location: '.$_SERVER["PHP_SELF"].'?id='.$object->id);
520  exit();
521  }
522  }
523 
524  /*
525  * delete a line
526  */
527  elseif ($action == 'deleteline' && !empty($line_id))
528  {
529  $object->fetch($id);
530  $lines = $object->lines;
531  $line = new CommandeFournisseurDispatch($db);
532 
533  $num_prod = count($lines);
534  for ($i = 0; $i < $num_prod; $i++)
535  {
536  if ($lines[$i]->id == $line_id)
537  {
538  // delete single warehouse line
539  $line->id = $line_id;
540  if (!$error && $line->delete($user) < 0)
541  {
542  $error++;
543  }
544  }
545  unset($_POST["lineid"]);
546  }
547 
548  if (!$error) {
549  header('Location: '.$_SERVER["PHP_SELF"].'?id='.$object->id);
550  exit();
551  } else {
552  setEventMessages($line->error, $line->errors, 'errors');
553  }
554  }
555 
556  /*
557  * Update a line
558  */
559  elseif ($action == 'updateline' && $user->rights->reception->creer && GETPOST('save'))
560  {
561  // Clean parameters
562  $qty = 0;
563  $entrepot_id = 0;
564  $batch_id = 0;
565 
566  $lines = $object->lines;
567  $num_prod = count($lines);
568  for ($i = 0; $i < $num_prod; $i++)
569  {
570  if ($lines[$i]->id == $line_id) // we have found line to update
571  {
572  $line = new CommandeFournisseurDispatch($db);
573  $line->fetch($line_id);
574  // Extrafields Lines
575  $extrafields->fetch_name_optionals_label($object->table_element_line);
576  $line->array_options = $extrafields->getOptionalsFromPost($object->table_element_line);
577 
578 
579  $line->fk_product = $lines[$i]->fk_product;
580 
581 
582  if ($lines[$i]->fk_product > 0)
583  {
584  // single warehouse reception line
585  $stockLocation = "entl".$line_id;
586  $qty = "qtyl".$line_id;
587  $comment = "comment".$line_id;
588 
589 
590  $line->id = $line_id;
591  $line->fk_entrepot = GETPOST($stockLocation, 'int');
592  $line->qty = GETPOST($qty, 'int');
593  $line->comment = GETPOST($comment, 'alpha');
594 
595  if (!empty($conf->productbatch->enabled)) {
596  $batch = "batch".$line_id;
597  $dlc = "dlc".$line_id;
598  $dluo = "dluo".$line_id;
599  $eatby = GETPOST($dlc, 'alpha');
600  $eatbydate = str_replace('/', '-', $eatby);
601  $sellby = GETPOST($dluo, 'alpha');
602  $sellbydate = str_replace('/', '-', $sellby);
603  $line->batch = GETPOST($batch, 'alpha');
604  $line->eatby = strtotime($eatbydate);
605  $line->sellby = strtotime($sellbydate);
606  }
607 
608  if ($line->update($user) < 0)
609  {
610  setEventMessages($line->error, $line->errors, 'errors');
611  $error++;
612  }
613  } else // Product no predefined
614  {
615  $qty = "qtyl".$line_id;
616  $line->id = $line_id;
617  $line->qty = GETPOST($qty, 'int');
618  $line->fk_entrepot = 0;
619  if ($line->update($user) < 0)
620  {
621  setEventMessages($line->error, $line->errors, 'errors');
622  $error++;
623  }
624  unset($_POST[$qty]);
625  }
626  }
627  }
628 
629  unset($_POST["lineid"]);
630 
631  if (!$error) {
632  if (empty($conf->global->MAIN_DISABLE_PDF_AUTOUPDATE)) {
633  // Define output language
634  $outputlangs = $langs;
635  $newlang = '';
636  if ($conf->global->MAIN_MULTILANGS && empty($newlang) && GETPOST('lang_id', 'aZ09'))
637  $newlang = GETPOST('lang_id', 'aZ09');
638  if ($conf->global->MAIN_MULTILANGS && empty($newlang))
639  $newlang = $object->thirdparty->default_lang;
640  if (!empty($newlang)) {
641  $outputlangs = new Translate("", $conf);
642  $outputlangs->setDefaultLang($newlang);
643  }
644 
645  $ret = $object->fetch($object->id); // Reload to get new records
646  $object->generateDocument($object->model_pdf, $outputlangs, $hidedetails, $hidedesc, $hideref);
647  }
648  } else {
649  header('Location: '.$_SERVER['PHP_SELF'].'?id='.$object->id); // Pour reaffichage de la fiche en cours d'edition
650  exit();
651  }
652  } elseif ($action == 'updateline' && $user->rights->reception->creer && GETPOST('cancel', 'alpha') == $langs->trans("Cancel")) {
653  header('Location: '.$_SERVER['PHP_SELF'].'?id='.$object->id); // Pour reaffichage de la fiche en cours d'edition
654  exit();
655  }
656 
657  include DOL_DOCUMENT_ROOT.'/core/actions_printing.inc.php';
658 
659  // Actions to send emails
660  if (empty($id)) $id = $facid;
661  $triggersendname = 'RECEPTION_SENTBYMAIL';
662  $paramname = 'id';
663  $mode = 'emailfromreception';
664  $trackid = 'shi'.$object->id;
665  include DOL_DOCUMENT_ROOT.'/core/actions_sendmails.inc.php';
666 }
667 
668 
669 /*
670  * View
671  */
672 
673 llxHeader('', $langs->trans('Reception'), 'Reception');
674 
675 $form = new Form($db);
676 $formfile = new FormFile($db);
677 $formproduct = new FormProduct($db);
678 if (!empty($conf->projet->enabled)) { $formproject = new FormProjets($db); }
679 
680 $product_static = new Product($db);
681 $reception_static = new Reception($db);
682 $warehousestatic = new Entrepot($db);
683 
684 if ($action == 'create2')
685 {
686  print load_fiche_titre($langs->trans("CreateReception"), '', 'dollyrevert');
687 
688  print '<br>'.$langs->trans("ReceptionCreationIsDoneFromOrder");
689  $action = ''; $id = ''; $ref = '';
690 }
691 
692 // Mode creation.
693 if ($action == 'create')
694 {
695  $recept = new Reception($db);
696 
697  print load_fiche_titre($langs->trans("CreateReception"));
698  if (!$origin)
699  {
700  setEventMessages($langs->trans("ErrorBadParameters"), null, 'errors');
701  }
702 
703  if ($origin)
704  {
705  if ($origin == 'supplierorder')$classname = 'CommandeFournisseur';
706  else $classname = ucfirst($origin);
707 
708  $object = new $classname($db);
709  if ($object->fetch($origin_id)) // This include the fetch_lines
710  {
711  $soc = new Societe($db);
712  $soc->fetch($object->socid);
713 
714  $author = new User($db);
715  $author->fetch($object->user_author_id);
716 
717  if (!empty($conf->stock->enabled)) $entrepot = new Entrepot($db);
718 
719  print '<form action="'.$_SERVER["PHP_SELF"].'" method="post">';
720  print '<input type="hidden" name="token" value="'.newToken().'">';
721  print '<input type="hidden" name="action" value="add">';
722  print '<input type="hidden" name="origin" value="'.$origin.'">';
723  print '<input type="hidden" name="origin_id" value="'.$object->id.'">';
724  print '<input type="hidden" name="ref_int" value="'.$object->ref_int.'">';
725  if (GETPOST('entrepot_id', 'int'))
726  {
727  print '<input type="hidden" name="entrepot_id" value="'.GETPOST('entrepot_id', 'int').'">';
728  }
729 
731 
732  print '<table class="border centpercent">';
733 
734  // Ref
735  print '<tr><td class="titlefieldcreate fieldrequired">';
736  if ($origin == 'supplierorder' && !empty($conf->fournisseur->enabled))
737  {
738  print $langs->trans("RefOrder").'</td><td colspan="3"><a href="'.DOL_URL_ROOT.'/fourn/commande/card.php?id='.$object->id.'">'.img_object($langs->trans("ShowOrder"), 'order').' '.$object->ref;
739  }
740  if ($origin == 'propal' && !empty($conf->propal->enabled))
741  {
742  print $langs->trans("RefProposal").'</td><td colspan="3"><a href="'.DOL_URL_ROOT.'/comm/card.php?id='.$object->id.'">'.img_object($langs->trans("ShowProposal"), 'propal').' '.$object->ref;
743  }
744  print '</a></td>';
745  print "</tr>\n";
746 
747  // Ref client
748  print '<tr><td>';
749  if ($origin == 'supplier_order') print $langs->trans('SupplierOrder');
750  else print $langs->trans('RefSupplier');
751  print '</td><td colspan="3">';
752  print '<input type="text" name="ref_supplier" value="'.$object->ref_supplier.'" />';
753  print '</td>';
754  print '</tr>';
755 
756  // Tiers
757  print '<tr><td class="titlefieldcreate fieldrequired">'.$langs->trans('Company').'</td>';
758  print '<td colspan="3">'.$soc->getNomUrl(1).'</td>';
759  print '</tr>';
760 
761  // Project
762  if (!empty($conf->projet->enabled))
763  {
764  $projectid = GETPOST('projectid', 'int') ?GETPOST('projectid', 'int') : 0;
765  if (empty($projectid) && !empty($object->fk_project)) $projectid = $object->fk_project;
766  if ($origin == 'project') $projectid = ($originid ? $originid : 0);
767 
768  $langs->load("projects");
769  print '<tr>';
770  print '<td>'.$langs->trans("Project").'</td><td colspan="2">';
771  $numprojet = $formproject->select_projects($soc->id, $projectid, 'projectid', 0);
772  print ' &nbsp; <a href="'.DOL_URL_ROOT.'/projet/card.php?socid='.$soc->id.'&action=create&status=1&backtopage='.urlencode($_SERVER["PHP_SELF"].'?action=create&socid='.$soc->id).'"><span class="valignmiddle text-plus-circle">'.$langs->trans("AddProject").'</span><span class="fa fa-plus-circle valignmiddle"></span></a>';
773  print '</td>';
774  print '</tr>';
775  }
776 
777  // Date delivery planned
778  print '<tr><td>'.$langs->trans("DateDeliveryPlanned").'</td>';
779  print '<td colspan="3">';
780  $date_delivery = ($date_delivery ? $date_delivery : $object->delivery_date); // $date_delivery comes from GETPOST
781  print $form->selectDate($date_delivery ? $date_delivery : -1, 'date_delivery', 1, 1, 1);
782  print "</td>\n";
783  print '</tr>';
784 
785  // Note Public
786  print '<tr><td>'.$langs->trans("NotePublic").'</td>';
787  print '<td colspan="3">';
788  $doleditor = new DolEditor('note_public', $object->note_public, '', 60, 'dolibarr_notes', 'In', 0, false, true, ROWS_3, '90%');
789  print $doleditor->Create(1);
790  print "</td></tr>";
791 
792  // Note Private
793  if ($object->note_private && !$user->socid)
794  {
795  print '<tr><td>'.$langs->trans("NotePrivate").'</td>';
796  print '<td colspan="3">';
797  $doleditor = new DolEditor('note_private', $object->note_private, '', 60, 'dolibarr_notes', 'In', 0, false, true, ROWS_3, '90%');
798  print $doleditor->Create(1);
799  print "</td></tr>";
800  }
801 
802  // Weight
803  print '<tr><td>';
804  print $langs->trans("Weight");
805  print '</td><td colspan="3"><input name="weight" size="4" value="'.GETPOST('weight', 'int').'"> ';
806  $text = $formproduct->selectMeasuringUnits("weight_units", "weight", GETPOST('weight_units', 'int'), 0, 2);
807  $htmltext = $langs->trans("KeepEmptyForAutoCalculation");
808  print $form->textwithpicto($text, $htmltext);
809  print '</td></tr>';
810  // Dim
811  print '<tr><td>';
812  print $langs->trans("Width").' x '.$langs->trans("Height").' x '.$langs->trans("Depth");
813  print ' </td><td colspan="3"><input name="sizeW" size="4" value="'.GETPOST('sizeW', 'int').'">';
814  print ' x <input name="sizeH" size="4" value="'.GETPOST('sizeH', 'int').'">';
815  print ' x <input name="sizeS" size="4" value="'.GETPOST('sizeS', 'int').'">';
816  print ' ';
817  $text = $formproduct->selectMeasuringUnits("size_units", "size", GETPOST('size_units', 'int'), 0, 2);
818  $htmltext = $langs->trans("KeepEmptyForAutoCalculation");
819  print $form->textwithpicto($text, $htmltext);
820  print '</td></tr>';
821 
822  // Delivery method
823  print "<tr><td>".$langs->trans("ReceptionMethod")."</td>";
824  print '<td colspan="3">';
825  $recept->fetch_delivery_methods();
826  print $form->selectarray("shipping_method_id", $recept->meths, GETPOST('shipping_method_id', 'int'), 1, 0, 0, "", 1);
827  if ($user->admin) print info_admin($langs->trans("YouCanChangeValuesForThisListFromDictionarySetup"), 1);
828  print "</td></tr>\n";
829 
830  // Tracking number
831  print "<tr><td>".$langs->trans("TrackingNumber")."</td>";
832  print '<td colspan="3">';
833  print '<input name="tracking_number" size="20" value="'.GETPOST('tracking_number', 'alpha').'">';
834  print "</td></tr>\n";
835 
836  // Other attributes
837  $parameters = array('objectsrc' => $objectsrc, 'colspan' => ' colspan="3"', 'cols' => '3', 'socid'=>$socid);
838  $reshook = $hookmanager->executeHooks('formObjectOptions', $parameters, $recept, $action); // Note that $action and $object may have been modified by hook
839  print $hookmanager->resPrint;
840 
841  // Here $object can be of an object Order
842  $extrafields->fetch_name_optionals_label($object->table_element);
843  if (empty($reshook) && !empty($extrafields->attributes[$object->table_element]['label'])) {
844  // copy from order
845  if ($object->fetch_optionals() > 0) {
846  $recept->array_options = array_merge($recept->array_options, $object->array_options);
847  }
848  print $object->showOptionals($extrafields, 'edit', $parameters);
849  }
850 
851  // Incoterms
852  if (!empty($conf->incoterm->enabled))
853  {
854  print '<tr>';
855  print '<td><label for="incoterm_id">'.$form->textwithpicto($langs->trans("IncotermLabel"), $object->label_incoterms, 1).'</label></td>';
856  print '<td colspan="3" class="maxwidthonsmartphone">';
857  print $form->select_incoterms((!empty($object->fk_incoterms) ? $object->fk_incoterms : ''), (!empty($object->location_incoterms) ? $object->location_incoterms : ''));
858  print '</td></tr>';
859  }
860 
861  // Document model
862  include_once DOL_DOCUMENT_ROOT.'/core/modules/reception/modules_reception.php';
863  $liste = ModelePdfReception::liste_modeles($db);
864 
865  if (count($liste) > 1)
866  {
867  print "<tr><td>".$langs->trans("DefaultModel")."</td>";
868  print '<td colspan="3">';
869  print $form->selectarray('model', $liste, $conf->global->RECEPTION_ADDON_PDF);
870  print "</td></tr>\n";
871  }
872 
873  print "</table>";
874 
875  print dol_get_fiche_end();
876 
877 
878  // Reception lines
879  $numAsked = 0;
880  $dispatchLines = array();
881  foreach ($_POST as $key => $value)
882  {
883  // without batch module enabled
884  if (preg_match('/^product_([0-9]+)_([0-9]+)$/i', $key, $reg))
885  {
886  $numAsked++;
887 
888  // $numline=$reg[2] + 1; // line of product
889  $numline = $numAsked;
890  $prod = "product_".$reg[1].'_'.$reg[2];
891  $qty = "qty_".$reg[1].'_'.$reg[2];
892  $ent = "entrepot_".$reg[1].'_'.$reg[2];
893  $pu = "pu_".$reg[1].'_'.$reg[2]; // This is unit price including discount
894  $fk_commandefourndet = "fk_commandefourndet_".$reg[1].'_'.$reg[2];
895  $dispatchLines[$numAsked] = array('prod' => GETPOST($prod, 'int'), 'qty' =>GETPOST($qty), 'ent' =>GETPOST($ent, 'int'), 'pu' =>GETPOST($pu), 'comment' =>GETPOST('comment'), 'fk_commandefourndet' => GETPOST($fk_commandefourndet, 'int'));
896  }
897 
898  // with batch module enabled
899  if (preg_match('/^product_batch_([0-9]+)_([0-9]+)$/i', $key, $reg))
900  {
901  $numAsked++;
902 
903  // eat-by date dispatch
904  // $numline=$reg[2] + 1; // line of product
905  $numline = $numAsked;
906  $prod = 'product_batch_'.$reg[1].'_'.$reg[2];
907  $qty = 'qty_'.$reg[1].'_'.$reg[2];
908  $ent = 'entrepot_'.$reg[1].'_'.$reg[2];
909  $pu = 'pu_'.$reg[1].'_'.$reg[2];
910  $lot = 'lot_number_'.$reg[1].'_'.$reg[2];
911  $dDLUO = dol_mktime(12, 0, 0, $_POST['dluo_'.$reg[1].'_'.$reg[2].'month'], $_POST['dluo_'.$reg[1].'_'.$reg[2].'day'], $_POST['dluo_'.$reg[1].'_'.$reg[2].'year']);
912  $dDLC = dol_mktime(12, 0, 0, $_POST['dlc_'.$reg[1].'_'.$reg[2].'month'], $_POST['dlc_'.$reg[1].'_'.$reg[2].'day'], $_POST['dlc_'.$reg[1].'_'.$reg[2].'year']);
913  $fk_commandefourndet = 'fk_commandefourndet_'.$reg[1].'_'.$reg[2];
914  $dispatchLines[$numAsked] = array('prod' => GETPOST($prod, 'int'), 'qty' =>GETPOST($qty), 'ent' =>GETPOST($ent, 'int'), 'pu' =>GETPOST($pu), 'comment' =>GETPOST('comment'), 'fk_commandefourndet' => GETPOST($fk_commandefourndet, 'int'), 'DLC'=> $dDLC, 'DLUO'=> $dDLUO, 'lot'=> GETPOST($lot, 'alpha'));
915  }
916  }
917 
918 
919  print '<script type="text/javascript" language="javascript">
920  jQuery(document).ready(function() {
921  jQuery("#autofill").click(function() {';
922  $i = 1;
923  while ($i <= $numAsked)
924  {
925  print 'jQuery("#qtyl'.$i.'").val(jQuery("#qtyasked'.$i.'").val() - jQuery("#qtydelivered'.$i.'").val());'."\n";
926  $i++;
927  }
928  print '});
929  jQuery("#autoreset").click(function() {';
930  $i = 1;
931  while ($i <= $numAsked)
932  {
933  print 'jQuery("#qtyl'.$i.'").val(0);'."\n";
934  $i++;
935  }
936  print '});
937  });
938  </script>';
939 
940  print '<br>';
941 
942  print '<table class="noborder centpercent">';
943 
944  // Load receptions already done for same order
945  $object->loadReceptions();
946 
947  if ($numAsked)
948  {
949  print '<tr class="liste_titre">';
950  print '<td>'.$langs->trans("Description").'</td>';
951  print '<td class="center">'.$langs->trans("QtyOrdered").'</td>';
952  print '<td class="center">'.$langs->trans("QtyReceived").'</td>';
953  print '<td class="center">'.$langs->trans("QtyToReceive");
954  if (empty($conf->productbatch->enabled))
955  {
956  print ' <br>(<a href="#" id="autofill">'.$langs->trans("Fill").'</a>';
957  print ' / <a href="#" id="autoreset">'.$langs->trans("Reset").'</a>)';
958  }
959  print '</td>';
960  if (!empty($conf->stock->enabled))
961  {
962  print '<td class="left">'.$langs->trans("Warehouse").' ('.$langs->trans("Stock").')</td>';
963  }
964  if (!empty($conf->productbatch->enabled))
965  {
966  print '<td class="left">'.$langs->trans("batch_number").'</td>';
967  if (empty($conf->global->PRODUCT_DISABLE_EATBY)) {
968  print '<td class="left">'.$langs->trans("EatByDate").'</td>';
969  }
970  if (empty($conf->global->PRODUCT_DISABLE_SELLBY)) {
971  print '<td class="left">'.$langs->trans("SellByDate").'</td>';
972  }
973  }
974  print "</tr>\n";
975  }
976 
977  $indiceAsked = 1;
978  while ($indiceAsked <= $numAsked)
979  {
980  $product = new Product($db);
981  foreach ($object->lines as $supplierLine) {
982  if ($dispatchLines[$indiceAsked]['fk_commandefourndet'] == $supplierLine->id) {
983  $line = $supplierLine;
984  break;
985  }
986  }
987 
988 
989  // Show product and description
990  $type = $line->product_type ? $line->product_type : $line->fk_product_type;
991  // Try to enhance type detection using date_start and date_end for free lines where type
992  // was not saved.
993  if (!empty($line->date_start)) $type = 1;
994  if (!empty($line->date_end)) $type = 1;
995 
996  print '<!-- line '.$line->rowid.' for product -->'."\n";
997  print '<tr class="oddeven">'."\n";
998 
999 
1000  // Product label
1001  if ($line->fk_product > 0) // If predefined product
1002  {
1003  $product->fetch($line->fk_product);
1004  $product->load_stock('warehouseopen'); // Load all $product->stock_warehouse[idwarehouse]->detail_batch
1005  //var_dump($product->stock_warehouse[1]);
1006 
1007  print '<td>';
1008  print '<a name="'.$line->id.'"></a>'; // ancre pour retourner sur la ligne
1009 
1010  // Show product and description
1011  $product_static->type = $line->fk_product_type;
1012  $product_static->id = $line->fk_product;
1013  $product_static->ref = $line->ref;
1014  $product_static->status_batch = $line->product_tobatch;
1015 
1016  $text = $product_static->getNomUrl(1);
1017  $text .= ' - '.(!empty($line->label) ? $line->label : $line->product_label);
1018  $description = ($conf->global->PRODUIT_DESC_IN_FORM ? '' : dol_htmlentitiesbr($line->desc));
1019  print $form->textwithtooltip($text, $description, 3, '', '', $i);
1020 
1021  // Show range
1022  print_date_range($db->jdate($line->date_start), $db->jdate($line->date_end));
1023 
1024  // Add description in form
1025  if (!empty($conf->global->PRODUIT_DESC_IN_FORM))
1026  {
1027  print ($line->desc && $line->desc != $line->product_label) ? '<br>'.dol_htmlentitiesbr($line->desc) : '';
1028  }
1029 
1030  print '</td>';
1031  } else {
1032  print "<td>";
1033  if ($type == 1) $text = img_object($langs->trans('Service'), 'service');
1034  else $text = img_object($langs->trans('Product'), 'product');
1035 
1036  if (!empty($line->label)) {
1037  $text .= ' <strong>'.$line->label.'</strong>';
1038  print $form->textwithtooltip($text, $line->desc, 3, '', '', $i);
1039  } else {
1040  print $text.' '.nl2br($line->desc);
1041  }
1042 
1043  // Show range
1044  print_date_range($db->jdate($line->date_start), $db->jdate($line->date_end));
1045  print "</td>\n";
1046  }
1047 
1048  // Qty
1049  print '<td class="center">'.$line->qty;
1050  print '<input type="hidden" name="fk_commandefournisseurdet'.$indiceAsked.'" value=\''.$line->id.'\' />';
1051  print '<textarea style="display:none;" name="comment'.$indiceAsked.'" >'.$line->desc.'</textarea>';
1052  print '<input name="qtyasked'.$indiceAsked.'" id="qtyasked'.$indiceAsked.'" type="hidden" value="'.$line->qty.'">';
1053  print '</td>';
1054  $qtyProdCom = $line->qty;
1055 
1056  // Qty already received
1057  print '<td class="center">';
1058 
1059 
1060  $quantityDelivered = $object->receptions[$line->id];
1061  print $quantityDelivered;
1062  print '<input name="qtydelivered'.$indiceAsked.'" id="qtydelivered'.$indiceAsked.'" type="hidden" value="'.$quantityDelivered.'">';
1063  print '</td>';
1064 
1065 
1066  if ($line->product_type == 1 && empty($conf->global->STOCK_SUPPORTS_SERVICES))
1067  {
1068  $quantityToBeDelivered = 0;
1069  } else {
1070  $quantityToBeDelivered = $dispatchLines[$indiceAsked]['qty'];
1071  }
1072  $warehouse_id = $dispatchLines[$indiceAsked]['ent'];
1073 
1074 
1075  $warehouseObject = null;
1076  if (!empty($conf->stock->enabled)) // If warehouse was already selected or if product is not a predefined, we go into this part with no multiwarehouse selection
1077  {
1078  print '<!-- Case warehouse already known or product not a predefined product -->';
1079 
1080  $stock = + $product->stock_warehouse[$dispatchLines[$indiceAsked]['ent']]->real; // Convert to number
1081  $deliverableQty = $dispatchLines[$indiceAsked]['qty'];
1082 
1083  // Quantity to send
1084  print '<td class="center">';
1085  if ($line->product_type == Product::TYPE_PRODUCT || !empty($conf->global->STOCK_SUPPORTS_SERVICES))
1086  {
1087  if (GETPOST('qtyl'.$indiceAsked, 'int')) $defaultqty = GETPOST('qtyl'.$indiceAsked, 'int');
1088  print '<input name="idl'.$indiceAsked.'" type="hidden" value="'.$line->id.'">';
1089  print '<input name="qtyl'.$indiceAsked.'" id="qtyl'.$indiceAsked.'" type="text" size="4" value="'.$deliverableQty.'">';
1090  } else print $langs->trans("NA");
1091  print '</td>';
1092 
1093  // Stock
1094  if (!empty($conf->stock->enabled))
1095  {
1096  print '<td class="left">';
1097  if ($line->product_type == Product::TYPE_PRODUCT || !empty($conf->global->STOCK_SUPPORTS_SERVICES)) // Type of product need stock change ?
1098  {
1099  // Show warehouse combo list
1100  $ent = "entl".$indiceAsked;
1101  $idl = "idl".$indiceAsked;
1102  $tmpentrepot_id = is_numeric(GETPOST($ent, 'int')) ?GETPOST($ent, 'int') : $warehouse_id;
1103  if ($line->fk_product > 0)
1104  {
1105  print '<!-- Show warehouse selection -->';
1106  print $formproduct->selectWarehouses($tmpentrepot_id, 'entl'.$indiceAsked, '', 0, 0, $line->fk_product, '', 1);
1107  }
1108  } else {
1109  print $langs->trans("Service");
1110  }
1111  print '</td>';
1112  }
1113 
1114  if (!empty($conf->productbatch->enabled))
1115  {
1116  if (!empty($product->status_batch))
1117  {
1118  print '<td><input name="batch'.$indiceAsked.'" value="'.$dispatchLines[$indiceAsked]['lot'].'"></td>';
1119  if (empty($conf->global->PRODUCT_DISABLE_EATBY)) {
1120  print '<td>';
1121  print $form->selectDate($dispatchLines[$indiceAsked]['DLC'], 'dlc'.$indiceAsked, '', '', 1, "");
1122  print '</td>';
1123  }
1124  if (empty($conf->global->PRODUCT_DISABLE_SELLBY)) {
1125  print '<td>';
1126  print $form->selectDate($dispatchLines[$indiceAsked]['DLUO'], 'dluo'.$indiceAsked, '', '', 1, "");
1127  print '</td>';
1128  }
1129  } else {
1130  print '<td colspan="3"></td>';
1131  }
1132  }
1133  print "</tr>\n";
1134  }
1135 
1136  //Display lines extrafields
1137  if (is_array($extralabelslines) && count($extralabelslines) > 0)
1138  {
1139  $colspan = 5;
1140  if ($conf->productbatch->enabled) $colspan += 3;
1141 
1142  $srcLine = new CommandeFournisseurLigne($db);
1143  $line = new CommandeFournisseurDispatch($db);
1144 
1145  $extrafields->fetch_name_optionals_label($srcLine->table_element);
1146  $extrafields->fetch_name_optionals_label($line->table_element);
1147 
1148  $srcLine->id = $line->id;
1149  $srcLine->fetch_optionals(); // fetch extrafields also available in orderline
1150  $line->fetch_optionals();
1151 
1152  $line->array_options = array_merge($line->array_options, $srcLine->array_options);
1153 
1154  print $line->showOptionals($extrafields, 'edit', array('style'=>'class="oddeven"', 'colspan'=>$colspan), $indiceAsked);
1155  }
1156 
1157  $indiceAsked++;
1158  }
1159 
1160  print "</table>";
1161 
1162  print '<br>';
1163 
1164  print '<div class="center">';
1165  print '<input type="submit" class="button" name="add" value="'.dol_escape_htmltag($langs->trans("Create")).'">';
1166  print '&nbsp; ';
1167  print '<input type="'.($backtopage ? "submit" : "button").'" class="button button-cancel" name="cancel" value="'.dol_escape_htmltag($langs->trans("Cancel")).'"'.($backtopage ? '' : ' onclick="javascript:history.go(-1)"').'>'; // Cancel for create does not post form if we don't know the backtopage
1168  print '</div>';
1169 
1170  print '</form>';
1171 
1172  print '<br>';
1173  } else {
1174  dol_print_error($db);
1175  }
1176  }
1177 } elseif ($id || $ref)
1178 /* *************************************************************************** */
1179 /* */
1180 /* Edit and view mode */
1181 /* */
1182 /* *************************************************************************** */
1183 {
1184  $lines = $object->lines;
1185 
1186  $num_prod = count($lines);
1187 
1188  if ($object->id > 0)
1189  {
1190  if (!empty($object->origin) && $object->origin_id > 0)
1191  {
1192  $object->origin = 'CommandeFournisseur';
1193  $typeobject = $object->origin;
1194  $origin = $object->origin;
1195  $origin_id = $object->origin_id;
1196  $object->fetch_origin(); // Load property $object->commande, $object->propal, ...
1197  }
1198 
1199  $soc = new Societe($db);
1200  $soc->fetch($object->socid);
1201 
1202  $res = $object->fetch_optionals();
1203 
1204  $head = reception_prepare_head($object);
1205  print dol_get_fiche_head($head, 'reception', $langs->trans("Reception"), -1, 'dollyrevert');
1206 
1207  $formconfirm = '';
1208 
1209  // Confirm deleteion
1210  if ($action == 'delete')
1211  {
1212  $formconfirm = $form->formconfirm($_SERVER['PHP_SELF'].'?id='.$object->id, $langs->trans('DeleteReception'), $langs->trans("ConfirmDeleteReception", $object->ref), 'confirm_delete', '', 0, 1);
1213  }
1214 
1215  // Confirmation validation
1216  if ($action == 'valid')
1217  {
1218  $objectref = substr($object->ref, 1, 4);
1219  if ($objectref == 'PROV')
1220  {
1221  $numref = $object->getNextNumRef($soc);
1222  } else {
1223  $numref = $object->ref;
1224  }
1225 
1226  $text = $langs->trans("ConfirmValidateReception", $numref);
1227 
1228  if (!empty($conf->notification->enabled))
1229  {
1230  require_once DOL_DOCUMENT_ROOT.'/core/class/notify.class.php';
1231  $notify = new Notify($db);
1232  $text .= '<br>';
1233  $text .= $notify->confirmMessage('RECEPTION_VALIDATE', $object->socid, $object);
1234  }
1235 
1236  $formconfirm = $form->formconfirm($_SERVER['PHP_SELF'].'?id='.$object->id, $langs->trans('ValidateReception'), $text, 'confirm_valid', '', 0, 1);
1237  }
1238 
1239  // Confirm cancelation
1240  if ($action == 'annuler')
1241  {
1242  $formconfirm = $form->formconfirm($_SERVER['PHP_SELF'].'?id='.$object->id, $langs->trans('CancelReception'), $langs->trans("ConfirmCancelReception", $object->ref), 'confirm_cancel', '', 0, 1);
1243  }
1244 
1245  if (!$formconfirm) {
1246  $parameters = array('formConfirm' => $formconfirm);
1247  $reshook = $hookmanager->executeHooks('formConfirm', $parameters, $object, $action); // Note that $action and $object may have been modified by hook
1248  if (empty($reshook)) $formconfirm .= $hookmanager->resPrint;
1249  elseif ($reshook > 0) $formconfirm = $hookmanager->resPrint;
1250  }
1251 
1252  // Print form confirm
1253  print $formconfirm;
1254 
1255 
1256  // Calculate totalWeight and totalVolume for all products
1257  // by adding weight and volume of each product line.
1258  $tmparray = $object->getTotalWeightVolume();
1259  $totalWeight = $tmparray['weight'];
1260  $totalVolume = $tmparray['volume'];
1261 
1262 
1263  if ($typeobject == 'commande' && $object->$typeobject->id && !empty($conf->commande->enabled))
1264  {
1265  $objectsrc = new Commande($db);
1266  $objectsrc->fetch($object->$typeobject->id);
1267  }
1268  if ($typeobject == 'propal' && $object->$typeobject->id && !empty($conf->propal->enabled))
1269  {
1270  $objectsrc = new Propal($db);
1271  $objectsrc->fetch($object->$typeobject->id);
1272  }
1273  if ($typeobject == 'CommandeFournisseur' && $object->$typeobject->id && !empty($conf->fournisseur->enabled))
1274  {
1275  $objectsrc = new CommandeFournisseur($db);
1276  $objectsrc->fetch($object->$typeobject->id);
1277  }
1278  // Reception card
1279  $linkback = '<a href="'.DOL_URL_ROOT.'/reception/list.php?restore_lastsearch_values=1'.(!empty($socid) ? '&socid='.$socid : '').'">'.$langs->trans("BackToList").'</a>';
1280  $morehtmlref = '<div class="refidno">';
1281  // Ref customer reception
1282 
1283  $morehtmlref .= $form->editfieldkey("RefSupplier", 'ref_supplier', $object->ref_supplier, $object, $user->rights->reception->creer, 'string', '', 0, 1);
1284  $morehtmlref .= $form->editfieldval("RefSupplier", 'ref_supplier', $object->ref_supplier, $object, $user->rights->reception->creer, 'string', '', null, null, '', 1);
1285 
1286  // Thirdparty
1287  $morehtmlref .= '<br>'.$langs->trans('ThirdParty').' : '.$object->thirdparty->getNomUrl(1);
1288  // Project
1289  if (!empty($conf->projet->enabled))
1290  {
1291  $langs->load("projects");
1292  $morehtmlref .= '<br>'.$langs->trans('Project').' ';
1293  if (0) { // Do not change on reception
1294  if ($action != 'classify') {
1295  $morehtmlref .= '<a class="editfielda" href="'.$_SERVER['PHP_SELF'].'?action=classify&amp;id='.$object->id.'">'.img_edit($langs->transnoentitiesnoconv('SetProject')).'</a> : ';
1296  }
1297  if ($action == 'classify') {
1298  // $morehtmlref.=$form->form_project($_SERVER['PHP_SELF'] . '?id=' . $object->id, $object->socid, $object->fk_project, 'projectid', 0, 0, 1, 1);
1299  $morehtmlref .= '<form method="post" action="'.$_SERVER['PHP_SELF'].'?id='.$object->id.'">';
1300  $morehtmlref .= '<input type="hidden" name="action" value="classin">';
1301  $morehtmlref .= '<input type="hidden" name="token" value="'.newToken().'">';
1302  $morehtmlref .= $formproject->select_projects($object->socid, $object->fk_project, 'projectid', $maxlength, 0, 1, 0, 1, 0, 0, '', 1);
1303  $morehtmlref .= '<input type="submit" class="button" value="'.$langs->trans("Modify").'">';
1304  $morehtmlref .= '</form>';
1305  } else {
1306  $morehtmlref .= $form->form_project($_SERVER['PHP_SELF'].'?id='.$object->id, $object->socid, $object->fk_project, 'none', 0, 0, 0, 1);
1307  }
1308  } else {
1309  // We don't have project on reception, so we will use the project or source object instead
1310  // TODO Add project on reception
1311  $morehtmlref .= ' : ';
1312  if (!empty($objectsrc->fk_project)) {
1313  $proj = new Project($db);
1314  $proj->fetch($objectsrc->fk_project);
1315  $morehtmlref .= '<a href="'.DOL_URL_ROOT.'/projet/card.php?id='.$objectsrc->fk_project.'" title="'.$langs->trans('ShowProject').'">';
1316  $morehtmlref .= $proj->ref;
1317  $morehtmlref .= '</a>';
1318  } else {
1319  $morehtmlref .= '';
1320  }
1321  }
1322  }
1323  $morehtmlref .= '</div>';
1324 
1325  $object->picto = 'sending';
1326  dol_banner_tab($object, 'ref', $linkback, 1, 'ref', 'ref', $morehtmlref);
1327 
1328 
1329  print '<div class="fichecenter">';
1330  print '<div class="fichehalfleft">';
1331  print '<div class="underbanner clearboth"></div>';
1332 
1333  print '<table class="border centpercent">';
1334 
1335  // Linked documents
1336  if ($typeobject == 'commande' && $object->$typeobject->id && !empty($conf->commande->enabled))
1337  {
1338  print '<tr><td>';
1339  print $langs->trans("RefOrder").'</td>';
1340  print '<td colspan="3">';
1341  print $objectsrc->getNomUrl(1, 'commande');
1342  print "</td>\n";
1343  print '</tr>';
1344  }
1345  if ($typeobject == 'propal' && $object->$typeobject->id && !empty($conf->propal->enabled))
1346  {
1347  print '<tr><td>';
1348  print $langs->trans("RefProposal").'</td>';
1349  print '<td colspan="3">';
1350  print $objectsrc->getNomUrl(1, 'reception');
1351  print "</td>\n";
1352  print '</tr>';
1353  }
1354  if ($typeobject == 'CommandeFournisseur' && $object->$typeobject->id && !empty($conf->propal->enabled))
1355  {
1356  print '<tr><td>';
1357  print $langs->trans("SupplierOrder").'</td>';
1358  print '<td colspan="3">';
1359  print $objectsrc->getNomUrl(1, 'reception');
1360  print "</td>\n";
1361  print '</tr>';
1362  }
1363 
1364  // Date creation
1365  print '<tr><td class="titlefield">'.$langs->trans("DateCreation").'</td>';
1366  print '<td colspan="3">'.dol_print_date($object->date_creation, "dayhour")."</td>\n";
1367  print '</tr>';
1368 
1369  // Delivery date planned
1370  print '<tr><td height="10">';
1371  print '<table class="nobordernopadding" width="100%"><tr><td>';
1372  print $langs->trans('DateDeliveryPlanned');
1373  print '</td>';
1374 
1375  if ($action != 'editdate_livraison') print '<td class="right"><a class="editfielda" href="'.$_SERVER["PHP_SELF"].'?action=editdate_livraison&amp;id='.$object->id.'">'.img_edit($langs->trans('SetDeliveryDate'), 1).'</a></td>';
1376  print '</tr></table>';
1377  print '</td><td colspan="2">';
1378  if ($action == 'editdate_livraison')
1379  {
1380  print '<form name="setdate_livraison" action="'.$_SERVER["PHP_SELF"].'?id='.$object->id.'" method="post">';
1381  print '<input type="hidden" name="token" value="'.newToken().'">';
1382  print '<input type="hidden" name="action" value="setdate_livraison">';
1383  print $form->selectDate($object->date_delivery ? $object->date_delivery : -1, 'liv_', 1, 1, '', "setdate_livraison", 1, 0);
1384  print '<input type="submit" class="button" value="'.$langs->trans('Modify').'">';
1385  print '</form>';
1386  } else {
1387  print $object->date_delivery ? dol_print_date($object->date_delivery, 'dayhour') : '&nbsp;';
1388  }
1389  print '</td>';
1390  print '</tr>';
1391 
1392  // Weight
1393  print '<tr><td>';
1394  print $form->editfieldkey("Weight", 'trueWeight', $object->trueWeight, $object, $user->rights->reception->creer);
1395  print '</td><td colspan="3">';
1396 
1397  if ($action == 'edittrueWeight')
1398  {
1399  print '<form name="settrueweight" action="'.$_SERVER["PHP_SELF"].'" method="post">';
1400  print '<input name="action" value="settrueWeight" type="hidden">';
1401  print '<input name="id" value="'.$object->id.'" type="hidden">';
1402  print '<input type="hidden" name="token" value="'.newToken().'">';
1403  print '<input id="trueWeight" name="trueWeight" value="'.$object->trueWeight.'" type="text">';
1404  print $formproduct->selectMeasuringUnits("weight_units", "weight", $object->weight_units, 0, 2);
1405  print ' <input class="button" name="modify" value="'.$langs->trans("Modify").'" type="submit">';
1406  print ' <input class="button button-cancel" name="cancel" value="'.$langs->trans("Cancel").'" type="submit">';
1407  print '</form>';
1408  } else {
1409  print $object->trueWeight;
1410  print ($object->trueWeight && $object->weight_units != '') ? ' '.measuringUnitString(0, "weight", $object->weight_units) : '';
1411  }
1412 
1413  // Calculated
1414  if ($totalWeight > 0)
1415  {
1416  if (!empty($object->trueWeight)) print ' ('.$langs->trans("SumOfProductWeights").': ';
1417  print showDimensionInBestUnit($totalWeight, 0, "weight", $langs, isset($conf->global->MAIN_WEIGHT_DEFAULT_ROUND) ? $conf->global->MAIN_WEIGHT_DEFAULT_ROUND : -1, isset($conf->global->MAIN_WEIGHT_DEFAULT_UNIT) ? $conf->global->MAIN_WEIGHT_DEFAULT_UNIT : 'no');
1418  if (!empty($object->trueWeight)) print ')';
1419  }
1420  print '</td></tr>';
1421 
1422  // Width
1423  print '<tr><td>'.$form->editfieldkey("Width", 'trueWidth', $object->trueWidth, $object, $user->rights->reception->creer).'</td><td colspan="3">';
1424  print $form->editfieldval("Width", 'trueWidth', $object->trueWidth, $object, $user->rights->reception->creer);
1425  print ($object->trueWidth && $object->width_units != '') ? ' '.measuringUnitString(0, "size", $object->width_units) : '';
1426  print '</td></tr>';
1427 
1428  // Height
1429  print '<tr><td>'.$form->editfieldkey("Height", 'trueHeight', $object->trueHeight, $object, $user->rights->reception->creer).'</td><td colspan="3">';
1430  if ($action == 'edittrueHeight')
1431  {
1432  print '<form name="settrueHeight" action="'.$_SERVER["PHP_SELF"].'" method="post">';
1433  print '<input name="action" value="settrueHeight" type="hidden">';
1434  print '<input name="id" value="'.$object->id.'" type="hidden">';
1435  print '<input type="hidden" name="token" value="'.newToken().'">';
1436  print '<input id="trueHeight" name="trueHeight" value="'.$object->trueHeight.'" type="text">';
1437  print $formproduct->selectMeasuringUnits("size_units", "size", $object->size_units, 0, 2);
1438  print ' <input class="button" name="modify" value="'.$langs->trans("Modify").'" type="submit">';
1439  print ' <input class="button button-cancel" name="cancel" value="'.$langs->trans("Cancel").'" type="submit">';
1440  print '</form>';
1441  } else {
1442  print $object->trueHeight;
1443  print ($object->trueHeight && $object->height_units != '') ? ' '.measuringUnitString(0, "size", $object->height_units) : '';
1444  }
1445 
1446  print '</td></tr>';
1447 
1448  // Depth
1449  print '<tr><td>'.$form->editfieldkey("Depth", 'trueDepth', $object->trueDepth, $object, $user->rights->reception->creer).'</td><td colspan="3">';
1450  print $form->editfieldval("Depth", 'trueDepth', $object->trueDepth, $object, $user->rights->reception->creer);
1451  print ($object->trueDepth && $object->depth_units != '') ? ' '.measuringUnitString(0, "size", $object->depth_units) : '';
1452  print '</td></tr>';
1453 
1454  // Volume
1455  print '<tr><td>';
1456  print $langs->trans("Volume");
1457  print '</td>';
1458  print '<td colspan="3">';
1459  $calculatedVolume = 0;
1460  $volumeUnit = 0;
1461  if ($object->trueWidth && $object->trueHeight && $object->trueDepth)
1462  {
1463  $calculatedVolume = ($object->trueWidth * $object->trueHeight * $object->trueDepth);
1464  $volumeUnit = $object->size_units * 3;
1465  }
1466  // If reception volume not defined we use sum of products
1467  if ($calculatedVolume > 0)
1468  {
1469  if ($volumeUnit < 50)
1470  {
1471  print showDimensionInBestUnit($calculatedVolume, $volumeUnit, "volume", $langs, isset($conf->global->MAIN_VOLUME_DEFAULT_ROUND) ? $conf->global->MAIN_VOLUME_DEFAULT_ROUND : -1, isset($conf->global->MAIN_VOLUME_DEFAULT_UNIT) ? $conf->global->MAIN_VOLUME_DEFAULT_UNIT : 'no');
1472  } else print $calculatedVolume.' '.measuringUnitString(0, "volume", $volumeUnit);
1473  }
1474  if ($totalVolume > 0)
1475  {
1476  if ($calculatedVolume) print ' ('.$langs->trans("SumOfProductVolumes").': ';
1477  print showDimensionInBestUnit($totalVolume, 0, "volume", $langs, isset($conf->global->MAIN_VOLUME_DEFAULT_ROUND) ? $conf->global->MAIN_VOLUME_DEFAULT_ROUND : -1, isset($conf->global->MAIN_VOLUME_DEFAULT_UNIT) ? $conf->global->MAIN_VOLUME_DEFAULT_UNIT : 'no');
1478  //if (empty($calculatedVolume)) print ' ('.$langs->trans("Calculated").')';
1479  if ($calculatedVolume) print ')';
1480  }
1481  print "</td>\n";
1482  print '</tr>';
1483 
1484  // Other attributes
1485  $cols = 2;
1486 
1487  include DOL_DOCUMENT_ROOT.'/core/tpl/extrafields_view.tpl.php';
1488 
1489  print '</table>';
1490 
1491  print '</div>';
1492  print '<div class="fichehalfright">';
1493  print '<div class="ficheaddleft">';
1494  print '<div class="underbanner clearboth"></div>';
1495 
1496  print '<table class="border centpercent">';
1497 
1498  // Reception method
1499  print '<tr><td height="10">';
1500  print '<table class="nobordernopadding" width="100%"><tr><td>';
1501  print $langs->trans('ReceptionMethod');
1502  print '</td>';
1503 
1504  if ($action != 'editshipping_method_id') print '<td class="right"><a class="editfielda" href="'.$_SERVER["PHP_SELF"].'?action=editshipping_method_id&amp;id='.$object->id.'">'.img_edit($langs->trans('SetReceptionMethod'), 1).'</a></td>';
1505  print '</tr></table>';
1506  print '</td><td colspan="2">';
1507  if ($action == 'editshipping_method_id')
1508  {
1509  print '<form name="setshipping_method_id" action="'.$_SERVER["PHP_SELF"].'?id='.$object->id.'" method="post">';
1510  print '<input type="hidden" name="token" value="'.newToken().'">';
1511  print '<input type="hidden" name="action" value="setshipping_method_id">';
1512  $object->fetch_delivery_methods();
1513  print $form->selectarray("shipping_method_id", $object->meths, $object->shipping_method_id, 1, 0, 0, "", 1);
1514  if ($user->admin) print info_admin($langs->trans("YouCanChangeValuesForThisListFromDictionarySetup"), 1);
1515  print '<input type="submit" class="button" value="'.$langs->trans('Modify').'">';
1516  print '</form>';
1517  } else {
1518  if ($object->shipping_method_id > 0)
1519  {
1520  // Get code using getLabelFromKey
1521  $code = $langs->getLabelFromKey($db, $object->shipping_method_id, 'c_shipment_mode', 'rowid', 'code');
1522  print $langs->trans("SendingMethod".strtoupper($code));
1523  }
1524  }
1525  print '</td>';
1526  print '</tr>';
1527 
1528  // Tracking Number
1529 
1530  print '<tr><td class="titlefield">'.$form->editfieldkey("TrackingNumber", 'tracking_number', $object->tracking_number, $object, $user->rights->reception->creer).'</td><td colspan="3">';
1531  print $form->editfieldval("TrackingNumber", 'tracking_number', $object->tracking_url, $object, $user->rights->reception->creer, 'string', $object->tracking_number);
1532  print '</td></tr>';
1533 
1534  // Incoterms
1535  if (!empty($conf->incoterm->enabled))
1536  {
1537  print '<tr><td>';
1538  print '<table width="100%" class="nobordernopadding"><tr><td>';
1539  print $langs->trans('IncotermLabel');
1540  print '<td><td class="right">';
1541  if ($user->rights->reception->creer) print '<a class="editfielda" href="'.DOL_URL_ROOT.'/reception/card.php?id='.$object->id.'&action=editincoterm">'.img_edit().'</a>';
1542  else print '&nbsp;';
1543  print '</td></tr></table>';
1544  print '</td>';
1545  print '<td colspan="3">';
1546  if ($action != 'editincoterm')
1547  {
1548  print $form->textwithpicto($object->display_incoterms(), $object->label_incoterms, 1);
1549  } else {
1550  print $form->select_incoterms((!empty($object->fk_incoterms) ? $object->fk_incoterms : ''), (!empty($object->location_incoterms) ? $object->location_incoterms : ''), $_SERVER['PHP_SELF'].'?id='.$object->id);
1551  }
1552  print '</td></tr>';
1553  }
1554 
1555  print "</table>";
1556 
1557  print '</div>';
1558  print '</div>';
1559  print '</div>';
1560 
1561  print '<div class="clearboth"></div>';
1562 
1563 
1564  // Lines of products
1565  if ($action == 'editline')
1566  {
1567  print '<form name="updateline" id="updateline" action="'.$_SERVER["PHP_SELF"].'?id='.$object->id.'&amp;lineid='.$line_id.'" method="POST">
1568  <input type="hidden" name="token" value="' . newToken().'">
1569  <input type="hidden" name="action" value="updateline">
1570  <input type="hidden" name="mode" value="">
1571  <input type="hidden" name="id" value="' . $object->id.'">';
1572  }
1573  print '<br>';
1574 
1575  print '<div class="div-table-responsive-no-min">';
1576  print '<table class="noborder centpercent">';
1577  print '<tr class="liste_titre">';
1578  // #
1579  if (!empty($conf->global->MAIN_VIEW_LINE_NUMBER))
1580  {
1581  print '<td width="5" class="center">&nbsp;</td>';
1582  }
1583  // Product/Service
1584  print '<td>'.$langs->trans("Products").'</td>';
1585  // Comment
1586  print '<td>'.$langs->trans("Description").'</td>';
1587  // Qty
1588  print '<td class="center">'.$langs->trans("QtyOrdered").'</td>';
1589  if ($origin && $origin_id > 0)
1590  {
1591  print '<td class="center">'.$langs->trans("QtyInOtherReceptions").'</td>';
1592  }
1593  if ($action == 'editline')
1594  {
1595  $editColspan = 3;
1596  if (empty($conf->stock->enabled)) $editColspan--;
1597  if (empty($conf->productbatch->enabled)) $editColspan--;
1598  print '<td class="center" colspan="'.$editColspan.'">';
1599  if ($object->statut <= 1)
1600  {
1601  print $langs->trans("QtyToReceive").' - ';
1602  } else {
1603  print $langs->trans("QtyReceived").' - ';
1604  }
1605  if (!empty($conf->stock->enabled))
1606  {
1607  print $langs->trans("WarehouseSource").' - ';
1608  }
1609  if (!empty($conf->productbatch->enabled))
1610  {
1611  print $langs->trans("Batch");
1612  }
1613  print '</td>';
1614  } else {
1615  if ($object->statut <= 1)
1616  {
1617  print '<td class="center">'.$langs->trans("QtyToReceive").'</td>';
1618  } else {
1619  print '<td class="center">'.$langs->trans("QtyReceived").'</td>';
1620  }
1621  if (!empty($conf->stock->enabled))
1622  {
1623  print '<td class="left">'.$langs->trans("WarehouseSource").'</td>';
1624  }
1625 
1626  if (!empty($conf->productbatch->enabled))
1627  {
1628  print '<td class="left">'.$langs->trans("Batch").'</td>';
1629  }
1630  }
1631  print '<td class="center">'.$langs->trans("CalculatedWeight").'</td>';
1632  print '<td class="center">'.$langs->trans("CalculatedVolume").'</td>';
1633  //print '<td class="center">'.$langs->trans("Size").'</td>';
1634  if ($object->statut == 0)
1635  {
1636  print '<td class="linecoledit"></td>';
1637  print '<td class="linecoldelete" width="10"></td>';
1638  }
1639  print "</tr>\n";
1640 
1641  $var = false;
1642 
1643  if (!empty($conf->global->MAIN_MULTILANGS) && !empty($conf->global->PRODUIT_TEXTS_IN_THIRDPARTY_LANGUAGE))
1644  {
1645  $object->fetch_thirdparty();
1646  $outputlangs = $langs;
1647  $newlang = '';
1648  if (empty($newlang) && GETPOST('lang_id', 'aZ09')) $newlang = GETPOST('lang_id', 'aZ09');
1649  if (empty($newlang)) $newlang = $object->thirdparty->default_lang;
1650  if (!empty($newlang))
1651  {
1652  $outputlangs = new Translate("", $conf);
1653  $outputlangs->setDefaultLang($newlang);
1654  }
1655  }
1656 
1657  // Get list of products already sent for same source object into $alreadysent
1658  $alreadysent = array();
1659 
1660  $origin = 'commande_fournisseur';
1661 
1662  if ($origin && $origin_id > 0)
1663  {
1664  $sql = "SELECT obj.rowid, obj.fk_product, obj.label, obj.description, obj.product_type as fk_product_type, obj.qty as qty_asked, obj.date_start, obj.date_end";
1665  $sql .= ", ed.rowid as receptionline_id, ed.qty, ed.fk_reception as reception_id, ed.fk_entrepot";
1666  $sql .= ", e.rowid as reception_id, e.ref as reception_ref, e.date_creation, e.date_valid, e.date_delivery, e.date_reception";
1667  //if ($conf->delivery_note->enabled) $sql .= ", l.rowid as livraison_id, l.ref as livraison_ref, l.date_delivery, ld.qty as qty_received";
1668  $sql .= ', p.label as product_label, p.ref, p.fk_product_type, p.rowid as prodid, p.tobatch as product_tobatch';
1669  $sql .= ', p.description as product_desc';
1670  $sql .= " FROM ".MAIN_DB_PREFIX."commande_fournisseur_dispatch as ed";
1671  $sql .= ", ".MAIN_DB_PREFIX."reception as e";
1672  $sql .= ", ".MAIN_DB_PREFIX.$origin."det as obj";
1673  //if ($conf->delivery_note->enabled) $sql .= " LEFT JOIN ".MAIN_DB_PREFIX."delivery as l ON l.fk_reception = e.rowid LEFT JOIN ".MAIN_DB_PREFIX."deliverydet as ld ON ld.fk_delivery = l.rowid AND obj.rowid = ld.fk_origin_line";
1674  $sql .= " LEFT JOIN ".MAIN_DB_PREFIX."product as p ON obj.fk_product = p.rowid";
1675  $sql .= " WHERE e.entity IN (".getEntity('reception').")";
1676  $sql .= " AND obj.fk_commande = ".$origin_id;
1677  $sql .= " AND obj.rowid = ed.fk_commandefourndet";
1678  $sql .= " AND ed.fk_reception = e.rowid";
1679  $sql .= " AND ed.fk_reception !=".$object->id;
1680  //if ($filter) $sql.= $filter;
1681  $sql .= " ORDER BY obj.fk_product";
1682 
1683  dol_syslog("get list of reception lines", LOG_DEBUG);
1684  $resql = $db->query($sql);
1685  if ($resql)
1686  {
1687  $num = $db->num_rows($resql);
1688  $i = 0;
1689 
1690  while ($i < $num)
1691  {
1692  $obj = $db->fetch_object($resql);
1693  if ($obj)
1694  {
1695  // $obj->rowid is rowid in $origin."det" table
1696  $alreadysent[$obj->rowid][$obj->receptionline_id] = array('reception_ref'=>$obj->reception_ref, 'reception_id'=>$obj->reception_id, 'warehouse'=>$obj->fk_entrepot, 'qty'=>$obj->qty, 'date_valid'=>$obj->date_valid, 'date_delivery'=>$obj->date_delivery);
1697  }
1698  $i++;
1699  }
1700  }
1701  //var_dump($alreadysent);
1702  }
1703 
1704  // Loop on each product to send/sent
1705  for ($i = 0; $i < $num_prod; $i++)
1706  {
1707  print '<!-- origin line id = '.$lines[$i]->origin_line_id.' -->'; // id of order line
1708  print '<tr class="oddeven">';
1709 
1710  // #
1711  if (!empty($conf->global->MAIN_VIEW_LINE_NUMBER))
1712  {
1713  print '<td class="center">'.($i + 1).'</td>';
1714  }
1715 
1716  // Predefined product or service
1717  if ($lines[$i]->fk_product > 0)
1718  {
1719  // Define output language
1720  if (!empty($conf->global->MAIN_MULTILANGS) && !empty($conf->global->PRODUIT_TEXTS_IN_THIRDPARTY_LANGUAGE))
1721  {
1722  $prod = new Product($db);
1723  $prod->fetch($lines[$i]->fk_product);
1724  $label = (!empty($prod->multilangs[$outputlangs->defaultlang]["label"])) ? $prod->multilangs[$outputlangs->defaultlang]["label"] : $lines[$i]->product->label;
1725  } else $label = (!empty($lines[$i]->product->label) ? $lines[$i]->product->label : $lines[$i]->product->product_label);
1726 
1727  print '<td>';
1728 
1729  $text = $lines[$i]->product->getNomUrl(1);
1730  $text .= ' - '.$label;
1731  $description = (!empty($conf->global->PRODUIT_DESC_IN_FORM) ? '' : dol_htmlentitiesbr($lines[$i]->product->description));
1732  print $form->textwithtooltip($text, $description, 3, '', '', $i);
1733  print_date_range($lines[$i]->date_start, $lines[$i]->date_end);
1734  if (!empty($conf->global->PRODUIT_DESC_IN_FORM))
1735  {
1736  print (!empty($lines[$i]->product->description) && $lines[$i]->description != $lines[$i]->product->description) ? '<br>'.dol_htmlentitiesbr($lines[$i]->description) : '';
1737  }
1738  print "</td>\n";
1739  } else {
1740  print "<td>";
1741  if ($lines[$i]->product_type == Product::TYPE_SERVICE) $text = img_object($langs->trans('Service'), 'service');
1742  else $text = img_object($langs->trans('Product'), 'product');
1743 
1744  if (!empty($lines[$i]->label)) {
1745  $text .= ' <strong>'.$lines[$i]->label.'</strong>';
1746  print $form->textwithtooltip($text, $lines[$i]->description, 3, '', '', $i);
1747  } else {
1748  print $text.' '.nl2br($lines[$i]->description);
1749  }
1750 
1751  print_date_range($lines[$i]->date_start, $lines[$i]->date_end);
1752  print "</td>\n";
1753  }
1754 
1755  if ($action == 'editline' && $lines[$i]->id == $line_id)
1756  {
1757  print '<td><textarea name="comment'.$line_id.'" id="comment'.$line_id.'" /> '.$lines[$i]->comment.'</textarea></td>';
1758  } else {
1759  print '<td style="white-space: pre-wrap;max-width: 200px;" >'.$lines[$i]->comment.'</td>';
1760  }
1761 
1762 
1763  // Qty ordered
1764  print '<td class="center">'.$lines[$i]->qty_asked.'</td>';
1765 
1766  // Qty in other receptions (with reception and warehouse used)
1767  if ($origin && $origin_id > 0)
1768  {
1769  print '<td class="center nowrap">';
1770  foreach ($alreadysent as $key => $val)
1771  {
1772  if ($lines[$i]->fk_commandefourndet == $key)
1773  {
1774  $j = 0;
1775  foreach ($val as $receptionline_id=> $receptionline_var)
1776  {
1777  if ($receptionline_var['reception_id'] == $lines[$i]->fk_reception) continue; // We want to show only "other receptions"
1778 
1779  $j++;
1780  if ($j > 1) print '<br>';
1781  $reception_static->fetch($receptionline_var['reception_id']);
1782  print $reception_static->getNomUrl(1);
1783  print ' - '.$receptionline_var['qty'];
1784 
1785  $htmltext = $langs->trans("DateValidation").' : '.(empty($receptionline_var['date_valid']) ? $langs->trans("Draft") : dol_print_date($receptionline_var['date_valid'], 'dayhour'));
1786  if (!empty($conf->stock->enabled) && $receptionline_var['warehouse'] > 0)
1787  {
1788  $warehousestatic->fetch($receptionline_var['warehouse']);
1789  $htmltext .= '<br>'.$langs->trans("From").' : '.$warehousestatic->getNomUrl(1);
1790  }
1791  print ' '.$form->textwithpicto('', $htmltext, 1);
1792  }
1793  }
1794  }
1795  }
1796  print '</td>';
1797 
1798  if ($action == 'editline' && $lines[$i]->id == $line_id)
1799  {
1800  // edit mode
1801  print '<td colspan="'.$editColspan.'" class="center"><table class="nobordernopadding">';
1802  if (!empty($conf->stock->enabled))
1803  {
1804  if ($lines[$i]->fk_product > 0)
1805  {
1806  print '<!-- case edit 1 -->';
1807  print '<tr>';
1808  // Qty to receive or received
1809  print '<td><input name="qtyl'.$line_id.'" id="qtyl'.$line_id.'" type="text" size="4" value="'.$lines[$i]->qty.'"></td>';
1810  // Warehouse source
1811  print '<td>'.$formproduct->selectWarehouses($lines[$i]->fk_entrepot, 'entl'.$line_id, '', 1, 0, $lines[$i]->fk_product, '', 1).'</td>';
1812  // Batch number managment
1813  if ($conf->productbatch->enabled && !empty($lines[$i]->product->status_batch))
1814  {
1815  print '<td> <input name="batch'.$line_id.'" id="batch'.$line_id.'" type="text" value="'.$lines[$i]->batch.'"> </br>';
1816  if (empty($conf->global->PRODUCT_DISABLE_EATBY)) {
1817  print $langs->trans('EatByDate').' : ';
1818  print $form->selectDate($lines[$i]->eatby, 'dlc'.$line_id, '', '', 1, "").'</br>';
1819  }
1820  if (empty($conf->global->PRODUCT_DISABLE_SELLBY)) {
1821  print $langs->trans('SellByDate').' : ';
1822  print $form->selectDate($lines[$i]->sellby, 'dluo'.$line_id, '', '', 1, "");
1823  }
1824  print '</td>';
1825  }
1826  print '</tr>';
1827  } else {
1828  print '<!-- case edit 2 -->';
1829  print '<tr>';
1830  // Qty to receive or received
1831  print '<td><input name="qtyl'.$line_id.'" id="qtyl'.$line_id.'" type="text" size="4" value="'.$lines[$i]->qty.'"></td>';
1832  // Warehouse source
1833  print '<td></td>';
1834  // Batch number managment
1835  print '<td></td>';
1836  print '</tr>';
1837  }
1838  }
1839  print '</table></td>';
1840  } else {
1841  // Qty to receive or received
1842  print '<td class="center">'.$lines[$i]->qty.'</td>';
1843 
1844  // Warehouse source
1845  if (!empty($conf->stock->enabled))
1846  {
1847  print '<td class="left">';
1848 
1849  if ($lines[$i]->fk_entrepot > 0)
1850  {
1851  $entrepot = new Entrepot($db);
1852  $entrepot->fetch($lines[$i]->fk_entrepot);
1853  print $entrepot->getNomUrl(1);
1854  }
1855 
1856  print '</td>';
1857  }
1858 
1859  // Batch number managment
1860  if (!empty($conf->productbatch->enabled))
1861  {
1862  if (isset($lines[$i]->batch))
1863  {
1864  print '<!-- Detail of lot -->';
1865  print '<td>';
1866  $detail = '';
1867  if ($lines[$i]->product->status_batch)
1868  {
1869  $detail .= $langs->trans("Batch").': '.$lines[$i]->batch;
1870  if (empty($conf->global->PRODUCT_DISABLE_SELLBY)) {
1871  $detail .= ' - '.$langs->trans("SellByDate").': '.dol_print_date($lines[$i]->sellby, "day");
1872  }
1873  if (empty($conf->global->PRODUCT_DISABLE_EATBY)) {
1874  $detail .= ' - '.$langs->trans("EatByDate").': '.dol_print_date($lines[$i]->eatby, "day");
1875  }
1876  $detail .= '<br>';
1877 
1878  print $form->textwithtooltip(img_picto('', 'object_barcode').' '.$langs->trans("DetailBatchNumber"), $detail);
1879  } else {
1880  print $langs->trans("NA");
1881  }
1882  print '</td>';
1883  } else {
1884  print '<td></td>';
1885  }
1886  }
1887  }
1888 
1889  // Weight
1890  print '<td class="center">';
1891  if ($lines[$i]->fk_product_type == Product::TYPE_PRODUCT) print $lines[$i]->product->weight * $lines[$i]->qty.' '.measuringUnitString(0, "weight", $lines[$i]->product->weight_units);
1892  else print '&nbsp;';
1893  print '</td>';
1894 
1895  // Volume
1896  print '<td class="center">';
1897  if ($lines[$i]->fk_product_type == Product::TYPE_PRODUCT) print $lines[$i]->product->volume * $lines[$i]->qty.' '.measuringUnitString(0, "volume", $lines[$i]->product->volume_units);
1898  else print '&nbsp;';
1899  print '</td>';
1900 
1901 
1902  if ($action == 'editline' && $lines[$i]->id == $line_id)
1903  {
1904  print '<td class="center" colspan="2" valign="middle">';
1905  print '<input type="submit" class="button button-save" id="savelinebutton marginbottomonly" name="save" value="'.$langs->trans("Save").'"><br>';
1906  print '<input type="submit" class="button button-cancel" id="cancellinebutton" name="cancel" value="'.$langs->trans("Cancel").'"><br>';
1907  } elseif ($object->statut == Reception::STATUS_DRAFT)
1908  {
1909  // edit-delete buttons
1910  print '<td class="linecoledit center">';
1911  print '<a class="editfielda" href="'.$_SERVER["PHP_SELF"].'?id='.$object->id.'&amp;action=editline&amp;token='.newToken().'&amp;lineid='.$lines[$i]->id.'">'.img_edit().'</a>';
1912  print '</td>';
1913  print '<td class="linecoldelete" width="10">';
1914  print '<a class="reposition" href="'.$_SERVER["PHP_SELF"].'?id='.$object->id.'&amp;action=deleteline&amp;token='.newToken().'&amp;lineid='.$lines[$i]->id.'">'.img_delete().'</a>';
1915  print '</td>';
1916 
1917  // Display lines extrafields
1918  if (!empty($rowExtrafieldsStart))
1919  {
1920  print $rowExtrafieldsStart;
1921  print $rowExtrafieldsView;
1922  print $rowEnd;
1923  }
1924  }
1925  print "</tr>";
1926 
1927  // Display lines extrafields
1928  if (is_array($extralabelslines) && count($extralabelslines) > 0)
1929  {
1930  $colspan = empty($conf->productbatch->enabled) ? 8 : 9;
1931  $line = new CommandeFournisseurDispatch($db);
1932  $line->id = $lines[$i]->id;
1933  $line->fetch_optionals();
1934 
1935  if ($action == 'editline' && $lines[$i]->id == $line_id)
1936  {
1937  print $line->showOptionals($extrafields, 'edit', array('colspan'=>$colspan), $indiceAsked);
1938  } else {
1939  print $line->showOptionals($extrafields, 'view', array('colspan'=>$colspan), $indiceAsked);
1940  }
1941  }
1942  }
1943 
1944  // TODO Show also lines ordered but not delivered
1945 
1946  print "</table>\n";
1947  print '</div>';
1948  }
1949 
1950 
1951  print dol_get_fiche_end();
1952 
1953 
1954  $object->fetchObjectLinked($object->id, $object->element);
1955 
1956 
1957  /*
1958  * Boutons actions
1959  */
1960 
1961  if (($user->socid == 0) && ($action != 'presend'))
1962  {
1963  print '<div class="tabsAction">';
1964 
1965  $parameters = array();
1966  $reshook = $hookmanager->executeHooks('addMoreActionsButtons', $parameters, $object, $action); // Note that $action and $object may have been modified by hook
1967  if (empty($reshook))
1968  {
1969  if ($object->statut == Reception::STATUS_DRAFT && $num_prod > 0)
1970  {
1971  if ((empty($conf->global->MAIN_USE_ADVANCED_PERMS) && !empty($user->rights->reception->creer))
1972  || (!empty($conf->global->MAIN_USE_ADVANCED_PERMS) && !empty($user->rights->reception->reception_advance->validate)))
1973  {
1974  print '<a class="butAction" href="'.$_SERVER["PHP_SELF"].'?id='.$object->id.'&amp;action=valid">'.$langs->trans("Validate").'</a>';
1975  } else {
1976  print '<a class="butActionRefused" href="#" title="'.$langs->trans("NotAllowed").'">'.$langs->trans("Validate").'</a>';
1977  }
1978  }
1979  // Edit
1980  if ($object->statut == Reception::STATUS_VALIDATED && $user->rights->reception->creer) {
1981  print '<div class="inline-block divButAction"><a class="butAction" href="card.php?id='.$object->id.'&amp;action=modif">'.$langs->trans('Modify').'</a></div>';
1982  }
1983 
1984  // TODO add alternative status
1985  // 0=draft, 1=validated, 2=billed, we miss a status "delivered" (only available on order)
1986  if ($object->statut == Reception::STATUS_CLOSED && $user->rights->reception->creer)
1987  {
1988  if (!empty($conf->facture->enabled) && !empty($conf->global->WORKFLOW_BILL_ON_RECEPTION)) // Quand l'option est on, il faut avoir le bouton en plus et non en remplacement du Close ?
1989  {
1990  print '<a class="butAction" href="'.$_SERVER["PHP_SELF"].'?id='.$object->id.'&amp;action=reopen">'.$langs->trans("ClassifyUnbilled").'</a>';
1991  } else {
1992  print '<a class="butAction" href="'.$_SERVER["PHP_SELF"].'?id='.$object->id.'&amp;action=reopen">'.$langs->trans("ReOpen").'</a>';
1993  }
1994  }
1995 
1996  // Send
1997  if (empty($user->socid)) {
1998  if ($object->statut > 0)
1999  {
2000  if (empty($conf->global->MAIN_USE_ADVANCED_PERMS) || $user->rights->reception->reception_advance->send)
2001  {
2002  print '<a class="butAction" href="'.$_SERVER["PHP_SELF"].'?id='.$object->id.'&action=presend&mode=init#formmailbeforetitle">'.$langs->trans('SendByMail').'</a>';
2003  } else print '<a class="butActionRefused" href="#">'.$langs->trans('SendByMail').'</a>';
2004  }
2005  }
2006 
2007  // Create bill
2008  if (!empty($conf->fournisseur->enabled) && ($object->statut == Reception::STATUS_VALIDATED || $object->statut == Reception::STATUS_CLOSED))
2009  {
2010  if ($user->rights->fournisseur->facture->creer)
2011  {
2012  // TODO show button only if (! empty($conf->global->WORKFLOW_BILL_ON_RECEPTION))
2013  // If we do that, we must also make this option official.
2014  print '<a class="butAction" href="'.DOL_URL_ROOT.'/fourn/facture/card.php?action=create&amp;origin='.$object->element.'&amp;originid='.$object->id.'&amp;socid='.$object->socid.'">'.$langs->trans("CreateBill").'</a>';
2015  }
2016  }
2017 
2018 
2019  // Close
2020  if ($object->statut == Reception::STATUS_VALIDATED)
2021  {
2022  if ($user->rights->reception->creer && $object->statut > 0 && !$object->billed)
2023  {
2024  $label = "Close"; $paramaction = 'classifyclosed'; // = Transferred/Received
2025  // Label here should be "Close" or "ClassifyBilled" if we decided to make bill on receptions instead of orders
2026  if (!empty($conf->fournisseur->enabled) && !empty($conf->global->WORKFLOW_BILL_ON_RECEPTION)) // Quand l'option est on, il faut avoir le bouton en plus et non en remplacement du Close ?
2027  {
2028  $label = "ClassifyBilled";
2029  $paramaction = 'classifybilled';
2030  }
2031  print '<a class="butAction" href="'.$_SERVER["PHP_SELF"].'?id='.$object->id.'&amp;action='.$paramaction.'">'.$langs->trans($label).'</a>';
2032  }
2033  }
2034 
2035  if ($user->rights->reception->supprimer)
2036  {
2037  print '<a class="butActionDelete" href="'.$_SERVER["PHP_SELF"].'?id='.$object->id.'&amp;action=delete&amp;token='.newToken().'">'.$langs->trans("Delete").'</a>';
2038  }
2039  }
2040 
2041  print '</div>';
2042  }
2043 
2044 
2045  /*
2046  * Documents generated
2047  */
2048 
2049  if ($action != 'presend' && $action != 'editline')
2050  {
2051  print '<div class="fichecenter"><div class="fichehalfleft">';
2052 
2053  $objectref = dol_sanitizeFileName($object->ref);
2054  $filedir = $conf->reception->dir_output."/".$objectref;
2055 
2056  $urlsource = $_SERVER["PHP_SELF"]."?id=".$object->id;
2057 
2058  $genallowed = $user->rights->reception->lire;
2059  $delallowed = $user->rights->reception->creer;
2060 
2061  print $formfile->showdocuments('reception', $objectref, $filedir, $urlsource, $genallowed, $delallowed, $object->model_pdf, 1, 0, 0, 28, 0, '', '', '', $soc->default_lang);
2062 
2063  // Show links to link elements
2064  //$linktoelem = $form->showLinkToObjectBlock($object, null, array('order'));
2065  $somethingshown = $form->showLinkedObjectBlock($object, '');
2066 
2067  print '</div><div class="fichehalfright"><div class="ficheaddleft">';
2068  }
2069 
2070  // Presend form
2071  $modelmail = 'shipping_send';
2072  $defaulttopic = 'SendReceptionRef';
2073  $diroutput = $conf->reception->dir_output;
2074  $trackid = 'rec'.$object->id;
2075 
2076  include DOL_DOCUMENT_ROOT.'/core/tpl/card_presend.tpl.php';
2077 }
2078 
2079 
2080 llxFooter();
2081 
2082 $db->close();
GETPOST($paramname, $check= 'alphanohtml', $method=0, $filter=null, $options=null, $noreplace=0)
Return value of a param into GET or POST supervariable.
Class to manage notifications.
img_edit($titlealt= 'default', $float=0, $other= '')
Show logo editer/modifier fiche.
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...
</td > param sortfield sortorder printFieldListOption< tdclass="liste_titremaxwidthsearchright"></td ></tr >< trclass="liste_titre">< inputtype="checkbox"onClick="toggle(this)"/> Ref p ref Label p label Duration p duration center DesiredStock p desiredstock right StockLimitShort p seuil_stock_alerte right stock_physique right stock_real_warehouse right Ordered right StockToBuy right SupplierRef right param sortfield sortorder printFieldListTitle warehouseinternal SELECT description FROM product_lang WHERE qty< br > qty qty qty StockTooLow StockTooLow help help help< trclass="oddeven">< td >< inputtype="checkbox"class="check"name="choose'.$i.'"></td >< tdclass="nowrap"> stock</td >< td >< inputtype="hidden"name="desc'.$i.'"value="'.dol_escape_htmltag($objp-> description
Only used if Module[ID]Desc translation string is not found.
Definition: replenish.php:750
Class to manage table commandefournisseurdispatch.
Class to manage products or services.
Class to manage Dolibarr users.
Definition: user.class.php:44
dol_clone($object, $native=0)
Create a clone of instance of object (new instance with same value for properties) With native = 0: P...
dol_htmlentitiesbr($stringtoencode, $nl2brmode=0, $pagecodefrom= 'UTF-8', $removelasteolbr=1)
This function is called to encode a string into a HTML string but differs from htmlentities because a...
const TYPE_SERVICE
Service.
const TYPE_PRODUCT
Regular product.
$conf db name
Only used if Module[ID]Name translation string is not found.
Definition: repair.php:108
Class with static methods for building HTML components related to products Only components common to ...
llxHeader()
Empty header.
Definition: wrapper.php:45
Class to manage standard extra fields.
setEventMessages($mesg, $mesgs, $style= 'mesgs', $messagekey= '')
Set event messages in dol_events session object.
Class to manage generation of HTML components Only common components must be here.
Class to manage third parties objects (customers, suppliers, prospects...)
Class to manage projects.
load_fiche_titre($titre, $morehtmlright= '', $picto= 'generic', $pictoisfullpath=0, $id= '', $morecssontable= '', $morehtmlcenter= '')
Load a title with picto.
Class to manage building of HTML components.
showDimensionInBestUnit($dimension, $unit, $type, $outputlangs, $round=-1, $forceunitoutput= 'no')
Output a dimension with best unit.
img_picto($titlealt, $picto, $moreatt= '', $pictoisfullpath=false, $srconly=0, $notitle=0, $alt= '', $morecss= '', $marginleftonlyshort=2)
Show picto whatever it&#39;s its name (generic function)
Class to manage receptions.
Class to manage customers orders.
dol_syslog($message, $level=LOG_INFO, $ident=0, $suffixinfilename= '', $restricttologhandler= '', $logcontext=null)
Write log message into outputs.
dol_delete_file($file, $disableglob=0, $nophperrors=0, $nohook=0, $object=null, $allowdotdot=false, $indexdatabase=1)
Remove a file or several files with a mask.
Definition: files.lib.php:1144
img_object($titlealt, $picto, $moreatt= '', $pictoisfullpath=false, $srconly=0, $notitle=0)
Show a picto called object_picto (generic function)
restrictedArea($user, $features, $objectid=0, $tableandshare= '', $feature2= '', $dbt_keyfield= 'fk_soc', $dbt_select= 'rowid', $isdraft=0)
Check permissions of a user to show a page and an object.
accessforbidden($message= '', $printheader=1, $printfooter=1, $showonlymessage=0, $params=null)
Show a message to say access is forbidden and stop program Calling this function terminate execution ...
Class to manage translations.
dol_sanitizeFileName($str, $newstr= '_', $unaccent=1)
Clean a string to use it as a file name.
Class to manage predefined suppliers products.
Class to offer components to list and upload files.
print $_SERVER["PHP_SELF"]
Edit parameters.
dol_get_fiche_head($links=array(), $active= '', $title= '', $notab=0, $picto= '', $pictoisfullpath=0, $morehtmlright= '', $morecss= '', $limittoshow=0, $moretabssuffix= '')
Show tabs of a record.
static liste_modeles($db, $maxfilenamelength=0)
Return list of active generation modules.
reception_prepare_head(Reception $object)
Prepare array with list of tabs.
print
Draft customers invoices.
Definition: index.php:89
dol_print_date($time, $format= '', $tzoutput= 'auto', $outputlangs= '', $encodetooutput=false)
Output date in a string format according to outputlangs (or langs if not defined).
if(!empty($conf->facture->enabled)&&$user->rights->facture->lire) if((!empty($conf->fournisseur->enabled)&&empty($conf->global->MAIN_USE_NEW_SUPPLIERMOD)||!empty($conf->supplier_invoice->enabled))&&$user->rights->fournisseur->facture->lire) if(!empty($conf->don->enabled)&&$user->rights->don->lire) if(!empty($conf->tax->enabled)&&$user->rights->tax->charges->lire) if(!empty($conf->facture->enabled)&&!empty($conf->commande->enabled)&&$user->rights->commande->lire &&empty($conf->global->WORKFLOW_DISABLE_CREATE_INVOICE_FROM_ORDER)) if(!empty($conf->facture->enabled)&&$user->rights->facture->lire) if((!empty($conf->fournisseur->enabled)&&empty($conf->global->MAIN_USE_NEW_SUPPLIERMOD)||!empty($conf->supplier_invoice->enabled))&&$user->rights->fournisseur->facture->lire) $resql
Social contributions to pay.
Definition: index.php:1232
dol_print_error($db= '', $error= '', $errors=null)
Displays error message system with all the information to facilitate the diagnosis and the escalation...
newToken()
Return the value of token currently saved into session with name &#39;newtoken&#39;.
dol_get_fiche_end($notab=0)
Return tab footer of a card.
Class to manage a WYSIWYG editor.
print_date_range($date_start, $date_end, $format= '', $outputlangs= '')
Format output for start and end date.
dol_banner_tab($object, $paramid, $morehtml= '', $shownav=1, $fieldid= 'rowid', $fieldref= 'ref', $morehtmlref= '', $moreparam= '', $nodbprefix=0, $morehtmlleft= '', $morehtmlstatus= '', $onlybanner=0, $morehtmlright= '')
Show tab footer of a card.
llxFooter()
Empty footer.
Definition: wrapper.php:59
img_delete($titlealt= 'default', $other= 'class="pictodelete"', $morecss= '')
Show delete logo.
if(!defined('CSRFCHECK_WITH_TOKEN')) define('CSRFCHECK_WITH_TOKEN'
Draft customers invoices.
info_admin($text, $infoonimgalt=0, $nodiv=0, $admin= '1', $morecss= '', $textfordropdown= '')
Show information for admin users or standard users.
if(preg_match('/crypted:/i', $dolibarr_main_db_pass)||!empty($dolibarr_main_db_encrypted_pass)) $conf db type
Definition: repair.php:105
Class to manage proposals.
measuringUnitString($unit, $measuring_style= '', $scale= '', $use_short_label=0, $outputlangs=null)
Return translation label of a unit key.
Class to manage warehouses.