dolibarr  16.0.1
card.php
Go to the documentation of this file.
1 <?php
2 /* Copyright (C) 2003-2006 Rodolphe Quiedeville <rodolphe@quiedeville.org>
3  * Copyright (C) 2004-2015 Laurent Destailleur <eldy@users.sourceforge.net>
4  * Copyright (C) 2005 Marc Barilley / Ocebo <marc@ocebo.com>
5  * Copyright (C) 2005-2015 Regis Houssin <regis.houssin@inodbox.com>
6  * Copyright (C) 2006 Andre Cianfarani <acianfa@free.fr>
7  * Copyright (C) 2010-2013 Juanjo Menent <jmenent@2byte.es>
8  * Copyright (C) 2011-2019 Philippe Grand <philippe.grand@atoo-net.com>
9  * Copyright (C) 2012-2013 Christophe Battarel <christophe.battarel@altairis.fr>
10  * Copyright (C) 2012-2016 Marcos García <marcosgdf@gmail.com>
11  * Copyright (C) 2012 Cedric Salvador <csalvador@gpcsolutions.fr>
12  * Copyright (C) 2013 Florian Henry <florian.henry@open-concept.pro>
13  * Copyright (C) 2014 Ferran Marcet <fmarcet@2byte.es>
14  * Copyright (C) 2015 Jean-François Ferry <jfefe@aternatik.fr>
15  * Copyright (C) 2018-2021 Frédéric France <frederic.france@netlogic.fr>
16  * Copyright (C) 2022 Gauthier VERDOL <gauthier.verdol@atm-consulting.fr>
17  *
18  * This program is free software; you can redistribute it and/or modify
19  * it under the terms of the GNU General Public License as published by
20  * the Free Software Foundation; either version 3 of the License, or
21  * (at your option) any later version.
22  *
23  * This program is distributed in the hope that it will be useful,
24  * but WITHOUT ANY WARRANTY; without even the implied warranty of
25  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
26  * GNU General Public License for more details.
27  *
28  * You should have received a copy of the GNU General Public License
29  * along with this program. If not, see <https://www.gnu.org/licenses/>.
30  */
31 
38 require '../main.inc.php';
39 require_once DOL_DOCUMENT_ROOT.'/core/class/html.formfile.class.php';
40 require_once DOL_DOCUMENT_ROOT.'/core/class/html.formorder.class.php';
41 require_once DOL_DOCUMENT_ROOT.'/core/class/html.formmargin.class.php';
42 require_once DOL_DOCUMENT_ROOT.'/core/modules/commande/modules_commande.php';
43 require_once DOL_DOCUMENT_ROOT.'/commande/class/commande.class.php';
44 require_once DOL_DOCUMENT_ROOT.'/comm/action/class/actioncomm.class.php';
45 require_once DOL_DOCUMENT_ROOT.'/core/lib/order.lib.php';
46 require_once DOL_DOCUMENT_ROOT.'/core/lib/functions2.lib.php';
47 require_once DOL_DOCUMENT_ROOT.'/core/class/extrafields.class.php';
48 if (!empty($conf->propal->enabled)) {
49  require_once DOL_DOCUMENT_ROOT.'/comm/propal/class/propal.class.php';
50 }
51 if (!empty($conf->project->enabled)) {
52  require_once DOL_DOCUMENT_ROOT.'/projet/class/project.class.php';
53  require_once DOL_DOCUMENT_ROOT.'/core/class/html.formprojet.class.php';
54 }
55 
56 require_once DOL_DOCUMENT_ROOT.'/core/class/doleditor.class.php';
57 
58 if (!empty($conf->variants->enabled)) {
59  require_once DOL_DOCUMENT_ROOT.'/variants/class/ProductCombination.class.php';
60 }
61 
62 // Load translation files required by the page
63 $langs->loadLangs(array('orders', 'sendings', 'companies', 'bills', 'propal', 'deliveries', 'products', 'other'));
64 if (!empty($conf->incoterm->enabled)) {
65  $langs->load('incoterm');
66 }
67 if (!empty($conf->margin->enabled)) {
68  $langs->load('margins');
69 }
70 if (!empty($conf->productbatch->enabled)) {
71  $langs->load("productbatch");
72 }
73 
74 $id = (GETPOST('id', 'int') ? GETPOST('id', 'int') : GETPOST('orderid', 'int'));
75 $ref = GETPOST('ref', 'alpha');
76 $socid = GETPOST('socid', 'int');
77 $action = GETPOST('action', 'aZ09');
78 $cancel = GETPOST('cancel', 'alpha');
79 $confirm = GETPOST('confirm', 'alpha');
80 $lineid = GETPOST('lineid', 'int');
81 $contactid = GETPOST('contactid', 'int');
82 $projectid = GETPOST('projectid', 'int');
83 $origin = GETPOST('origin', 'alpha');
84 $originid = (GETPOST('originid', 'int') ? GETPOST('originid', 'int') : GETPOST('origin_id', 'int')); // For backward compatibility
85 $rank = (GETPOST('rank', 'int') > 0) ? GETPOST('rank', 'int') : -1;
86 
87 // PDF
88 $hidedetails = (GETPOST('hidedetails', 'int') ? GETPOST('hidedetails', 'int') : (!empty($conf->global->MAIN_GENERATE_DOCUMENTS_HIDE_DETAILS) ? 1 : 0));
89 $hidedesc = (GETPOST('hidedesc', 'int') ? GETPOST('hidedesc', 'int') : (!empty($conf->global->MAIN_GENERATE_DOCUMENTS_HIDE_DESC) ? 1 : 0));
90 $hideref = (GETPOST('hideref', 'int') ? GETPOST('hideref', 'int') : (!empty($conf->global->MAIN_GENERATE_DOCUMENTS_HIDE_REF) ? 1 : 0));
91 
92 // Security check
93 if (!empty($user->socid)) {
94  $socid = $user->socid;
95 }
96 
97 // Initialize technical object to manage hooks of page. Note that conf->hooks_modules contains array of hook context
98 $hookmanager->initHooks(array('ordercard', 'globalcard'));
99 
100 $result = restrictedArea($user, 'commande', $id);
101 
102 $object = new Commande($db);
103 $extrafields = new ExtraFields($db);
104 
105 // fetch optionals attributes and labels
106 $extrafields->fetch_name_optionals_label($object->table_element);
107 
108 // Load object
109 include DOL_DOCUMENT_ROOT.'/core/actions_fetchobject.inc.php'; // Must be include, not include_once
110 
111 $usercanread = $user->hasRight("commande", "lire");
112 $usercancreate = $user->hasRight("commande", "creer");
113 $usercandelete = $user->hasRight("commande", "supprimer");
114 // Advanced permissions
115 $usercanclose = ((empty($conf->global->MAIN_USE_ADVANCED_PERMS) && !empty($user->rights->commande->creer)) || (!empty($conf->global->MAIN_USE_ADVANCED_PERMS) && !empty($user->rights->commande->order_advance->close)));
116 $usercanvalidate = ((empty($conf->global->MAIN_USE_ADVANCED_PERMS) && $usercancreate) || (!empty($conf->global->MAIN_USE_ADVANCED_PERMS) && !empty($user->rights->commande->order_advance->validate)));
117 $usercancancel = ((empty($conf->global->MAIN_USE_ADVANCED_PERMS) && $usercancreate) || (!empty($conf->global->MAIN_USE_ADVANCED_PERMS) && !empty($user->rights->commande->order_advance->annuler)));
118 $usercansend = (empty($conf->global->MAIN_USE_ADVANCED_PERMS) || $user->rights->commande->order_advance->send);
119 
120 $usercancreatepurchaseorder = ($user->hasRight("fournisseur", "commande", "creer") || $user->hasRight("supplier_order", "creer"));
121 
122 $permissionnote = $usercancreate; // Used by the include of actions_setnotes.inc.php
123 $permissiondellink = $usercancreate; // Used by the include of actions_dellink.inc.php
124 $permissiontoadd = $usercancreate; // Used by the include of actions_addupdatedelete.inc.php and actions_lineupdown.inc.php
125 
126 $error = 0;
127 
128 $date_delivery = dol_mktime(GETPOST('liv_hour', 'int'), GETPOST('liv_min', 'int'), 0, GETPOST('liv_month', 'int'), GETPOST('liv_day', 'int'), GETPOST('liv_year', 'int'));
129 
130 
131 /*
132  * Actions
133  */
134 
135 $parameters = array('socid' => $socid);
136 // Note that $action and $object may be modified by some hooks
137 $reshook = $hookmanager->executeHooks('doActions', $parameters, $object, $action);
138 if ($reshook < 0) {
139  setEventMessages($hookmanager->error, $hookmanager->errors, 'errors');
140 }
141 
142 if (empty($reshook)) {
143  $backurlforlist = DOL_URL_ROOT.'/commande/list.php';
144 
145  if (empty($backtopage) || ($cancel && empty($id))) {
146  if (empty($backtopage) || ($cancel && strpos($backtopage, '__ID__'))) {
147  if (empty($id) && (($action != 'add' && $action != 'create') || $cancel)) {
148  $backtopage = $backurlforlist;
149  } else {
150  $backtopage = DOL_URL_ROOT.'/commande/card.php?id='.((!empty($id) && $id > 0) ? $id : '__ID__');
151  }
152  }
153  }
154 
155  if ($cancel) {
156  if (!empty($backtopageforcancel)) {
157  header("Location: ".$backtopageforcancel);
158  exit;
159  } elseif (!empty($backtopage)) {
160  header("Location: ".$backtopage);
161  exit;
162  }
163  $action = '';
164  }
165 
166  include DOL_DOCUMENT_ROOT.'/core/actions_setnotes.inc.php'; // Must be include, not include_once
167 
168  include DOL_DOCUMENT_ROOT.'/core/actions_dellink.inc.php'; // Must be include, not include_once
169 
170  include DOL_DOCUMENT_ROOT.'/core/actions_lineupdown.inc.php'; // Must be include, not include_once
171 
172  // Action clone object
173  if ($action == 'confirm_clone' && $confirm == 'yes' && $usercancreate) {
174  if (1 == 0 && !GETPOST('clone_content') && !GETPOST('clone_receivers')) {
175  setEventMessages($langs->trans("NoCloneOptionsSpecified"), null, 'errors');
176  } else {
177  if ($object->id > 0) {
178  // Because createFromClone modifies the object, we must clone it so that we can restore it later
179  $orig = clone $object;
180 
181  $result = $object->createFromClone($user, $socid);
182  if ($result > 0) {
183  header("Location: ".$_SERVER['PHP_SELF'].'?id='.$result);
184  exit;
185  } else {
186  setEventMessages($object->error, $object->errors, 'errors');
187  $object = $orig;
188  $action = '';
189  }
190  }
191  }
192  } elseif ($action == 'reopen' && $usercancreate) {
193  // Reopen a closed order
194  if ($object->statut == Commande::STATUS_CANCELED || $object->statut == Commande::STATUS_CLOSED) {
195  $result = $object->set_reopen($user);
196  if ($result > 0) {
197  setEventMessages($langs->trans('OrderReopened', $object->ref), null);
198  } else {
199  setEventMessages($object->error, $object->errors, 'errors');
200  }
201  }
202  } elseif ($action == 'confirm_delete' && $confirm == 'yes' && $usercandelete) {
203  // Remove order
204  $result = $object->delete($user);
205  if ($result > 0) {
206  header('Location: list.php?restore_lastsearch_values=1');
207  exit;
208  } else {
209  setEventMessages($object->error, $object->errors, 'errors');
210  }
211  } elseif ($action == 'confirm_deleteline' && $confirm == 'yes' && $usercancreate) {
212  // Remove a product line
213  $result = $object->deleteline($user, $lineid);
214  if ($result > 0) {
215  // reorder lines
216  $object->line_order(true);
217  // Define output language
218  $outputlangs = $langs;
219  $newlang = '';
220  if ($conf->global->MAIN_MULTILANGS && empty($newlang) && GETPOST('lang_id', 'aZ09')) {
221  $newlang = GETPOST('lang_id', 'aZ09');
222  }
223  if ($conf->global->MAIN_MULTILANGS && empty($newlang)) {
224  $newlang = $object->thirdparty->default_lang;
225  }
226  if (!empty($newlang)) {
227  $outputlangs = new Translate("", $conf);
228  $outputlangs->setDefaultLang($newlang);
229  }
230  if (empty($conf->global->MAIN_DISABLE_PDF_AUTOUPDATE)) {
231  $ret = $object->fetch($object->id); // Reload to get new records
232  $object->generateDocument($object->model_pdf, $outputlangs, $hidedetails, $hidedesc, $hideref);
233  }
234 
235  header('Location: '.$_SERVER["PHP_SELF"].'?id='.$object->id);
236  exit;
237  } else {
238  setEventMessages($object->error, $object->errors, 'errors');
239  }
240  } elseif ($action == 'classin' && $usercancreate) {
241  // Link to a project
242  $object->setProject(GETPOST('projectid', 'int'));
243  } elseif ($action == 'add' && $usercancreate) {
244  // Add order
245  $datecommande = dol_mktime(12, 0, 0, GETPOST('remonth'), GETPOST('reday'), GETPOST('reyear'));
246  $date_delivery = dol_mktime(GETPOST('liv_hour', 'int'), GETPOST('liv_min', 'int'), 0, GETPOST('liv_month', 'int'), GETPOST('liv_day', 'int'), GETPOST('liv_year', 'int'));
247  $selectedLines = GETPOST('toselect', 'array');
248 
249  if ($datecommande == '') {
250  setEventMessages($langs->trans('ErrorFieldRequired', $langs->transnoentities('Date')), null, 'errors');
251  $action = 'create';
252  $error++;
253  }
254 
255  if ($socid < 1) {
256  setEventMessages($langs->trans("ErrorFieldRequired", $langs->transnoentitiesnoconv("Customer")), null, 'errors');
257  $action = 'create';
258  $error++;
259  }
260 
261  if (!$error) {
262  $object->socid = $socid;
263  $object->fetch_thirdparty();
264 
265  $db->begin();
266 
267  $object->date_commande = $datecommande;
268  $object->note_private = GETPOST('note_private', 'restricthtml');
269  $object->note_public = GETPOST('note_public', 'restricthtml');
270  $object->source = GETPOST('source_id');
271  $object->fk_project = GETPOST('projectid', 'int');
272  $object->ref_client = GETPOST('ref_client', 'alpha');
273  $object->model_pdf = GETPOST('model');
274  $object->cond_reglement_id = GETPOST('cond_reglement_id');
275  $object->deposit_percent = GETPOST('cond_reglement_id_deposit_percent', 'alpha');
276  $object->mode_reglement_id = GETPOST('mode_reglement_id');
277  $object->fk_account = GETPOST('fk_account', 'int');
278  $object->availability_id = GETPOST('availability_id');
279  $object->demand_reason_id = GETPOST('demand_reason_id');
280  $object->date_livraison = $date_delivery; // deprecated
281  $object->delivery_date = $date_delivery;
282  $object->shipping_method_id = GETPOST('shipping_method_id', 'int');
283  $object->warehouse_id = GETPOST('warehouse_id', 'int');
284  $object->fk_delivery_address = GETPOST('fk_address');
285  $object->contact_id = GETPOST('contactid');
286  $object->fk_incoterms = GETPOST('incoterm_id', 'int');
287  $object->location_incoterms = GETPOST('location_incoterms', 'alpha');
288  $object->multicurrency_code = GETPOST('multicurrency_code', 'alpha');
289  $object->multicurrency_tx = GETPOST('originmulticurrency_tx', 'int');
290  // Fill array 'array_options' with data from add form
291  if (!$error) {
292  $ret = $extrafields->setOptionalsFromPost(null, $object);
293  if ($ret < 0) {
294  $error++;
295  }
296  }
297 
298  // If creation from another object of another module (Example: origin=propal, originid=1)
299  if (!empty($origin) && !empty($originid)) {
300  // Parse element/subelement (ex: project_task)
301  $element = $subelement = $origin;
302  $regs = array();
303  if (preg_match('/^([^_]+)_([^_]+)/i', $origin, $regs)) {
304  $element = $regs [1];
305  $subelement = $regs [2];
306  }
307 
308  // For compatibility
309  if ($element == 'order') {
310  $element = $subelement = 'commande';
311  }
312  if ($element == 'propal') {
313  $element = 'comm/propal';
314  $subelement = 'propal';
315  }
316  if ($element == 'contract') {
317  $element = $subelement = 'contrat';
318  }
319 
320  $object->origin = $origin;
321  $object->origin_id = $originid;
322 
323  // Possibility to add external linked objects with hooks
324  $object->linked_objects [$object->origin] = $object->origin_id;
325  $other_linked_objects = GETPOST('other_linked_objects', 'array');
326  if (!empty($other_linked_objects)) {
327  $object->linked_objects = array_merge($object->linked_objects, $other_linked_objects);
328  }
329 
330  if (!$error) {
331  $object_id = $object->create($user);
332 
333  if ($object_id > 0) {
334  dol_include_once('/'.$element.'/class/'.$subelement.'.class.php');
335 
336  $classname = ucfirst($subelement);
337  $srcobject = new $classname($db);
338 
339  dol_syslog("Try to find source object origin=".$object->origin." originid=".$object->origin_id." to add lines");
340  $result = $srcobject->fetch($object->origin_id);
341  if ($result > 0) {
342  $lines = $srcobject->lines;
343  if (empty($lines) && method_exists($srcobject, 'fetch_lines')) {
344  $srcobject->fetch_lines();
345  $lines = $srcobject->lines;
346  }
347 
348  $fk_parent_line = 0;
349  $num = count($lines);
350 
351  for ($i = 0; $i < $num; $i++) {
352  if (!in_array($lines[$i]->id, $selectedLines)) {
353  continue; // Skip unselected lines
354  }
355 
356  $label = (!empty($lines[$i]->label) ? $lines[$i]->label : '');
357  $desc = (!empty($lines[$i]->desc) ? $lines[$i]->desc : '');
358  $product_type = (!empty($lines[$i]->product_type) ? $lines[$i]->product_type : 0);
359 
360  // Dates
361  // TODO mutualiser
362  $date_start = $lines[$i]->date_debut_prevue;
363  if ($lines[$i]->date_debut_reel) {
364  $date_start = $lines[$i]->date_debut_reel;
365  }
366  if ($lines[$i]->date_start) {
367  $date_start = $lines[$i]->date_start;
368  }
369  $date_end = $lines[$i]->date_fin_prevue;
370  if ($lines[$i]->date_fin_reel) {
371  $date_end = $lines[$i]->date_fin_reel;
372  }
373  if ($lines[$i]->date_end) {
374  $date_end = $lines[$i]->date_end;
375  }
376 
377  // Reset fk_parent_line for no child products and special product
378  if (($lines[$i]->product_type != 9 && empty($lines[$i]->fk_parent_line)) || $lines[$i]->product_type == 9) {
379  $fk_parent_line = 0;
380  }
381 
382  // Extrafields
383  if (method_exists($lines[$i], 'fetch_optionals')) { // For avoid conflicts if trigger used
384  $lines[$i]->fetch_optionals();
385  $array_options = $lines[$i]->array_options;
386  }
387 
388  $tva_tx = $lines[$i]->tva_tx;
389  if (!empty($lines[$i]->vat_src_code) && !preg_match('/\(/', $tva_tx)) {
390  $tva_tx .= ' ('.$lines[$i]->vat_src_code.')';
391  }
392 
393  $result = $object->addline(
394  $desc,
395  $lines[$i]->subprice,
396  $lines[$i]->qty,
397  $tva_tx,
398  $lines[$i]->localtax1_tx,
399  $lines[$i]->localtax2_tx,
400  $lines[$i]->fk_product,
401  $lines[$i]->remise_percent,
402  $lines[$i]->info_bits,
403  $lines[$i]->fk_remise_except,
404  'HT',
405  0,
406  $date_start,
407  $date_end,
408  $product_type,
409  $lines[$i]->rang,
410  $lines[$i]->special_code,
411  $fk_parent_line,
412  $lines[$i]->fk_fournprice,
413  $lines[$i]->pa_ht,
414  $label,
415  $array_options,
416  $lines[$i]->fk_unit,
417  $object->origin,
418  $lines[$i]->rowid
419  );
420 
421  if ($result < 0) {
422  $error++;
423  break;
424  }
425 
426  // Defined the new fk_parent_line
427  if ($result > 0 && $lines[$i]->product_type == 9) {
428  $fk_parent_line = $result;
429  }
430  }
431  } else {
432  setEventMessages($srcobject->error, $srcobject->errors, 'errors');
433  $error++;
434  }
435 
436  // Now we create same links to contact than the ones found on origin object
437  /* Useless, already into the create
438  if (! empty($conf->global->MAIN_PROPAGATE_CONTACTS_FROM_ORIGIN))
439  {
440  $originforcontact = $object->origin;
441  $originidforcontact = $object->origin_id;
442  if ($originforcontact == 'shipping') // shipment and order share the same contacts. If creating from shipment we take data of order
443  {
444  $originforcontact=$srcobject->origin;
445  $originidforcontact=$srcobject->origin_id;
446  }
447  $sqlcontact = "SELECT code, fk_socpeople FROM ".MAIN_DB_PREFIX."element_contact as ec, ".MAIN_DB_PREFIX."c_type_contact as ctc";
448  $sqlcontact.= " WHERE element_id = ".((int) $originidforcontact)." AND ec.fk_c_type_contact = ctc.rowid AND ctc.element = '".$db->escape($originforcontact)."'";
449 
450  $resqlcontact = $db->query($sqlcontact);
451  if ($resqlcontact)
452  {
453  while($objcontact = $db->fetch_object($resqlcontact))
454  {
455  //print $objcontact->code.'-'.$objcontact->fk_socpeople."\n";
456  $object->add_contact($objcontact->fk_socpeople, $objcontact->code);
457  }
458  }
459  else dol_print_error($resqlcontact);
460  }*/
461 
462  // Hooks
463  $parameters = array('objFrom' => $srcobject);
464  // Note that $action and $object may be modified by hook
465  $reshook = $hookmanager->executeHooks('createFrom', $parameters, $object, $action);
466  if ($reshook < 0) {
467  $error++;
468  }
469  } else {
470  setEventMessages($object->error, $object->errors, 'errors');
471  $error++;
472  }
473  } else {
474  // Required extrafield left blank, error message already defined by setOptionalsFromPost()
475  $action = 'create';
476  }
477  } else {
478  if (!$error) {
479  $object_id = $object->create($user);
480  }
481  }
482 
483  // Insert default contacts if defined
484  if ($object_id > 0) {
485  if (GETPOST('contactid', 'int')) {
486  $result = $object->add_contact(GETPOST('contactid', 'int'), 'CUSTOMER', 'external');
487  if ($result < 0) {
488  setEventMessages($langs->trans("ErrorFailedToAddContact"), null, 'errors');
489  $error++;
490  }
491  }
492 
493  $id = $object_id;
494  $action = '';
495  }
496 
497  // End of object creation, we show it
498  if ($object_id > 0 && !$error) {
499  $db->commit();
500  header('Location: '.$_SERVER["PHP_SELF"].'?id='.$object_id);
501  exit();
502  } else {
503  $db->rollback();
504  $action = 'create';
505  setEventMessages($object->error, $object->errors, 'errors');
506  }
507  }
508  } elseif ($action == 'classifybilled' && $usercancreate) {
509  $ret = $object->classifyBilled($user);
510 
511  if ($ret < 0) {
512  setEventMessages($object->error, $object->errors, 'errors');
513  }
514  } elseif ($action == 'classifyunbilled' && $usercancreate) {
515  $ret = $object->classifyUnBilled($user);
516  if ($ret < 0) {
517  setEventMessages($object->error, $object->errors, 'errors');
518  }
519  } elseif ($action == 'setref_client' && $usercancreate) {
520  // Positionne ref commande client
521  $result = $object->set_ref_client($user, GETPOST('ref_client'));
522  if ($result < 0) {
523  setEventMessages($object->error, $object->errors, 'errors');
524  }
525  } elseif ($action == 'setremise' && $usercancreate) {
526  $result = $object->setDiscount($user, price2num(GETPOST('remise'), 2));
527  if ($result < 0) {
528  setEventMessages($object->error, $object->errors, 'errors');
529  }
530  } elseif ($action == 'setabsolutediscount' && $usercancreate) {
531  if (GETPOST('remise_id')) {
532  if ($object->id > 0) {
533  $object->insert_discount(GETPOST('remise_id'));
534  } else {
535  dol_print_error($db, $object->error);
536  }
537  }
538  } elseif ($action == 'setdate' && $usercancreate) {
539  $date = dol_mktime(0, 0, 0, GETPOST('order_month', 'int'), GETPOST('order_day', 'int'), GETPOST('order_year', 'int'));
540 
541  $result = $object->set_date($user, $date);
542  if ($result < 0) {
543  setEventMessages($object->error, $object->errors, 'errors');
544  }
545  } elseif ($action == 'setdate_livraison' && $usercancreate) {
546  $date_delivery = dol_mktime(GETPOST('liv_hour', 'int'), GETPOST('liv_min', 'int'), 0, GETPOST('liv_month', 'int'), GETPOST('liv_day', 'int'), GETPOST('liv_year', 'int'));
547 
548  $object->fetch($id);
549  $result = $object->setDeliveryDate($user, $date_delivery);
550  if ($result < 0) {
551  setEventMessages($object->error, $object->errors, 'errors');
552  }
553  } elseif ($action == 'setmode' && $usercancreate) {
554  $result = $object->setPaymentMethods(GETPOST('mode_reglement_id', 'int'));
555  if ($result < 0) {
556  setEventMessages($object->error, $object->errors, 'errors');
557  }
558  } elseif ($action == 'setmulticurrencycode' && $usercancreate) {
559  // Multicurrency Code
560  $result = $object->setMulticurrencyCode(GETPOST('multicurrency_code', 'alpha'));
561  } elseif ($action == 'setmulticurrencyrate' && $usercancreate) {
562  // Multicurrency rate
563  $result = $object->setMulticurrencyRate(price2num(GETPOST('multicurrency_tx')), GETPOST('calculation_mode', 'int'));
564  } elseif ($action == 'setavailability' && $usercancreate) {
565  $result = $object->availability(GETPOST('availability_id'));
566  if ($result < 0) {
567  setEventMessages($object->error, $object->errors, 'errors');
568  }
569  } elseif ($action == 'setdemandreason' && $usercancreate) {
570  $result = $object->demand_reason(GETPOST('demand_reason_id'));
571  if ($result < 0) {
572  setEventMessages($object->error, $object->errors, 'errors');
573  }
574  } elseif ($action == 'setconditions' && $usercancreate) {
575  $result = $object->setPaymentTerms(GETPOST('cond_reglement_id', 'int'), GETPOST('cond_reglement_id_deposit_percent', 'alpha'));
576  if ($result < 0) {
577  dol_print_error($db, $object->error);
578  } else {
579  if (empty($conf->global->MAIN_DISABLE_PDF_AUTOUPDATE)) {
580  // Define output language
581  $outputlangs = $langs;
582  $newlang = GETPOST('lang_id', 'alpha');
583  if ($conf->global->MAIN_MULTILANGS && empty($newlang)) {
584  $newlang = $object->thirdparty->default_lang;
585  }
586  if (!empty($newlang)) {
587  $outputlangs = new Translate("", $conf);
588  $outputlangs->setDefaultLang($newlang);
589  }
590 
591  $ret = $object->fetch($object->id); // Reload to get new records
592  $object->generateDocument($object->model_pdf, $outputlangs, $hidedetails, $hidedesc, $hideref);
593  }
594  }
595  } elseif ($action == 'set_incoterms' && !empty($conf->incoterm->enabled)) {
596  // Set incoterm
597  $result = $object->setIncoterms(GETPOST('incoterm_id', 'int'), GETPOST('location_incoterms', 'alpha'));
598  if ($result < 0) {
599  setEventMessages($object->error, $object->errors, 'errors');
600  }
601  } elseif ($action == 'setbankaccount' && $usercancreate) {
602  // bank account
603  $result = $object->setBankAccount(GETPOST('fk_account', 'int'));
604  if ($result < 0) {
605  setEventMessages($object->error, $object->errors, 'errors');
606  }
607  } elseif ($action == 'setshippingmethod' && $usercancreate) {
608  // shipping method
609  $result = $object->setShippingMethod(GETPOST('shipping_method_id', 'int'));
610  if ($result < 0) {
611  setEventMessages($object->error, $object->errors, 'errors');
612  }
613  } elseif ($action == 'setwarehouse' && $usercancreate) {
614  // warehouse
615  $result = $object->setWarehouse(GETPOST('warehouse_id', 'int'));
616  if ($result < 0) {
617  setEventMessages($object->error, $object->errors, 'errors');
618  }
619  } elseif ($action == 'setremisepercent' && $usercancreate) {
620  $result = $object->setDiscount($user, price2num(GETPOST('remise_percent'), '', 2));
621  } elseif ($action == 'setremiseabsolue' && $usercancreate) {
622  $result = $object->set_remise_absolue($user, price2num(GETPOST('remise_absolue'), 'MU', 2));
623  } elseif ($action == 'addline' && GETPOST('submitforalllines', 'alpha') && GETPOST('vatforalllines', 'alpha') !== '') {
624  // Define vat_rate
625  $vat_rate = (GETPOST('vatforalllines') ? GETPOST('vatforalllines') : 0);
626  $vat_rate = str_replace('*', '', $vat_rate);
627  $localtax1_rate = get_localtax($vat_rate, 1, $object->thirdparty, $mysoc);
628  $localtax2_rate = get_localtax($vat_rate, 2, $object->thirdparty, $mysoc);
629  foreach ($object->lines as $line) {
630  $result = $object->updateline($line->id, $line->desc, $line->subprice, $line->qty, $line->remise_percent, $vat_rate, $localtax1_rate, $localtax2_rate, 'HT', $line->info_bits, $line->date_start, $line->date_end, $line->product_type, $line->fk_parent_line, 0, $line->fk_fournprice, $line->pa_ht, $line->label, $line->special_code, $line->array_options, $line->fk_unit, $line->multicurrency_subprice);
631  }
632  } elseif ($action == 'addline' && GETPOST('submitforalllines', 'alpha') && GETPOST('remiseforalllines', 'alpha') !== '' && $usercancreate) {
633  // Define remise_percent
634  $remise_percent = (GETPOST('remiseforalllines') ? GETPOST('remiseforalllines') : 0);
635  $remise_percent = str_replace('*', '', $remise_percent);
636  foreach ($object->lines as $line) {
637  $result = $object->updateline($line->id, $line->desc, $line->subprice, $line->qty, $remise_percent, $line->tva_tx, $line->localtax1_tx, $line->localtax2_tx, 'HT', $line->info_bits, $line->date_start, $line->date_end, $line->product_type, $line->fk_parent_line, 0, $line->fk_fournprice, $line->pa_ht, $line->label, $line->special_code, $line->array_options, $line->fk_unit, $line->multicurrency_subprice);
638  }
639  } elseif ($action == 'addline' && $usercancreate) { // Add a new line
640  $langs->load('errors');
641  $error = 0;
642 
643  // Set if we used free entry or predefined product
644  $predef = '';
645  $product_desc = (GETPOSTISSET('dp_desc') ? GETPOST('dp_desc', 'restricthtml') : '');
646  $price_ht = price2num(GETPOST('price_ht'), 'MU', 2);
647  $price_ht_devise = price2num(GETPOST('multicurrency_price_ht'), 'CU', 2);
648  $prod_entry_mode = GETPOST('prod_entry_mode');
649  if ($prod_entry_mode == 'free') {
650  $idprod = 0;
651  $tva_tx = (GETPOST('tva_tx') ? GETPOST('tva_tx') : 0);
652  } else {
653  $idprod = GETPOST('idprod', 'int');
654  $tva_tx = '';
655  }
656 
657  $qty = price2num(GETPOST('qty'.$predef, 'alpha'), 'MS');
658 
659  $remise_percent = (GETPOSTISSET('remise_percent'.$predef) ? price2num(GETPOST('remise_percent'.$predef, 'alpha'), '', 2) : 0);
660  if (empty($remise_percent)) {
661  $remise_percent = 0;
662  }
663 
664  // Extrafields
665  $extralabelsline = $extrafields->fetch_name_optionals_label($object->table_element_line);
666  $array_options = $extrafields->getOptionalsFromPost($object->table_element_line, $predef);
667  // Unset extrafield
668  if (is_array($extralabelsline)) {
669  // Get extra fields
670  foreach ($extralabelsline as $key => $value) {
671  unset($_POST["options_".$key]);
672  }
673  }
674 
675  if ((empty($idprod) || $idprod < 0) && ($price_ht < 0) && ($qty < 0)) {
676  setEventMessages($langs->trans('ErrorBothFieldCantBeNegative', $langs->transnoentitiesnoconv('UnitPriceHT'), $langs->transnoentitiesnoconv('Qty')), null, 'errors');
677  $error++;
678  }
679  if ($prod_entry_mode == 'free' && (empty($idprod) || $idprod < 0) && GETPOST('type') < 0) {
680  setEventMessages($langs->trans('ErrorFieldRequired', $langs->transnoentitiesnoconv('Type')), null, 'errors');
681  $error++;
682  }
683  if ($prod_entry_mode == 'free' && (empty($idprod) || $idprod < 0) && $price_ht == '' && $price_ht_devise == '') { // Unit price can be 0 but not ''. Also price can be negative for order.
684  setEventMessages($langs->trans("ErrorFieldRequired", $langs->transnoentitiesnoconv("UnitPriceHT")), null, 'errors');
685  $error++;
686  }
687  if ($qty == '') {
688  setEventMessages($langs->trans('ErrorFieldRequired', $langs->transnoentitiesnoconv('Qty')), null, 'errors');
689  $error++;
690  }
691  if ($qty < 0) {
692  setEventMessages($langs->trans('FieldCannotBeNegative', $langs->transnoentitiesnoconv('Qty')), null, 'errors');
693  $error++;
694  }
695  if ($prod_entry_mode == 'free' && (empty($idprod) || $idprod < 0) && empty($product_desc)) {
696  setEventMessages($langs->trans('ErrorFieldRequired', $langs->transnoentitiesnoconv('Description')), null, 'errors');
697  $error++;
698  }
699 
700  if (!$error && !empty($conf->variants->enabled) && $prod_entry_mode != 'free') {
701  if ($combinations = GETPOST('combinations', 'array')) {
702  //Check if there is a product with the given combination
703  $prodcomb = new ProductCombination($db);
704 
705  if ($res = $prodcomb->fetchByProductCombination2ValuePairs($idprod, $combinations)) {
706  $idprod = $res->fk_product_child;
707  } else {
708  setEventMessages($langs->trans('ErrorProductCombinationNotFound'), null, 'errors');
709  $error++;
710  }
711  }
712  }
713 
714  if (!$error && ($qty >= 0) && (!empty($product_desc) || (!empty($idprod) && $idprod > 0))) {
715  // Clean parameters
716  $date_start = dol_mktime(GETPOST('date_start'.$predef.'hour'), GETPOST('date_start'.$predef.'min'), GETPOST('date_start'.$predef.'sec'), GETPOST('date_start'.$predef.'month'), GETPOST('date_start'.$predef.'day'), GETPOST('date_start'.$predef.'year'));
717  $date_end = dol_mktime(GETPOST('date_end'.$predef.'hour'), GETPOST('date_end'.$predef.'min'), GETPOST('date_end'.$predef.'sec'), GETPOST('date_end'.$predef.'month'), GETPOST('date_end'.$predef.'day'), GETPOST('date_end'.$predef.'year'));
718  $price_base_type = (GETPOST('price_base_type', 'alpha') ?GETPOST('price_base_type', 'alpha') : 'HT');
719 
720  // Ecrase $pu par celui du produit
721  // Ecrase $desc par celui du produit
722  // Ecrase $tva_tx par celui du produit
723  // Ecrase $base_price_type par celui du produit
724  if (!empty($idprod) && $idprod > 0) {
725  $prod = new Product($db);
726  $prod->fetch($idprod);
727 
728  $label = ((GETPOST('product_label') && GETPOST('product_label') != $prod->label) ? GETPOST('product_label') : '');
729 
730  // Update if prices fields are defined
731  $tva_tx = get_default_tva($mysoc, $object->thirdparty, $prod->id);
732  $tva_npr = get_default_npr($mysoc, $object->thirdparty, $prod->id);
733  if (empty($tva_tx)) {
734  $tva_npr = 0;
735  }
736 
737  $pu_ht = $prod->price;
738  $pu_ttc = $prod->price_ttc;
739  $price_min = $prod->price_min;
740  $price_base_type = $prod->price_base_type;
741 
742  // If price per segment
743  if (!empty($conf->global->PRODUIT_MULTIPRICES) && !empty($object->thirdparty->price_level)) {
744  $pu_ht = $prod->multiprices[$object->thirdparty->price_level];
745  $pu_ttc = $prod->multiprices_ttc[$object->thirdparty->price_level];
746  $price_min = $prod->multiprices_min[$object->thirdparty->price_level];
747  $price_base_type = $prod->multiprices_base_type[$object->thirdparty->price_level];
748  if (!empty($conf->global->PRODUIT_MULTIPRICES_USE_VAT_PER_LEVEL)) { // using this option is a bug. kept for backward compatibility
749  if (isset($prod->multiprices_tva_tx[$object->thirdparty->price_level])) {
750  $tva_tx = $prod->multiprices_tva_tx[$object->thirdparty->price_level];
751  }
752  if (isset($prod->multiprices_recuperableonly[$object->thirdparty->price_level])) {
753  $tva_npr = $prod->multiprices_recuperableonly[$object->thirdparty->price_level];
754  }
755  }
756  } elseif (!empty($conf->global->PRODUIT_CUSTOMER_PRICES)) {
757  // If price per customer
758  require_once DOL_DOCUMENT_ROOT.'/product/class/productcustomerprice.class.php';
759 
760  $prodcustprice = new Productcustomerprice($db);
761 
762  $filter = array('t.fk_product' => $prod->id, 't.fk_soc' => $object->thirdparty->id);
763 
764  $result = $prodcustprice->fetch_all('', '', 0, 0, $filter);
765  if ($result >= 0) {
766  if (count($prodcustprice->lines) > 0) {
767  $pu_ht = price($prodcustprice->lines[0]->price);
768  $pu_ttc = price($prodcustprice->lines[0]->price_ttc);
769  $price_min = price($prodcustprice->lines[0]->price_min);
770  $price_base_type = $prodcustprice->lines[0]->price_base_type;
771  $tva_tx = $prodcustprice->lines[0]->tva_tx;
772  if ($prodcustprice->lines[0]->default_vat_code && !preg_match('/\(.*\)/', $tva_tx)) {
773  $tva_tx .= ' ('.$prodcustprice->lines[0]->default_vat_code.')';
774  }
775  $tva_npr = $prodcustprice->lines[0]->recuperableonly;
776  if (empty($tva_tx)) {
777  $tva_npr = 0;
778  }
779  }
780  } else {
781  setEventMessages($prodcustprice->error, $prodcustprice->errors, 'errors');
782  }
783  } elseif (!empty($conf->global->PRODUIT_CUSTOMER_PRICES_BY_QTY)) {
784  // If price per quantity
785  if ($prod->prices_by_qty[0]) { // yes, this product has some prices per quantity
786  // Search the correct price into loaded array product_price_by_qty using id of array retrieved into POST['pqp'].
787  $pqp = GETPOST('pbq', 'int');
788 
789  // Search price into product_price_by_qty from $prod->id
790  foreach ($prod->prices_by_qty_list[0] as $priceforthequantityarray) {
791  if ($priceforthequantityarray['rowid'] != $pqp) {
792  continue;
793  }
794  // We found the price
795  if ($priceforthequantityarray['price_base_type'] == 'HT') {
796  $pu_ht = $priceforthequantityarray['unitprice'];
797  } else {
798  $pu_ttc = $priceforthequantityarray['unitprice'];
799  }
800  // Note: the remise_percent or price by qty is used to set data on form, so we will use value from POST.
801  break;
802  }
803  }
804  } elseif (!empty($conf->global->PRODUIT_CUSTOMER_PRICES_BY_QTY_MULTIPRICES)) {
805  // If price per quantity and customer
806  if ($prod->prices_by_qty[$object->thirdparty->price_level]) { // yes, this product has some prices per quantity
807  // Search the correct price into loaded array product_price_by_qty using id of array retrieved into POST['pqp'].
808  $pqp = GETPOST('pbq', 'int');
809  // Search price into product_price_by_qty from $prod->id
810  foreach ($prod->prices_by_qty_list[$object->thirdparty->price_level] as $priceforthequantityarray) {
811  if ($priceforthequantityarray['rowid'] != $pqp) {
812  continue;
813  }
814  // We found the price
815  if ($priceforthequantityarray['price_base_type'] == 'HT') {
816  $pu_ht = $priceforthequantityarray['unitprice'];
817  } else {
818  $pu_ttc = $priceforthequantityarray['unitprice'];
819  }
820  // Note: the remise_percent or price by qty is used to set data on form, so we will use value from POST.
821  break;
822  }
823  }
824  }
825 
826  $tmpvat = price2num(preg_replace('/\s*\(.*\)/', '', $tva_tx));
827  $tmpprodvat = price2num(preg_replace('/\s*\(.*\)/', '', $prod->tva_tx));
828 
829  // if price ht is forced (ie: calculated by margin rate and cost price). TODO Why this ?
830  if (!empty($price_ht) || $price_ht === '0') {
831  $pu_ht = price2num($price_ht, 'MU');
832  $pu_ttc = price2num($pu_ht * (1 + ($tmpvat / 100)), 'MU');
833  } elseif ($tmpvat != $tmpprodvat) {
834  // On reevalue prix selon taux tva car taux tva transaction peut etre different
835  // de ceux du produit par defaut (par exemple si pays different entre vendeur et acheteur).
836  if ($price_base_type != 'HT') {
837  $pu_ht = price2num($pu_ttc / (1 + ($tmpvat / 100)), 'MU');
838  } else {
839  $pu_ttc = price2num($pu_ht * (1 + ($tmpvat / 100)), 'MU');
840  }
841  }
842 
843  $desc = '';
844 
845  // Define output language
846  if (!empty($conf->global->MAIN_MULTILANGS) && !empty($conf->global->PRODUIT_TEXTS_IN_THIRDPARTY_LANGUAGE)) {
847  $outputlangs = $langs;
848  $newlang = '';
849  if (empty($newlang) && GETPOST('lang_id', 'aZ09')) {
850  $newlang = GETPOST('lang_id', 'aZ09');
851  }
852  if (empty($newlang)) {
853  $newlang = $object->thirdparty->default_lang;
854  }
855  if (!empty($newlang)) {
856  $outputlangs = new Translate("", $conf);
857  $outputlangs->setDefaultLang($newlang);
858  }
859 
860  $desc = (!empty($prod->multilangs[$outputlangs->defaultlang]["description"])) ? $prod->multilangs[$outputlangs->defaultlang]["description"] : $prod->description;
861  } else {
862  $desc = $prod->description;
863  }
864 
865  //If text set in desc is the same as product descpription (as now it's preloaded) whe add it only one time
866  if ($product_desc==$desc && !empty($conf->global->PRODUIT_AUTOFILL_DESC)) {
867  $product_desc='';
868  }
869 
870  if (!empty($product_desc) && !empty($conf->global->MAIN_NO_CONCAT_DESCRIPTION)) {
871  $desc = $product_desc;
872  } else {
873  $desc = dol_concatdesc($desc, $product_desc, '', !empty($conf->global->MAIN_CHANGE_ORDER_CONCAT_DESCRIPTION));
874  }
875 
876  // Add custom code and origin country into description
877  if (empty($conf->global->MAIN_PRODUCT_DISABLE_CUSTOMCOUNTRYCODE) && (!empty($prod->customcode) || !empty($prod->country_code))) {
878  $tmptxt = '(';
879  // Define output language
880  if (!empty($conf->global->MAIN_MULTILANGS) && !empty($conf->global->PRODUIT_TEXTS_IN_THIRDPARTY_LANGUAGE)) {
881  $outputlangs = $langs;
882  $newlang = '';
883  if (empty($newlang) && GETPOST('lang_id', 'alpha')) {
884  $newlang = GETPOST('lang_id', 'alpha');
885  }
886  if (empty($newlang)) {
887  $newlang = $object->thirdparty->default_lang;
888  }
889  if (!empty($newlang)) {
890  $outputlangs = new Translate("", $conf);
891  $outputlangs->setDefaultLang($newlang);
892  $outputlangs->load('products');
893  }
894  if (!empty($prod->customcode)) {
895  $tmptxt .= $outputlangs->transnoentitiesnoconv("CustomCode").': '.$prod->customcode;
896  }
897  if (!empty($prod->customcode) && !empty($prod->country_code)) {
898  $tmptxt .= ' - ';
899  }
900  if (!empty($prod->country_code)) {
901  $tmptxt .= $outputlangs->transnoentitiesnoconv("CountryOrigin").': '.getCountry($prod->country_code, 0, $db, $outputlangs, 0);
902  }
903  } else {
904  if (!empty($prod->customcode)) {
905  $tmptxt .= $langs->transnoentitiesnoconv("CustomCode").': '.$prod->customcode;
906  }
907  if (!empty($prod->customcode) && !empty($prod->country_code)) {
908  $tmptxt .= ' - ';
909  }
910  if (!empty($prod->country_code)) {
911  $tmptxt .= $langs->transnoentitiesnoconv("CountryOrigin").': '.getCountry($prod->country_code, 0, $db, $langs, 0);
912  }
913  }
914  $tmptxt .= ')';
915  $desc = dol_concatdesc($desc, $tmptxt);
916  }
917 
918  $type = $prod->type;
919  $fk_unit = $prod->fk_unit;
920  } else {
921  $pu_ht = price2num($price_ht, 'MU');
922  $pu_ttc = price2num(GETPOST('price_ttc'), 'MU');
923  $tva_npr = (preg_match('/\*/', $tva_tx) ? 1 : 0);
924  $tva_tx = str_replace('*', '', $tva_tx);
925  $label = (GETPOST('product_label') ? GETPOST('product_label') : '');
926  $desc = $product_desc;
927  $type = GETPOST('type');
928  $fk_unit = GETPOST('units', 'alpha');
929  $pu_ht_devise = price2num($price_ht_devise, 'MU');
930  }
931 
932  // Margin
933  $fournprice = price2num(GETPOST('fournprice'.$predef) ? GETPOST('fournprice'.$predef) : '');
934  $buyingprice = price2num(GETPOST('buying_price'.$predef) != '' ? GETPOST('buying_price'.$predef) : ''); // If buying_price is '0', we muste keep this value
935 
936  // Local Taxes
937  $localtax1_tx = get_localtax($tva_tx, 1, $object->thirdparty);
938  $localtax2_tx = get_localtax($tva_tx, 2, $object->thirdparty);
939 
940  $desc = dol_htmlcleanlastbr($desc);
941 
942  $info_bits = 0;
943  if ($tva_npr) {
944  $info_bits |= 0x01;
945  }
946 
947  if (((!empty($conf->global->MAIN_USE_ADVANCED_PERMS) && empty($user->rights->produit->ignore_price_min_advance)) || empty($conf->global->MAIN_USE_ADVANCED_PERMS)) && (!empty($price_min) && (price2num($pu_ht) * (1 - price2num($remise_percent) / 100) < price2num($price_min)))) {
948  $mesg = $langs->trans("CantBeLessThanMinPrice", price(price2num($price_min, 'MU'), 0, $langs, 0, 0, - 1, $conf->currency));
949  setEventMessages($mesg, null, 'errors');
950  } else {
951  // Insert line
952  $result = $object->addline($desc, $pu_ht, $qty, $tva_tx, $localtax1_tx, $localtax2_tx, $idprod, $remise_percent, $info_bits, 0, $price_base_type, $pu_ttc, $date_start, $date_end, $type, min($rank, count($object->lines) + 1), 0, GETPOST('fk_parent_line'), $fournprice, $buyingprice, $label, $array_options, $fk_unit, '', 0, $pu_ht_devise);
953 
954  if ($result > 0) {
955  $ret = $object->fetch($object->id); // Reload to get new records
956  $object->fetch_thirdparty();
957 
958  if (empty($conf->global->MAIN_DISABLE_PDF_AUTOUPDATE)) {
959  // Define output language
960  $outputlangs = $langs;
961  $newlang = GETPOST('lang_id', 'alpha');
962  if (!empty($conf->global->MAIN_MULTILANGS) && empty($newlang)) {
963  $newlang = $object->thirdparty->default_lang;
964  }
965  if (!empty($newlang)) {
966  $outputlangs = new Translate("", $conf);
967  $outputlangs->setDefaultLang($newlang);
968  }
969 
970  $object->generateDocument($object->model_pdf, $outputlangs, $hidedetails, $hidedesc, $hideref);
971  }
972 
973  unset($_POST['prod_entry_mode']);
974 
975  unset($_POST['qty']);
976  unset($_POST['type']);
977  unset($_POST['remise_percent']);
978  unset($_POST['price_ht']);
979  unset($_POST['multicurrency_price_ht']);
980  unset($_POST['price_ttc']);
981  unset($_POST['tva_tx']);
982  unset($_POST['product_ref']);
983  unset($_POST['product_label']);
984  unset($_POST['product_desc']);
985  unset($_POST['fournprice']);
986  unset($_POST['buying_price']);
987  unset($_POST['np_marginRate']);
988  unset($_POST['np_markRate']);
989  unset($_POST['dp_desc']);
990  unset($_POST['idprod']);
991  unset($_POST['units']);
992 
993  unset($_POST['date_starthour']);
994  unset($_POST['date_startmin']);
995  unset($_POST['date_startsec']);
996  unset($_POST['date_startday']);
997  unset($_POST['date_startmonth']);
998  unset($_POST['date_startyear']);
999  unset($_POST['date_endhour']);
1000  unset($_POST['date_endmin']);
1001  unset($_POST['date_endsec']);
1002  unset($_POST['date_endday']);
1003  unset($_POST['date_endmonth']);
1004  unset($_POST['date_endyear']);
1005  } else {
1006  setEventMessages($object->error, $object->errors, 'errors');
1007  }
1008  }
1009  }
1010  } elseif ($action == 'updateline' && $usercancreate && GETPOST('save')) {
1011  // Update a line
1012  // Clean parameters
1013  $date_start = '';
1014  $date_end = '';
1015  $date_start = dol_mktime(GETPOST('date_starthour'), GETPOST('date_startmin'), GETPOST('date_startsec'), GETPOST('date_startmonth'), GETPOST('date_startday'), GETPOST('date_startyear'));
1016  $date_end = dol_mktime(GETPOST('date_endhour'), GETPOST('date_endmin'), GETPOST('date_endsec'), GETPOST('date_endmonth'), GETPOST('date_endday'), GETPOST('date_endyear'));
1017  $description = dol_htmlcleanlastbr(GETPOST('product_desc', 'restricthtml'));
1018  $pu_ht = price2num(GETPOST('price_ht'), '', 2);
1019  $vat_rate = (GETPOST('tva_tx') ? GETPOST('tva_tx', 'alpha') : 0);
1020  $pu_ht_devise = price2num(GETPOST('multicurrency_subprice'), '', 2);
1021 
1022  $qty = price2num(GETPOST('qty'), 'MS');
1023 
1024  // Define info_bits
1025  $info_bits = 0;
1026  if (preg_match('/\*/', $vat_rate)) {
1027  $info_bits |= 0x01;
1028  }
1029 
1030  // Define vat_rate
1031  $vat_rate = str_replace('*', '', $vat_rate);
1032  $localtax1_rate = get_localtax($vat_rate, 1, $object->thirdparty, $mysoc);
1033  $localtax2_rate = get_localtax($vat_rate, 2, $object->thirdparty, $mysoc);
1034 
1035  // Add buying price
1036  $fournprice = price2num(GETPOST('fournprice') ? GETPOST('fournprice') : '');
1037  $buyingprice = price2num(GETPOST('buying_price') != '' ? GETPOST('buying_price') : ''); // If buying_price is '0', we muste keep this value
1038 
1039  // Extrafields Lines
1040  $extralabelsline = $extrafields->fetch_name_optionals_label($object->table_element_line);
1041  $array_options = $extrafields->getOptionalsFromPost($object->table_element_line);
1042  // Unset extrafield POST Data
1043  if (is_array($extralabelsline)) {
1044  foreach ($extralabelsline as $key => $value) {
1045  unset($_POST["options_".$key]);
1046  }
1047  }
1048 
1049  // Define special_code for special lines
1050  $special_code = GETPOST('special_code');
1051  if (!GETPOST('qty')) {
1052  $special_code = 3;
1053  }
1054 
1055  $remise_percent = price2num(GETPOST('remise_percent'), '', 2);
1056 
1057  // Check minimum price
1058  $productid = GETPOST('productid', 'int');
1059  if (!empty($productid)) {
1060  $product = new Product($db);
1061  $product->fetch($productid);
1062 
1063  $type = $product->type;
1064 
1065  $price_min = $product->price_min;
1066  if ((!empty($conf->global->PRODUIT_MULTIPRICES) || !empty($conf->global->PRODUIT_CUSTOMER_PRICES_BY_QTY_MULTIPRICES)) && !empty($object->thirdparty->price_level)) {
1067  $price_min = $product->multiprices_min[$object->thirdparty->price_level];
1068  }
1069 
1070  $label = ((GETPOST('update_label') && GETPOST('product_label')) ? GETPOST('product_label') : '');
1071 
1072  if (((!empty($conf->global->MAIN_USE_ADVANCED_PERMS) && empty($user->rights->produit->ignore_price_min_advance)) || empty($conf->global->MAIN_USE_ADVANCED_PERMS)) && ($price_min && (price2num($pu_ht) * (1 - $remise_percent / 100) < price2num($price_min)))) {
1073  setEventMessages($langs->trans("CantBeLessThanMinPrice", price(price2num($price_min, 'MU'), 0, $langs, 0, 0, - 1, $conf->currency)), null, 'errors');
1074  $error++;
1075  $action = 'editline';
1076  }
1077  } else {
1078  $type = GETPOST('type');
1079  $label = (GETPOST('product_label') ? GETPOST('product_label') : '');
1080 
1081  // Check parameters
1082  if (GETPOST('type') < 0) {
1083  setEventMessages($langs->trans("ErrorFieldRequired", $langs->transnoentitiesnoconv("Type")), null, 'errors');
1084  $error++;
1085  $action = 'editline';
1086  }
1087  }
1088 
1089  if ($qty < 0) {
1090  setEventMessages($langs->trans('FieldCannotBeNegative', $langs->transnoentitiesnoconv('Qty')), null, 'errors');
1091  $error++;
1092  $action = 'editline';
1093  }
1094 
1095  if (!$error) {
1096  if (empty($user->rights->margins->creer)) {
1097  foreach ($object->lines as &$line) {
1098  if ($line->id == GETPOST('lineid', 'int')) {
1099  $fournprice = $line->fk_fournprice;
1100  $buyingprice = $line->pa_ht;
1101  break;
1102  }
1103  }
1104  }
1105  $result = $object->updateline(GETPOST('lineid', 'int'), $description, $pu_ht, $qty, $remise_percent, $vat_rate, $localtax1_rate, $localtax2_rate, 'HT', $info_bits, $date_start, $date_end, $type, GETPOST('fk_parent_line'), 0, $fournprice, $buyingprice, $label, $special_code, $array_options, GETPOST('units'), $pu_ht_devise);
1106 
1107  if ($result >= 0) {
1108  if (empty($conf->global->MAIN_DISABLE_PDF_AUTOUPDATE)) {
1109  // Define output language
1110  $outputlangs = $langs;
1111  $newlang = '';
1112  if ($conf->global->MAIN_MULTILANGS && empty($newlang) && GETPOST('lang_id', 'aZ09')) {
1113  $newlang = GETPOST('lang_id', 'aZ09');
1114  }
1115  if ($conf->global->MAIN_MULTILANGS && empty($newlang)) {
1116  $newlang = $object->thirdparty->default_lang;
1117  }
1118  if (!empty($newlang)) {
1119  $outputlangs = new Translate("", $conf);
1120  $outputlangs->setDefaultLang($newlang);
1121  }
1122 
1123  $ret = $object->fetch($object->id); // Reload to get new records
1124  $object->generateDocument($object->model_pdf, $outputlangs, $hidedetails, $hidedesc, $hideref);
1125  }
1126 
1127  unset($_POST['qty']);
1128  unset($_POST['type']);
1129  unset($_POST['productid']);
1130  unset($_POST['remise_percent']);
1131  unset($_POST['price_ht']);
1132  unset($_POST['multicurrency_price_ht']);
1133  unset($_POST['price_ttc']);
1134  unset($_POST['tva_tx']);
1135  unset($_POST['product_ref']);
1136  unset($_POST['product_label']);
1137  unset($_POST['product_desc']);
1138  unset($_POST['fournprice']);
1139  unset($_POST['buying_price']);
1140 
1141  unset($_POST['date_starthour']);
1142  unset($_POST['date_startmin']);
1143  unset($_POST['date_startsec']);
1144  unset($_POST['date_startday']);
1145  unset($_POST['date_startmonth']);
1146  unset($_POST['date_startyear']);
1147  unset($_POST['date_endhour']);
1148  unset($_POST['date_endmin']);
1149  unset($_POST['date_endsec']);
1150  unset($_POST['date_endday']);
1151  unset($_POST['date_endmonth']);
1152  unset($_POST['date_endyear']);
1153  } else {
1154  setEventMessages($object->error, $object->errors, 'errors');
1155  }
1156  }
1157  } elseif ($action == 'updateline' && $usercancreate && GETPOST('cancel', 'alpha')) {
1158  header('Location: '.$_SERVER['PHP_SELF'].'?id='.$object->id); // Pour reaffichage de la fiche en cours d'edition
1159  exit();
1160  } elseif ($action == 'confirm_validate' && $confirm == 'yes' && $usercanvalidate) {
1161  $idwarehouse = GETPOST('idwarehouse', 'int');
1162 
1163  $qualified_for_stock_change = 0;
1164  if (empty($conf->global->STOCK_SUPPORTS_SERVICES)) {
1165  $qualified_for_stock_change = $object->hasProductsOrServices(2);
1166  } else {
1167  $qualified_for_stock_change = $object->hasProductsOrServices(1);
1168  }
1169 
1170  // Check parameters
1171  if (!empty($conf->stock->enabled) && !empty($conf->global->STOCK_CALCULATE_ON_VALIDATE_ORDER) && $qualified_for_stock_change) {
1172  if (!$idwarehouse || $idwarehouse == -1) {
1173  $error++;
1174  setEventMessages($langs->trans('ErrorFieldRequired', $langs->transnoentitiesnoconv("Warehouse")), null, 'errors');
1175  $action = '';
1176  }
1177  }
1178 
1179  if (!$error) {
1180  $locationTarget = '';
1181  $db->begin();
1182  $result = $object->valid($user, $idwarehouse);
1183  if ($result >= 0) {
1184  $error = 0;
1185  $deposit = null;
1186 
1187  $deposit_percent_from_payment_terms = getDictionaryValue('c_payment_term', 'deposit_percent', $object->cond_reglement_id);
1188 
1189  if (
1190  GETPOST('generate_deposit', 'alpha') == 'on' && ! empty($deposit_percent_from_payment_terms)
1191  && ! empty($conf->facture->enabled) && ! empty($user->rights->facture->creer)
1192  ) {
1193  require_once DOL_DOCUMENT_ROOT . '/compta/facture/class/facture.class.php';
1194 
1195  $date = dol_mktime(0, 0, 0, GETPOST('datefmonth', 'int'), GETPOST('datefday', 'int'), GETPOST('datefyear', 'int'));
1196  $forceFields = array();
1197 
1198  if (GETPOSTISSET('date_pointoftax')) {
1199  $forceFields['date_pointoftax'] = dol_mktime(0, 0, 0, GETPOST('date_pointoftaxmonth', 'int'), GETPOST('date_pointoftaxday', 'int'), GETPOST('date_pointoftaxyear', 'int'));
1200  }
1201 
1202  $deposit = Facture::createDepositFromOrigin($object, $date, GETPOST('cond_reglement_id', 'int'), $user, 0, GETPOST('validate_generated_deposit', 'alpha') == 'on', $forceFields);
1203 
1204  if ($deposit) {
1205  setEventMessage('DepositGenerated');
1206  $locationTarget = DOL_URL_ROOT . '/compta/facture/card.php?id=' . $deposit->id;
1207  } else {
1208  $error++;
1209  setEventMessages($object->error, $object->errors, 'errors');
1210  }
1211  }
1212 
1213  // Define output language
1214  if (! $error) {
1215  $db->commit();
1216 
1217  if (empty($conf->global->MAIN_DISABLE_PDF_AUTOUPDATE)) {
1218  $outputlangs = $langs;
1219  $newlang = '';
1220  if (getDolGlobalInt('MAIN_MULTILANGS') && empty($newlang) && GETPOST('lang_id', 'aZ09')) {
1221  $newlang = GETPOST('lang_id', 'aZ09');
1222  }
1223  if (getDolGlobalInt('MAIN_MULTILANGS') && empty($newlang)) {
1224  $newlang = $object->thirdparty->default_lang;
1225  }
1226  if (!empty($newlang)) {
1227  $outputlangs = new Translate("", $conf);
1228  $outputlangs->setDefaultLang($newlang);
1229  }
1230  $model = $object->model_pdf;
1231  $ret = $object->fetch($id); // Reload to get new records
1232 
1233  $object->generateDocument($model, $outputlangs, $hidedetails, $hidedesc, $hideref);
1234 
1235  if ($deposit) {
1236  $deposit->fetch($deposit->id); // Reload to get new records
1237  $deposit->generateDocument($deposit->model_pdf, $outputlangs, $hidedetails, $hidedesc, $hideref);
1238  }
1239  }
1240 
1241  if ($locationTarget) {
1242  header('Location: ' . $locationTarget);
1243  exit;
1244  }
1245  } else {
1246  $db->rollback();
1247  }
1248  } else {
1249  $db->rollback();
1250  setEventMessages($object->error, $object->errors, 'errors');
1251  }
1252  }
1253  } elseif ($action == 'confirm_modif' && $usercancreate) {
1254  // Go back to draft status
1255  $idwarehouse = GETPOST('idwarehouse');
1256 
1257  $qualified_for_stock_change = 0;
1258  if (empty($conf->global->STOCK_SUPPORTS_SERVICES)) {
1259  $qualified_for_stock_change = $object->hasProductsOrServices(2);
1260  } else {
1261  $qualified_for_stock_change = $object->hasProductsOrServices(1);
1262  }
1263 
1264  // Check parameters
1265  if (!empty($conf->stock->enabled) && !empty($conf->global->STOCK_CALCULATE_ON_VALIDATE_ORDER) && $qualified_for_stock_change) {
1266  if (!$idwarehouse || $idwarehouse == -1) {
1267  $error++;
1268  setEventMessages($langs->trans('ErrorFieldRequired', $langs->transnoentitiesnoconv("Warehouse")), null, 'errors');
1269  $action = '';
1270  }
1271  }
1272 
1273  if (!$error) {
1274  $result = $object->setDraft($user, $idwarehouse);
1275  if ($result >= 0) {
1276  // Define output language
1277  if (empty($conf->global->MAIN_DISABLE_PDF_AUTOUPDATE)) {
1278  $outputlangs = $langs;
1279  $newlang = '';
1280  if ($conf->global->MAIN_MULTILANGS && empty($newlang) && GETPOST('lang_id', 'aZ09')) {
1281  $newlang = GETPOST('lang_id', 'aZ09');
1282  }
1283  if ($conf->global->MAIN_MULTILANGS && empty($newlang)) {
1284  $newlang = $object->thirdparty->default_lang;
1285  }
1286  if (!empty($newlang)) {
1287  $outputlangs = new Translate("", $conf);
1288  $outputlangs->setDefaultLang($newlang);
1289  }
1290  $model = $object->model_pdf;
1291  $ret = $object->fetch($id); // Reload to get new records
1292 
1293  $object->generateDocument($model, $outputlangs, $hidedetails, $hidedesc, $hideref);
1294  }
1295  }
1296  }
1297  } elseif ($action == 'confirm_shipped' && $confirm == 'yes' && $usercanclose) {
1298  $result = $object->cloture($user);
1299  if ($result < 0) {
1300  setEventMessages($object->error, $object->errors, 'errors');
1301  }
1302  } elseif ($action == 'confirm_cancel' && $confirm == 'yes' && $usercanvalidate) {
1303  $idwarehouse = GETPOST('idwarehouse', 'int');
1304 
1305  $qualified_for_stock_change = 0;
1306  if (empty($conf->global->STOCK_SUPPORTS_SERVICES)) {
1307  $qualified_for_stock_change = $object->hasProductsOrServices(2);
1308  } else {
1309  $qualified_for_stock_change = $object->hasProductsOrServices(1);
1310  }
1311 
1312  // Check parameters
1313  if (!empty($conf->stock->enabled) && !empty($conf->global->STOCK_CALCULATE_ON_VALIDATE_ORDER) && $qualified_for_stock_change) {
1314  if (!$idwarehouse || $idwarehouse == -1) {
1315  $error++;
1316  setEventMessages($langs->trans('ErrorFieldRequired', $langs->transnoentitiesnoconv("Warehouse")), null, 'errors');
1317  $action = '';
1318  }
1319  }
1320 
1321  if (!$error) {
1322  $result = $object->cancel($idwarehouse);
1323 
1324  if ($result < 0) {
1325  setEventMessages($object->error, $object->errors, 'errors');
1326  }
1327  }
1328  }
1329 
1330  if ($action == 'update_extras') {
1331  $object->oldcopy = dol_clone($object);
1332 
1333  // Fill array 'array_options' with data from update form
1334  $ret = $extrafields->setOptionalsFromPost(null, $object, GETPOST('attribute', 'restricthtml'));
1335  if ($ret < 0) {
1336  $error++;
1337  }
1338 
1339  if (!$error) {
1340  // Actions on extra fields
1341  $result = $object->insertExtraFields('ORDER_MODIFY');
1342  if ($result < 0) {
1343  setEventMessages($object->error, $object->errors, 'errors');
1344  $error++;
1345  }
1346  }
1347 
1348  if ($error) {
1349  $action = 'edit_extras';
1350  }
1351  }
1352 
1353  // add lines from objectlinked
1354  if ($action == 'import_lines_from_object'
1355  && $usercancreate
1356  && $object->statut == Commande::STATUS_DRAFT
1357  ) {
1358  $fromElement = GETPOST('fromelement');
1359  $fromElementid = GETPOST('fromelementid');
1360  $importLines = GETPOST('line_checkbox');
1361 
1362  if (!empty($importLines) && is_array($importLines) && !empty($fromElement) && ctype_alpha($fromElement) && !empty($fromElementid)) {
1363  if ($fromElement == 'commande') {
1364  dol_include_once('/'.$fromElement.'/class/'.$fromElement.'.class.php');
1365  $lineClassName = 'OrderLine';
1366  } elseif ($fromElement == 'propal') {
1367  dol_include_once('/comm/'.$fromElement.'/class/'.$fromElement.'.class.php');
1368  $lineClassName = 'PropaleLigne';
1369  }
1370  $nextRang = count($object->lines) + 1;
1371  $importCount = 0;
1372  $error = 0;
1373  foreach ($importLines as $lineId) {
1374  $lineId = intval($lineId);
1375  $originLine = new $lineClassName($db);
1376  if (intval($fromElementid) > 0 && $originLine->fetch($lineId) > 0) {
1377  $originLine->fetch_optionals();
1378  $desc = $originLine->desc;
1379  $pu_ht = $originLine->subprice;
1380  $qty = $originLine->qty;
1381  $txtva = $originLine->tva_tx;
1382  $txlocaltax1 = $originLine->localtax1_tx;
1383  $txlocaltax2 = $originLine->localtax2_tx;
1384  $fk_product = $originLine->fk_product;
1385  $remise_percent = $originLine->remise_percent;
1386  $date_start = $originLine->date_start;
1387  $date_end = $originLine->date_end;
1388  $ventil = 0;
1389  $info_bits = $originLine->info_bits;
1390  $fk_remise_except = $originLine->fk_remise_except;
1391  $price_base_type = 'HT';
1392  $pu_ttc = 0;
1393  $type = $originLine->product_type;
1394  $rang = $nextRang++;
1395  $special_code = $originLine->special_code;
1396  $origin = $originLine->element;
1397  $origin_id = $originLine->id;
1398  $fk_parent_line = 0;
1399  $fk_fournprice = $originLine->fk_fournprice;
1400  $pa_ht = $originLine->pa_ht;
1401  $label = $originLine->label;
1402  $array_options = $originLine->array_options;
1403  $situation_percent = 100;
1404  $fk_prev_id = '';
1405  $fk_unit = $originLine->fk_unit;
1406  $pu_ht_devise = $originLine->multicurrency_subprice;
1407 
1408  $res = $object->addline($desc, $pu_ht, $qty, $txtva, $txlocaltax1, $txlocaltax2, $fk_product, $remise_percent, $info_bits, $fk_remise_except, $price_base_type, $pu_ttc, $date_start, $date_end, $type, $rang, $special_code, $fk_parent_line, $fk_fournprice, $pa_ht, $label, $array_options, $fk_unit, $origin, $origin_id, $pu_ht_devise);
1409 
1410  if ($res > 0) {
1411  $importCount++;
1412  } else {
1413  $error++;
1414  }
1415  } else {
1416  $error++;
1417  }
1418  }
1419 
1420  if ($error) {
1421  setEventMessages($langs->trans('ErrorsOnXLines', $error), null, 'errors');
1422  }
1423  }
1424  }
1425 
1426  // Actions when printing a doc from card
1427  include DOL_DOCUMENT_ROOT.'/core/actions_printing.inc.php';
1428 
1429  // Actions to build doc
1430  $upload_dir = !empty($conf->commande->multidir_output[$object->entity])?$conf->commande->multidir_output[$object->entity]:$conf->commande->dir_output;
1431  $permissiontoadd = $usercancreate;
1432  include DOL_DOCUMENT_ROOT.'/core/actions_builddoc.inc.php';
1433 
1434  // Actions to send emails
1435  $triggersendname = 'ORDER_SENTBYMAIL';
1436  $paramname = 'id';
1437  $autocopy = 'MAIN_MAIL_AUTOCOPY_ORDER_TO'; // used to know the automatic BCC to add
1438  $trackid = 'ord'.$object->id;
1439  include DOL_DOCUMENT_ROOT.'/core/actions_sendmails.inc.php';
1440 
1441 
1442  if (!$error && !empty($conf->global->MAIN_DISABLE_CONTACTS_TAB) && $usercancreate) {
1443  if ($action == 'addcontact') {
1444  if ($object->id > 0) {
1445  $contactid = (GETPOST('userid') ? GETPOST('userid') : GETPOST('contactid'));
1446  $typeid = (GETPOST('typecontact') ? GETPOST('typecontact') : GETPOST('type'));
1447  $result = $object->add_contact($contactid, $typeid, GETPOST("source", 'aZ09'));
1448  }
1449 
1450  if ($result >= 0) {
1451  header("Location: ".$_SERVER['PHP_SELF']."?id=".$object->id);
1452  exit();
1453  } else {
1454  if ($object->error == 'DB_ERROR_RECORD_ALREADY_EXISTS') {
1455  $langs->load("errors");
1456  setEventMessages($langs->trans("ErrorThisContactIsAlreadyDefinedAsThisType"), null, 'errors');
1457  } else {
1458  setEventMessages($object->error, $object->errors, 'errors');
1459  }
1460  }
1461  } elseif ($action == 'swapstatut') {
1462  // bascule du statut d'un contact
1463  if ($object->id > 0) {
1464  $result = $object->swapContactStatus(GETPOST('ligne', 'int'));
1465  } else {
1466  dol_print_error($db);
1467  }
1468  } elseif ($action == 'deletecontact') {
1469  // Efface un contact
1470  $result = $object->delete_contact($lineid);
1471 
1472  if ($result >= 0) {
1473  header("Location: ".$_SERVER['PHP_SELF']."?id=".$object->id);
1474  exit();
1475  } else {
1476  dol_print_error($db);
1477  }
1478  }
1479  }
1480 }
1481 
1482 
1483 /*
1484  * View
1485  */
1486 
1487 $title = $langs->trans('Order')." - ".$langs->trans('Card');
1488 $help_url = 'EN:Customers_Orders|FR:Commandes_Clients|ES:Pedidos de clientes|DE:Modul_Kundenaufträge';
1489 llxHeader('', $title, $help_url);
1490 
1491 $form = new Form($db);
1492 $formfile = new FormFile($db);
1493 $formorder = new FormOrder($db);
1494 $formmargin = new FormMargin($db);
1495 if (!empty($conf->project->enabled)) {
1496  $formproject = new FormProjets($db);
1497 }
1498 
1499 // Mode creation
1500 if ($action == 'create' && $usercancreate) {
1501  print load_fiche_titre($langs->trans('CreateOrder'), '', 'order');
1502 
1503  $soc = new Societe($db);
1504  if ($socid > 0) {
1505  $res = $soc->fetch($socid);
1506  }
1507 
1508  $remise_absolue = 0;
1509 
1510  $currency_code = $conf->currency;
1511 
1512  $cond_reglement_id = GETPOST('cond_reglement_id', 'int');
1513  $deposit_percent = GETPOST('cond_reglement_id_deposit_percent', 'alpha');
1514  $mode_reglement_id = GETPOST('mode_reglement_id', 'int');
1515 
1516  if (!empty($origin) && !empty($originid)) {
1517  // Parse element/subelement (ex: project_task)
1518  $element = $subelement = $origin;
1519  $regs = array();
1520  if (preg_match('/^([^_]+)_([^_]+)/i', $origin, $regs)) {
1521  $element = $regs[1];
1522  $subelement = $regs[2];
1523  }
1524 
1525  if ($element == 'project') {
1526  $projectid = $originid;
1527 
1528  if (!$cond_reglement_id) {
1529  $cond_reglement_id = $soc->cond_reglement_id;
1530  }
1531  if (!$deposit_percent) {
1532  $deposit_percent = $soc->deposit_percent;
1533  }
1534  if (!$mode_reglement_id) {
1535  $mode_reglement_id = $soc->mode_reglement_id;
1536  }
1537  if (!$remise_percent) {
1538  $remise_percent = $soc->remise_percent;
1539  }
1540  if (!$dateorder) {
1541  // Do not set 0 here (0 for a date is 1970)
1542  $dateorder = (empty($dateinvoice) ? (empty($conf->global->MAIN_AUTOFILL_DATE_ODER) ?-1 : '') : $dateorder);
1543  }
1544  } else {
1545  // For compatibility
1546  if ($element == 'order' || $element == 'commande') {
1547  $element = $subelement = 'commande';
1548  } elseif ($element == 'propal') {
1549  $element = 'comm/propal';
1550  $subelement = 'propal';
1551  } elseif ($element == 'contract') {
1552  $element = $subelement = 'contrat';
1553  }
1554 
1555  dol_include_once('/'.$element.'/class/'.$subelement.'.class.php');
1556 
1557  $classname = ucfirst($subelement);
1558  $objectsrc = new $classname($db);
1559  $objectsrc->fetch($originid);
1560  if (empty($objectsrc->lines) && method_exists($objectsrc, 'fetch_lines')) {
1561  $objectsrc->fetch_lines();
1562  }
1563  $objectsrc->fetch_thirdparty();
1564 
1565  // Replicate extrafields
1566  $objectsrc->fetch_optionals();
1567  $object->array_options = $objectsrc->array_options;
1568 
1569  $projectid = (!empty($objectsrc->fk_project) ? $objectsrc->fk_project : '');
1570  $ref_client = (!empty($objectsrc->ref_client) ? $objectsrc->ref_client : '');
1571 
1572  $soc = $objectsrc->thirdparty;
1573  $cond_reglement_id = (!empty($objectsrc->cond_reglement_id) ? $objectsrc->cond_reglement_id : (!empty($soc->cond_reglement_id) ? $soc->cond_reglement_id : 0)); // TODO maybe add default value option
1574  $deposit_percent = (!empty($objectsrc->deposit_percent) ? $objectsrc->deposit_percent : (!empty($soc->deposit_percent) ? $soc->deposit_percent : null));
1575  $mode_reglement_id = (!empty($objectsrc->mode_reglement_id) ? $objectsrc->mode_reglement_id : (!empty($soc->mode_reglement_id) ? $soc->mode_reglement_id : 0));
1576  $fk_account = (!empty($objectsrc->fk_account) ? $objectsrc->fk_account : (!empty($soc->fk_account) ? $soc->fk_account : 0));
1577  $availability_id = (!empty($objectsrc->availability_id) ? $objectsrc->availability_id : 0);
1578  $shipping_method_id = (!empty($objectsrc->shipping_method_id) ? $objectsrc->shipping_method_id : (!empty($soc->shipping_method_id) ? $soc->shipping_method_id : 0));
1579  $warehouse_id = (!empty($objectsrc->warehouse_id) ? $objectsrc->warehouse_id : (!empty($soc->warehouse_id) ? $soc->warehouse_id : 0));
1580  $demand_reason_id = (!empty($objectsrc->demand_reason_id) ? $objectsrc->demand_reason_id : (!empty($soc->demand_reason_id) ? $soc->demand_reason_id : 0));
1581  $remise_percent = (!empty($objectsrc->remise_percent) ? $objectsrc->remise_percent : (!empty($soc->remise_percent) ? $soc->remise_percent : 0));
1582  $remise_absolue = (!empty($objectsrc->remise_absolue) ? $objectsrc->remise_absolue : (!empty($soc->remise_absolue) ? $soc->remise_absolue : 0));
1583  $dateorder = empty($conf->global->MAIN_AUTOFILL_DATE_ORDER) ? -1 : '';
1584 
1585  $date_delivery = (!empty($objectsrc->delivery_date) ? $objectsrc->delivery_date : '');
1586  if (empty($date_delivery)) {
1587  $date_delivery = (!empty($objectsrc->date_livraison) ? $objectsrc->date_livraison : '');
1588  }
1589 
1590  if (!empty($conf->multicurrency->enabled)) {
1591  if (!empty($objectsrc->multicurrency_code)) {
1592  $currency_code = $objectsrc->multicurrency_code;
1593  }
1594  if (!empty($conf->global->MULTICURRENCY_USE_ORIGIN_TX) && !empty($objectsrc->multicurrency_tx)) {
1595  $currency_tx = $objectsrc->multicurrency_tx;
1596  }
1597  }
1598 
1599  $note_private = $object->getDefaultCreateValueFor('note_private', (!empty($objectsrc->note_private) ? $objectsrc->note_private : null));
1600  $note_public = $object->getDefaultCreateValueFor('note_public', (!empty($objectsrc->note_public) ? $objectsrc->note_public : null));
1601 
1602  // Object source contacts list
1603  $srccontactslist = $objectsrc->liste_contact(-1, 'external', 1);
1604  }
1605  } else {
1606  $cond_reglement_id = $soc->cond_reglement_id;
1607  $deposit_percent = $soc->deposit_percent;
1608  $mode_reglement_id = $soc->mode_reglement_id;
1609  $fk_account = $soc->fk_account;
1610  $availability_id = 0;
1611  $shipping_method_id = $soc->shipping_method_id;
1612  $warehouse_id = $soc->fk_warehouse;
1613  $demand_reason_id = $soc->demand_reason_id;
1614  $remise_percent = $soc->remise_percent;
1615  $remise_absolue = 0;
1616  $dateorder = empty($conf->global->MAIN_AUTOFILL_DATE_ORDER) ?-1 : '';
1617 
1618  if (!empty($conf->multicurrency->enabled) && !empty($soc->multicurrency_code)) {
1619  $currency_code = $soc->multicurrency_code;
1620  }
1621 
1622  $note_private = $object->getDefaultCreateValueFor('note_private');
1623  $note_public = $object->getDefaultCreateValueFor('note_public');
1624  }
1625 
1626  //Warehouse default if null
1627  if ($soc->fk_warehouse > 0) {
1628  $warehouse_id = $soc->fk_warehouse;
1629  }
1630  if (!empty($conf->stock->enabled) && empty($warehouse_id) && !empty($conf->global->WAREHOUSE_ASK_WAREHOUSE_DURING_ORDER)) {
1631  if (empty($object->warehouse_id) && !empty($conf->global->MAIN_DEFAULT_WAREHOUSE)) {
1632  $warehouse_id = $conf->global->MAIN_DEFAULT_WAREHOUSE;
1633  }
1634  if (empty($object->warehouse_id) && !empty($conf->global->MAIN_DEFAULT_WAREHOUSE_USER)) {
1635  $warehouse_id = $user->fk_warehouse;
1636  }
1637  }
1638 
1639  print '<form name="crea_commande" action="'.$_SERVER["PHP_SELF"].'" method="POST">';
1640  print '<input type="hidden" name="token" value="'.newToken().'">';
1641  print '<input type="hidden" name="action" value="add">';
1642  print '<input type="hidden" name="socid" value="'.$soc->id.'">'."\n";
1643  print '<input type="hidden" name="remise_percent" value="'.$soc->remise_percent.'">';
1644  print '<input type="hidden" name="origin" value="'.$origin.'">';
1645  print '<input type="hidden" name="originid" value="'.$originid.'">';
1646  if (!empty($currency_tx)) {
1647  print '<input type="hidden" name="originmulticurrency_tx" value="'.$currency_tx.'">';
1648  }
1649 
1650  print dol_get_fiche_head('');
1651 
1652  print '<table class="border centpercent">';
1653 
1654  // Reference
1655  print '<tr><td class="titlefieldcreate fieldrequired">'.$langs->trans('Ref').'</td><td>'.$langs->trans("Draft").'</td></tr>';
1656 
1657  // Reference client
1658  print '<tr><td>'.$langs->trans('RefCustomer').'</td><td>';
1659  if (!empty($conf->global->MAIN_USE_PROPAL_REFCLIENT_FOR_ORDER) && !empty($origin) && !empty($originid)) {
1660  print '<input type="text" name="ref_client" value="'.$ref_client.'"></td>';
1661  } else {
1662  print '<input type="text" name="ref_client" value="'.GETPOST('ref_client').'"></td>';
1663  }
1664  print '</tr>';
1665 
1666  // Thirdparty
1667  print '<tr>';
1668  print '<td class="fieldrequired">'.$langs->trans('Customer').'</td>';
1669  if ($socid > 0) {
1670  print '<td>';
1671  print $soc->getNomUrl(1, 'customer');
1672  print '<input type="hidden" name="socid" value="'.$soc->id.'">';
1673  print '</td>';
1674  } else {
1675  print '<td>';
1676  print img_picto('', 'company').$form->select_company('', 'socid', '((s.client = 1 OR s.client = 2 OR s.client = 3) AND s.status=1)', 'SelectThirdParty', 0, 0, null, 0, 'minwidth175 maxwidth500 widthcentpercentminusxx');
1677  // reload page to retrieve customer informations
1678  if (empty($conf->global->RELOAD_PAGE_ON_CUSTOMER_CHANGE_DISABLED)) {
1679  print '<script type="text/javascript">
1680  $(document).ready(function() {
1681  $("#socid").change(function() {
1682  console.log("We have changed the company - Reload page");
1683  var socid = $(this).val();
1684  // reload page
1685  $("input[name=action]").val("create");
1686  $("form[name=crea_commande]").submit();
1687  });
1688  });
1689  </script>';
1690  }
1691  print ' <a href="'.DOL_URL_ROOT.'/societe/card.php?action=create&client=3&fournisseur=0&backtopage='.urlencode($_SERVER["PHP_SELF"].'?action=create').'"><span class="fa fa-plus-circle valignmiddle paddingleft" title="'.$langs->trans("AddThirdParty").'"></span></a>';
1692  print '</td>';
1693  }
1694  print '</tr>'."\n";
1695 
1696  // Contact of order
1697  if ($socid > 0) {
1698  // Contacts (ask contact only if thirdparty already defined).
1699  print "<tr><td>".$langs->trans("DefaultContact").'</td><td>';
1700  print img_picto('', 'contact', 'class="pictofixedwidth"');
1701  print $form->selectcontacts($soc->id, $contactid, 'contactid', 1, !empty($srccontactslist)?$srccontactslist:"", '', 1, 'maxwidth200 widthcentpercentminusx');
1702  print '</td></tr>';
1703 
1704  // Ligne info remises tiers
1705  print '<tr><td>'.$langs->trans('Discounts').'</td><td>';
1706 
1707  $absolute_discount = $soc->getAvailableDiscounts();
1708 
1709  $thirdparty = $soc;
1710  $discount_type = 0;
1711  $backtopage = urlencode($_SERVER["PHP_SELF"].'?socid='.$thirdparty->id.'&action='.$action.'&origin='.GETPOST('origin').'&originid='.GETPOST('originid'));
1712  include DOL_DOCUMENT_ROOT.'/core/tpl/object_discounts.tpl.php';
1713 
1714  print '</td></tr>';
1715  }
1716 
1717  // Date
1718  print '<tr><td class="fieldrequired">'.$langs->trans('Date').'</td><td>';
1719  print $form->selectDate('', 're', '', '', '', "crea_commande", 1, 1); // Always autofill date with current date
1720  print '</td></tr>';
1721 
1722  // Date delivery planned
1723  print '<tr><td>'.$langs->trans("DateDeliveryPlanned").'</td>';
1724  print '<td colspan="3">';
1725  $date_delivery = ($date_delivery ? $date_delivery : $object->delivery_date);
1726  print $form->selectDate($date_delivery ? $date_delivery : -1, 'liv_', 1, 1, 1);
1727  print "</td>\n";
1728  print '</tr>';
1729 
1730  // Delivery delay
1731  print '<tr class="fielddeliverydelay"><td>'.$langs->trans('AvailabilityPeriod').'</td><td>';
1732  print img_picto('', 'clock', 'class="pictofixedwidth"');
1733  $form->selectAvailabilityDelay($availability_id, 'availability_id', '', 1, 'maxwidth200 widthcentpercentminusx');
1734  print '</td></tr>';
1735 
1736  // Terms of payment
1737  print '<tr><td class="nowrap">'.$langs->trans('PaymentConditionsShort').'</td><td>';
1738  print img_picto('', 'payment', 'class="pictofixedwidth"');
1739  $form->select_conditions_paiements($cond_reglement_id, 'cond_reglement_id', 1, 1, 0, 'maxwidth200 widthcentpercentminusx', $deposit_percent);
1740  print '</td></tr>';
1741 
1742  // Payment mode
1743  print '<tr><td>'.$langs->trans('PaymentMode').'</td><td>';
1744  print img_picto('', 'bank', 'class="pictofixedwidth"');
1745  $form->select_types_paiements($mode_reglement_id, 'mode_reglement_id', 'CRDT', 0, 1, 0, 0, 1, 'maxwidth200 widthcentpercentminusx');
1746  print '</td></tr>';
1747 
1748  // Bank Account
1749  if (!empty($conf->global->BANK_ASK_PAYMENT_BANK_DURING_ORDER) && !empty($conf->banque->enabled)) {
1750  print '<tr><td>'.$langs->trans('BankAccount').'</td><td>';
1751  print img_picto('', 'bank_account', 'class="pictofixedwidth"').$form->select_comptes($fk_account, 'fk_account', 0, '', 1, '', 0, 'maxwidth200 widthcentpercentminusx', 1);
1752  print '</td></tr>';
1753  }
1754 
1755  // Shipping Method
1756  if (isModEnabled('expedition')) {
1757  print '<tr><td>'.$langs->trans('SendingMethod').'</td><td>';
1758  print img_picto('', 'object_dolly', 'class="pictofixedwidth"').$form->selectShippingMethod($shipping_method_id, 'shipping_method_id', '', 1, '', 0, 'maxwidth200 widthcentpercentminusx');
1759  print '</td></tr>';
1760  }
1761 
1762  // Warehouse
1763  if (!empty($conf->stock->enabled) && !empty($conf->global->WAREHOUSE_ASK_WAREHOUSE_DURING_ORDER)) {
1764  require_once DOL_DOCUMENT_ROOT.'/product/class/html.formproduct.class.php';
1765  $formproduct = new FormProduct($db);
1766  print '<tr><td>'.$langs->trans('Warehouse').'</td><td>';
1767  print img_picto('', 'stock', 'class="pictofixedwidth"').$formproduct->selectWarehouses($warehouse_id, 'warehouse_id', '', 1, 0, 0, '', 0, 0, array(), 'maxwidth500 widthcentpercentminusxx');
1768  print '</td></tr>';
1769  }
1770 
1771  // Source / Channel - What trigger creation
1772  print '<tr><td>'.$langs->trans('Channel').'</td><td>';
1773  print img_picto('', 'question', 'class="pictofixedwidth"');
1774  $form->selectInputReason($demand_reason_id, 'demand_reason_id', '', 1, 'maxwidth200 widthcentpercentminusx');
1775  print '</td></tr>';
1776 
1777  // TODO How record was recorded OrderMode (llx_c_input_method)
1778 
1779  // Project
1780  if (!empty($conf->project->enabled)) {
1781  $langs->load("projects");
1782  print '<tr>';
1783  print '<td>'.$langs->trans("Project").'</td><td>';
1784  print img_picto('', 'project', 'class="pictofixedwidth"').$formproject->select_projects(($soc->id > 0 ? $soc->id : -1), $projectid, 'projectid', 0, 0, 1, 0, 0, 0, 0, '', 1, 0, 'maxwidth500 widthcentpercentminusxx');
1785  print ' <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="fa fa-plus-circle valignmiddle" title="'.$langs->trans("AddProject").'"></span></a>';
1786  print '</td>';
1787  print '</tr>';
1788  }
1789 
1790  // Incoterms
1791  if (!empty($conf->incoterm->enabled)) {
1792  print '<tr>';
1793  print '<td><label for="incoterm_id">'.$form->textwithpicto($langs->trans("IncotermLabel"), $objectsrc->label_incoterms, 1).'</label></td>';
1794  print '<td class="maxwidthonsmartphone">';
1795  $incoterm_id = GETPOST('incoterm_id');
1796  $incoterm_location = GETPOST('location_incoterms');
1797  if (empty($incoterm_id)) {
1798  $incoterm_id = (!empty($objectsrc->fk_incoterms) ? $objectsrc->fk_incoterms : $soc->fk_incoterms);
1799  $incoterm_location = (!empty($objectsrc->location_incoterms) ? $objectsrc->location_incoterms : $soc->location_incoterms);
1800  }
1801  print $form->select_incoterms($incoterm_id, $incoterm_location);
1802  print '</td></tr>';
1803  }
1804 
1805  // Other attributes
1806  $parameters = array();
1807  if (!empty($origin) && !empty($originid) && is_object($objectsrc)) {
1808  $parameters['objectsrc'] = $objectsrc;
1809  }
1810  $parameters['socid'] = $socid;
1811 
1812  // Note that $action and $object may be modified by hook
1813  $reshook = $hookmanager->executeHooks('formObjectOptions', $parameters, $object, $action);
1814  print $hookmanager->resPrint;
1815  if (empty($reshook)) {
1816  if (!empty($conf->global->THIRDPARTY_PROPAGATE_EXTRAFIELDS_TO_ORDER) && !empty($soc->id)) {
1817  // copy from thirdparty
1818  $tpExtrafields = new Extrafields($db);
1819  $tpExtrafieldLabels = $tpExtrafields->fetch_name_optionals_label($soc->table_element);
1820  if ($soc->fetch_optionals() > 0) {
1821  $object->array_options = array_merge($object->array_options, $soc->array_options);
1822  }
1823  };
1824 
1825  print $object->showOptionals($extrafields, 'create', $parameters);
1826  }
1827 
1828  // Template to use by default
1829  print '<tr><td>'.$langs->trans('DefaultModel').'</td>';
1830  print '<td>';
1831  include_once DOL_DOCUMENT_ROOT.'/core/modules/commande/modules_commande.php';
1832  $liste = ModelePDFCommandes::liste_modeles($db);
1833  $preselected = $conf->global->COMMANDE_ADDON_PDF;
1834  print img_picto('', 'pdf', 'class="pictofixedwidth"');
1835  print $form->selectarray('model', $liste, $preselected, 0, 0, 0, '', 0, 0, 0, '', 'maxwidth200 widthcentpercentminusx', 1);
1836  print "</td></tr>";
1837 
1838  // Multicurrency
1839  if (!empty($conf->multicurrency->enabled)) {
1840  print '<tr>';
1841  print '<td>'.$form->editfieldkey("Currency", 'multicurrency_code', '', $object, 0).'</td>';
1842  print '<td class="maxwidthonsmartphone">';
1843  print img_picto('', 'currency', 'class="pictofixedwidth"').$form->selectMultiCurrency($currency_code, 'multicurrency_code', 0, '', false, 'maxwidth200 widthcentpercentminusx');
1844  print '</td></tr>';
1845  }
1846 
1847  // Note public
1848  print '<tr>';
1849  print '<td class="tdtop">'.$langs->trans('NotePublic').'</td>';
1850  print '<td>';
1851 
1852  $doleditor = new DolEditor('note_public', $note_public, '', 80, 'dolibarr_notes', 'In', 0, false, empty($conf->global->FCKEDITOR_ENABLE_NOTE_PUBLIC) ? 0 : 1, ROWS_3, '90%');
1853  print $doleditor->Create(1);
1854  // print '<textarea name="note_public" wrap="soft" cols="70" rows="'.ROWS_3.'">'.$note_public.'</textarea>';
1855  print '</td></tr>';
1856 
1857  // Note private
1858  if (empty($user->socid)) {
1859  print '<tr>';
1860  print '<td class="tdtop">'.$langs->trans('NotePrivate').'</td>';
1861  print '<td>';
1862 
1863  $doleditor = new DolEditor('note_private', $note_private, '', 80, 'dolibarr_notes', 'In', 0, false, empty($conf->global->FCKEDITOR_ENABLE_NOTE_PRIVATE) ? 0 : 1, ROWS_3, '90%');
1864  print $doleditor->Create(1);
1865  // print '<textarea name="note" wrap="soft" cols="70" rows="'.ROWS_3.'">'.$note_private.'</textarea>';
1866  print '</td></tr>';
1867  }
1868 
1869  if (!empty($origin) && !empty($originid) && is_object($objectsrc)) {
1870  // TODO for compatibility
1871  if ($origin == 'contrat') {
1872  // Calcul contrat->price (HT), contrat->total (TTC), contrat->tva
1873  $objectsrc->remise_absolue = $remise_absolue;
1874  $objectsrc->remise_percent = $remise_percent;
1875  $objectsrc->update_price(1);
1876  }
1877 
1878  print "\n<!-- ".$classname." info -->";
1879  print "\n";
1880  print '<input type="hidden" name="amount" value="'.$objectsrc->total_ht.'">'."\n";
1881  print '<input type="hidden" name="total" value="'.$objectsrc->total_ttc.'">'."\n";
1882  print '<input type="hidden" name="tva" value="'.$objectsrc->total_tva.'">'."\n";
1883  print '<input type="hidden" name="origin" value="'.$objectsrc->element.'">';
1884  print '<input type="hidden" name="originid" value="'.$objectsrc->id.'">';
1885 
1886  switch ($classname) {
1887  case 'Propal':
1888  $newclassname = 'CommercialProposal';
1889  break;
1890  case 'Commande':
1891  $newclassname = 'Order';
1892  break;
1893  case 'Expedition':
1894  $newclassname = 'Sending';
1895  break;
1896  case 'Contrat':
1897  $newclassname = 'Contract';
1898  break;
1899  default:
1900  $newclassname = $classname;
1901  }
1902 
1903  print '<tr><td>'.$langs->trans($newclassname).'</td><td>'.$objectsrc->getNomUrl(1).'</td></tr>';
1904 
1905  // Amount
1906  print '<tr><td>'.$langs->trans('AmountHT').'</td><td>'.price($objectsrc->total_ht).'</td></tr>';
1907  print '<tr><td>'.$langs->trans('AmountVAT').'</td><td>'.price($objectsrc->total_tva)."</td></tr>";
1908  if ($mysoc->localtax1_assuj == "1" || $objectsrc->total_localtax1 != 0) { // Localtax1 RE
1909  print '<tr><td>'.$langs->transcountry("AmountLT1", $mysoc->country_code).'</td><td>'.price($objectsrc->total_localtax1)."</td></tr>";
1910  }
1911 
1912  if ($mysoc->localtax2_assuj == "1" || $objectsrc->total_localtax2 != 0) { // Localtax2 IRPF
1913  print '<tr><td>'.$langs->transcountry("AmountLT2", $mysoc->country_code).'</td><td>'.price($objectsrc->total_localtax2)."</td></tr>";
1914  }
1915 
1916  print '<tr><td>'.$langs->trans('AmountTTC').'</td><td>'.price($objectsrc->total_ttc)."</td></tr>";
1917 
1918  if (!empty($conf->multicurrency->enabled)) {
1919  print '<tr><td>'.$langs->trans('MulticurrencyAmountHT').'</td><td>'.price($objectsrc->multicurrency_total_ht).'</td></tr>';
1920  print '<tr><td>'.$langs->trans('MulticurrencyAmountVAT').'</td><td>'.price($objectsrc->multicurrency_total_tva)."</td></tr>";
1921  print '<tr><td>'.$langs->trans('MulticurrencyAmountTTC').'</td><td>'.price($objectsrc->multicurrency_total_ttc)."</td></tr>";
1922  }
1923  }
1924 
1925  print '</table>';
1926 
1927  print dol_get_fiche_end();
1928 
1929  print $form->buttonsSaveCancel("CreateDraft");
1930 
1931  // Show origin lines
1932  if (!empty($origin) && !empty($originid) && is_object($objectsrc)) {
1933  $title = $langs->trans('ProductsAndServices');
1934  print load_fiche_titre($title);
1935 
1936  print '<div class="div-table-responsive-no-min">';
1937  print '<table class="noborder centpercent">';
1938 
1939  $objectsrc->printOriginLinesList('', $selectedLines);
1940 
1941  print '</table>';
1942  print '</div>';
1943  }
1944 
1945  print '</form>';
1946 } else {
1947  // Mode view
1948  $now = dol_now();
1949 
1950  if ($object->id > 0) {
1951  $product_static = new Product($db);
1952 
1953  $soc = new Societe($db);
1954  $soc->fetch($object->socid);
1955 
1956  $author = new User($db);
1957  $author->fetch($object->user_author_id);
1958 
1959  $object->fetch_thirdparty();
1960  $res = $object->fetch_optionals();
1961 
1962  $head = commande_prepare_head($object);
1963  print dol_get_fiche_head($head, 'order', $langs->trans("CustomerOrder"), -1, 'order');
1964 
1965  $formconfirm = '';
1966 
1967  // Confirmation to delete
1968  if ($action == 'delete') {
1969  $formconfirm = $form->formconfirm($_SERVER["PHP_SELF"].'?id='.$object->id, $langs->trans('DeleteOrder'), $langs->trans('ConfirmDeleteOrder'), 'confirm_delete', '', 0, 1);
1970  }
1971 
1972  // Confirmation of validation
1973  if ($action == 'validate') {
1974  // We check that object has a temporary ref
1975  $ref = substr($object->ref, 1, 4);
1976  if ($ref == 'PROV' || $ref == '') {
1977  $numref = $object->getNextNumRef($soc);
1978  if (empty($numref)) {
1979  $error++;
1980  setEventMessages($object->error, $object->errors, 'errors');
1981  }
1982  } else {
1983  $numref = $object->ref;
1984  }
1985 
1986  $text = $langs->trans('ConfirmValidateOrder', $numref);
1987  if (!empty($conf->notification->enabled)) {
1988  require_once DOL_DOCUMENT_ROOT.'/core/class/notify.class.php';
1989  $notify = new Notify($db);
1990  $text .= '<br>';
1991  $text .= $notify->confirmMessage('ORDER_VALIDATE', $object->socid, $object);
1992  }
1993 
1994  $qualified_for_stock_change = 0;
1995  if (empty($conf->global->STOCK_SUPPORTS_SERVICES)) {
1996  $qualified_for_stock_change = $object->hasProductsOrServices(2);
1997  } else {
1998  $qualified_for_stock_change = $object->hasProductsOrServices(1);
1999  }
2000 
2001  $formquestion = array();
2002  if (!empty($conf->stock->enabled) && !empty($conf->global->STOCK_CALCULATE_ON_VALIDATE_ORDER) && $qualified_for_stock_change) {
2003  $langs->load("stocks");
2004  require_once DOL_DOCUMENT_ROOT.'/product/class/html.formproduct.class.php';
2005  $formproduct = new FormProduct($db);
2006  $forcecombo = 0;
2007  if ($conf->browser->name == 'ie') {
2008  $forcecombo = 1; // There is a bug in IE10 that make combo inside popup crazy
2009  }
2010  $formquestion = array(
2011  // 'text' => $langs->trans("ConfirmClone"),
2012  // array('type' => 'checkbox', 'name' => 'clone_content', 'label' => $langs->trans("CloneMainAttributes"), 'value' => 1),
2013  // array('type' => 'checkbox', 'name' => 'update_prices', 'label' => $langs->trans("PuttingPricesUpToDate"), 'value' => 1),
2014  array('type' => 'other', 'name' => 'idwarehouse', 'label' => $langs->trans("SelectWarehouseForStockDecrease"), 'value' => $formproduct->selectWarehouses(GETPOST('idwarehouse', 'int') ?GETPOST('idwarehouse', 'int') : 'ifone', 'idwarehouse', '', 1, 0, 0, '', 0, $forcecombo))
2015  );
2016  }
2017 
2018  // mandatoryPeriod
2019  $nbMandated = 0;
2020  foreach ($object->lines as $line) {
2021  $res = $line->fetch_product();
2022  if ($res > 0 ) {
2023  if ($line->product->isService() && $line->product->isMandatoryPeriod() && (empty($line->date_start) || empty($line->date_end) )) {
2024  $nbMandated++;
2025  break;
2026  }
2027  }
2028  }
2029  if ($nbMandated > 0 ) $text .= '<div><span class="clearboth nowraponall warning">'.$langs->trans("mandatoryPeriodNeedTobeSetMsgValidate").'</span></div>';
2030 
2031 
2032  $deposit_percent_from_payment_terms = getDictionaryValue('c_payment_term', 'deposit_percent', $object->cond_reglement_id);
2033 
2034  if (! empty($deposit_percent_from_payment_terms) && ! empty($conf->facture->enabled) && ! empty($user->rights->facture->creer)) {
2035  require_once DOL_DOCUMENT_ROOT . '/compta/facture/class/facture.class.php';
2036 
2037  $object->fetchObjectLinked();
2038 
2039  $eligibleForDepositGeneration = true;
2040 
2041  if (array_key_exists('facture', $object->linkedObjects)) {
2042  foreach ($object->linkedObjects['facture'] as $invoice) {
2043  if ($invoice->type == Facture::TYPE_DEPOSIT) {
2044  $eligibleForDepositGeneration = false;
2045  break;
2046  }
2047  }
2048  }
2049 
2050  if ($eligibleForDepositGeneration && array_key_exists('propal', $object->linkedObjects)) {
2051  foreach ($object->linkedObjects['propal'] as $proposal) {
2052  $proposal->fetchObjectLinked();
2053 
2054  if (array_key_exists('facture', $proposal->linkedObjects)) {
2055  foreach ($proposal->linkedObjects['facture'] as $invoice) {
2056  if ($invoice->type == Facture::TYPE_DEPOSIT) {
2057  $eligibleForDepositGeneration = false;
2058  break 2;
2059  }
2060  }
2061  }
2062  }
2063  }
2064 
2065 
2066  if ($eligibleForDepositGeneration) {
2067  $formquestion[] = array(
2068  'type' => 'checkbox',
2069  'tdclass' => '',
2070  'name' => 'generate_deposit',
2071  'label' => $form->textwithpicto($langs->trans('GenerateDeposit', $object->deposit_percent), $langs->trans('DepositGenerationPermittedByThePaymentTermsSelected'))
2072  );
2073 
2074  $formquestion[] = array(
2075  'type' => 'date',
2076  'tdclass' => 'fieldrequired showonlyifgeneratedeposit',
2077  'name' => 'datef',
2078  'label' => $langs->trans('DateInvoice'),
2079  'value' => dol_now(),
2080  'datenow' => true
2081  );
2082 
2083  if (! empty($conf->global->INVOICE_POINTOFTAX_DATE)) {
2084  $formquestion[] = array(
2085  'type' => 'date',
2086  'tdclass' => 'fieldrequired showonlyifgeneratedeposit',
2087  'name' => 'date_pointoftax',
2088  'label' => $langs->trans('DatePointOfTax'),
2089  'value' => dol_now(),
2090  'datenow' => true
2091  );
2092  }
2093 
2094  ob_start();
2095  $form->select_conditions_paiements(0, 'cond_reglement_id', -1, 0, 0, 'minwidth200');
2096  $paymentTermsSelect = ob_get_clean();
2097 
2098  $formquestion[] = array(
2099  'type' => 'other',
2100  'tdclass' => 'fieldrequired showonlyifgeneratedeposit',
2101  'name' => 'cond_reglement_id',
2102  'label' => $langs->trans('PaymentTerm'),
2103  'value' => $paymentTermsSelect
2104  );
2105 
2106  $formquestion[] = array(
2107  'type' => 'checkbox',
2108  'tdclass' => 'showonlyifgeneratedeposit',
2109  'name' => 'validate_generated_deposit',
2110  'label' => $langs->trans('ValidateGeneratedDeposit')
2111  );
2112 
2113  $formquestion[] = array(
2114  'type' => 'onecolumn',
2115  'value' => '
2116  <script>
2117  $(document).ready(function() {
2118  $("[name=generate_deposit]").change(function () {
2119  let $self = $(this);
2120  let $target = $(".showonlyifgeneratedeposit").parent(".tagtr");
2121 
2122  if (! $self.parents(".tagtr").is(":hidden") && $self.is(":checked")) {
2123  $target.show();
2124  } else {
2125  $target.hide();
2126  }
2127 
2128  return true;
2129  });
2130  });
2131  </script>
2132  '
2133  );
2134  }
2135  }
2136 
2137  if (!$error) {
2138  $formconfirm = $form->formconfirm($_SERVER["PHP_SELF"].'?id='.$object->id, $langs->trans('ValidateOrder'), $text, 'confirm_validate', $formquestion, 0, 1, 220);
2139  }
2140  }
2141 
2142  // Confirm back to draft status
2143  if ($action == 'modif') {
2144  $qualified_for_stock_change = 0;
2145  if (empty($conf->global->STOCK_SUPPORTS_SERVICES)) {
2146  $qualified_for_stock_change = $object->hasProductsOrServices(2);
2147  } else {
2148  $qualified_for_stock_change = $object->hasProductsOrServices(1);
2149  }
2150 
2151  $text = $langs->trans('ConfirmUnvalidateOrder', $object->ref);
2152  $formquestion = array();
2153  if (!empty($conf->stock->enabled) && !empty($conf->global->STOCK_CALCULATE_ON_VALIDATE_ORDER) && $qualified_for_stock_change) {
2154  $langs->load("stocks");
2155  require_once DOL_DOCUMENT_ROOT.'/product/class/html.formproduct.class.php';
2156  $formproduct = new FormProduct($db);
2157  $forcecombo = 0;
2158  if ($conf->browser->name == 'ie') {
2159  $forcecombo = 1; // There is a bug in IE10 that make combo inside popup crazy
2160  }
2161  $formquestion = array(
2162  // 'text' => $langs->trans("ConfirmClone"),
2163  // array('type' => 'checkbox', 'name' => 'clone_content', 'label' => $langs->trans("CloneMainAttributes"), 'value' => 1),
2164  // array('type' => 'checkbox', 'name' => 'update_prices', 'label' => $langs->trans("PuttingPricesUpToDate"), 'value' => 1),
2165  array('type' => 'other', 'name' => 'idwarehouse', 'label' => $langs->trans("SelectWarehouseForStockIncrease"), 'value' => $formproduct->selectWarehouses(GETPOST('idwarehouse') ?GETPOST('idwarehouse') : 'ifone', 'idwarehouse', '', 1, 0, 0, '', 0, $forcecombo))
2166  );
2167  }
2168 
2169  $formconfirm = $form->formconfirm($_SERVER["PHP_SELF"].'?id='.$object->id, $langs->trans('UnvalidateOrder'), $text, 'confirm_modif', $formquestion, "yes", 1, 220);
2170  }
2171 
2172  /*
2173  * Confirmation de la cloture
2174  */
2175  if ($action == 'shipped') {
2176  $formconfirm = $form->formconfirm($_SERVER["PHP_SELF"].'?id='.$object->id, $langs->trans('CloseOrder'), $langs->trans('ConfirmCloseOrder'), 'confirm_shipped', '', 0, 1);
2177  }
2178 
2179  /*
2180  * Confirmation de l'annulation
2181  */
2182  if ($action == 'cancel') {
2183  $qualified_for_stock_change = 0;
2184  if (empty($conf->global->STOCK_SUPPORTS_SERVICES)) {
2185  $qualified_for_stock_change = $object->hasProductsOrServices(2);
2186  } else {
2187  $qualified_for_stock_change = $object->hasProductsOrServices(1);
2188  }
2189 
2190  $text = $langs->trans('ConfirmCancelOrder', $object->ref);
2191  $formquestion = array();
2192  if (!empty($conf->stock->enabled) && !empty($conf->global->STOCK_CALCULATE_ON_VALIDATE_ORDER) && $qualified_for_stock_change) {
2193  $langs->load("stocks");
2194  require_once DOL_DOCUMENT_ROOT.'/product/class/html.formproduct.class.php';
2195  $formproduct = new FormProduct($db);
2196  $forcecombo = 0;
2197  if ($conf->browser->name == 'ie') {
2198  $forcecombo = 1; // There is a bug in IE10 that make combo inside popup crazy
2199  }
2200  $formquestion = array(
2201  // 'text' => $langs->trans("ConfirmClone"),
2202  // array('type' => 'checkbox', 'name' => 'clone_content', 'label' => $langs->trans("CloneMainAttributes"), 'value' => 1),
2203  // array('type' => 'checkbox', 'name' => 'update_prices', 'label' => $langs->trans("PuttingPricesUpToDate"), 'value' => 1),
2204  array('type' => 'other', 'name' => 'idwarehouse', 'label' => $langs->trans("SelectWarehouseForStockIncrease"), 'value' => $formproduct->selectWarehouses(GETPOST('idwarehouse') ?GETPOST('idwarehouse') : 'ifone', 'idwarehouse', '', 1, 0, 0, '', 0, $forcecombo))
2205  );
2206  }
2207 
2208  $formconfirm = $form->formconfirm($_SERVER["PHP_SELF"].'?id='.$object->id, $langs->trans("Cancel"), $text, 'confirm_cancel', $formquestion, 0, 1);
2209  }
2210 
2211  // Confirmation to delete line
2212  if ($action == 'ask_deleteline') {
2213  $formconfirm = $form->formconfirm($_SERVER["PHP_SELF"].'?id='.$object->id.'&lineid='.$lineid, $langs->trans('DeleteProductLine'), $langs->trans('ConfirmDeleteProductLine'), 'confirm_deleteline', '', 0, 1);
2214  }
2215 
2216  // Clone confirmation
2217  if ($action == 'clone') {
2218  // Create an array for form
2219  $formquestion = array(
2220  array('type' => 'other', 'name' => 'socid', 'label' => $langs->trans("SelectThirdParty"), 'value' => $form->select_company(GETPOST('socid', 'int'), 'socid', '(s.client=1 OR s.client = 2 OR s.client=3)', '', 0, 0, null, 0, 'maxwidth300'))
2221  );
2222  $formconfirm = $form->formconfirm($_SERVER["PHP_SELF"].'?id='.$object->id, $langs->trans('ToClone'), $langs->trans('ConfirmCloneOrder', $object->ref), 'confirm_clone', $formquestion, 'yes', 1);
2223  }
2224 
2225  // Call Hook formConfirm
2226  $parameters = array('formConfirm' => $formconfirm, 'lineid' => $lineid);
2227  // Note that $action and $object may be modified by hook
2228  $reshook = $hookmanager->executeHooks('formConfirm', $parameters, $object, $action);
2229  if (empty($reshook)) {
2230  $formconfirm .= $hookmanager->resPrint;
2231  } elseif ($reshook > 0) {
2232  $formconfirm = $hookmanager->resPrint;
2233  }
2234 
2235  // Print form confirm
2236  print $formconfirm;
2237 
2238 
2239  // Order card
2240 
2241  $linkback = '<a href="'.DOL_URL_ROOT.'/commande/list.php?restore_lastsearch_values=1'.(!empty($socid) ? '&socid='.$socid : '').'">'.$langs->trans("BackToList").'</a>';
2242 
2243  $morehtmlref = '<div class="refidno">';
2244  // Ref customer
2245  $morehtmlref .= $form->editfieldkey("RefCustomer", 'ref_client', $object->ref_client, $object, $usercancreate, 'string', '', 0, 1);
2246  $morehtmlref .= $form->editfieldval("RefCustomer", 'ref_client', $object->ref_client, $object, $usercancreate, 'string', '', null, null, '', 1);
2247  // Thirdparty
2248  $morehtmlref .= '<br>'.$langs->trans('ThirdParty').' : '.$soc->getNomUrl(1, 'customer');
2249  if (empty($conf->global->MAIN_DISABLE_OTHER_LINK) && $object->thirdparty->id > 0) {
2250  $morehtmlref .= ' (<a href="'.DOL_URL_ROOT.'/commande/list.php?socid='.$object->thirdparty->id.'&search_societe='.urlencode($object->thirdparty->name).'">'.$langs->trans("OtherOrders").'</a>)';
2251  }
2252  // Project
2253  if (!empty($conf->project->enabled)) {
2254  $langs->load("projects");
2255  $morehtmlref .= '<br>'.$langs->trans('Project').' ';
2256  if ($usercancreate) {
2257  if ($action != 'classify') {
2258  $morehtmlref .= '<a class="editfielda" href="'.$_SERVER['PHP_SELF'].'?action=classify&token='.newToken().'&id='.$object->id.'">'.img_edit($langs->transnoentitiesnoconv('SetProject')).'</a> : ';
2259  }
2260  if ($action == 'classify') {
2261  //$morehtmlref.=$form->form_project($_SERVER['PHP_SELF'] . '?id=' . $object->id, $object->socid, $object->fk_project, 'projectid', 0, 0, 1, 1);
2262  $morehtmlref .= '<form method="post" action="'.$_SERVER['PHP_SELF'].'?id='.$object->id.'">';
2263  $morehtmlref .= '<input type="hidden" name="action" value="classin">';
2264  $morehtmlref .= '<input type="hidden" name="token" value="'.newToken().'">';
2265  $morehtmlref .= $formproject->select_projects($object->socid, $object->fk_project, 'projectid', 0, 0, 1, 0, 1, 0, 0, '', 1, 0, 'maxwidth500');
2266  $morehtmlref .= '<input type="submit" class="button valignmiddle" value="'.$langs->trans("Modify").'">';
2267  $morehtmlref .= '</form>';
2268  } else {
2269  $morehtmlref .= $form->form_project($_SERVER['PHP_SELF'].'?id='.$object->id, $object->socid, $object->fk_project, 'none', 0, 0, 0, 1);
2270  }
2271  } else {
2272  if (!empty($object->fk_project)) {
2273  $proj = new Project($db);
2274  $proj->fetch($object->fk_project);
2275  $morehtmlref .= ' : '.$proj->getNomUrl(1);
2276  if ($proj->title) {
2277  $morehtmlref .= ' - '.$proj->title;
2278  }
2279  } else {
2280  $morehtmlref .= '';
2281  }
2282  }
2283  }
2284  $morehtmlref .= '</div>';
2285 
2286 
2287  dol_banner_tab($object, 'ref', $linkback, 1, 'ref', 'ref', $morehtmlref);
2288 
2289 
2290  print '<div class="fichecenter">';
2291  print '<div class="fichehalfleft">';
2292  print '<div class="underbanner clearboth"></div>';
2293 
2294  print '<table class="border tableforfield centpercent">';
2295 
2296  if ($soc->outstanding_limit) {
2297  // Outstanding Bill
2298  print '<tr><td class="titlefield">';
2299  print $langs->trans('OutstandingBill');
2300  print '</td><td class="valuefield">';
2301  $arrayoutstandingbills = $soc->getOutstandingBills();
2302  print price($arrayoutstandingbills['opened']).' / ';
2303  print price($soc->outstanding_limit, 0, '', 1, - 1, - 1, $conf->currency);
2304  print '</td>';
2305  print '</tr>';
2306  }
2307 
2308  // Relative and absolute discounts
2309  if (!empty($conf->global->FACTURE_DEPOSITS_ARE_JUST_PAYMENTS)) {
2310  $filterabsolutediscount = "fk_facture_source IS NULL"; // If we want deposit to be substracted to payments only and not to total of final invoice
2311  $filtercreditnote = "fk_facture_source IS NOT NULL"; // If we want deposit to be substracted to payments only and not to total of final invoice
2312  } else {
2313  $filterabsolutediscount = "fk_facture_source IS NULL OR (description LIKE '(DEPOSIT)%' AND description NOT LIKE '(EXCESS RECEIVED)%')";
2314  $filtercreditnote = "fk_facture_source IS NOT NULL AND (description NOT LIKE '(DEPOSIT)%' OR description LIKE '(EXCESS RECEIVED)%')";
2315  }
2316 
2317  $addrelativediscount = '<a href="'.DOL_URL_ROOT.'/comm/remise.php?id='.$soc->id.'&backtopage='.urlencode($_SERVER["PHP_SELF"]).'?facid='.$object->id.'">'.$langs->trans("EditRelativeDiscounts").'</a>';
2318  $addabsolutediscount = '<a href="'.DOL_URL_ROOT.'/comm/remx.php?id='.$soc->id.'&backtopage='.urlencode($_SERVER["PHP_SELF"]).'?facid='.$object->id.'">'.$langs->trans("EditGlobalDiscounts").'</a>';
2319  $addcreditnote = '<a href="'.DOL_URL_ROOT.'/compta/facture/card.php?action=create&socid='.$soc->id.'&type=2&backtopage='.urlencode($_SERVER["PHP_SELF"]).'?facid='.$object->id.'">'.$langs->trans("AddCreditNote").'</a>';
2320 
2321  print '<tr><td class="titlefield">'.$langs->trans('Discounts').'</td><td class="valuefield">';
2322 
2323  $absolute_discount = $soc->getAvailableDiscounts('', $filterabsolutediscount);
2324  $absolute_creditnote = $soc->getAvailableDiscounts('', $filtercreditnote);
2325  $absolute_discount = price2num($absolute_discount, 'MT');
2326  $absolute_creditnote = price2num($absolute_creditnote, 'MT');
2327 
2328  $thirdparty = $soc;
2329  $discount_type = 0;
2330  $backtopage = urlencode($_SERVER["PHP_SELF"].'?id='.$object->id);
2331  include DOL_DOCUMENT_ROOT.'/core/tpl/object_discounts.tpl.php';
2332 
2333  print '</td></tr>';
2334 
2335  // Date
2336  print '<tr><td>';
2337  $editenable = $usercancreate && $object->statut == Commande::STATUS_DRAFT;
2338  print $form->editfieldkey("Date", 'date', '', $object, $editenable);
2339  print '</td><td class="valuefield">';
2340  if ($action == 'editdate') {
2341  print '<form name="setdate" action="'.$_SERVER["PHP_SELF"].'?id='.$object->id.'" method="post">';
2342  print '<input type="hidden" name="token" value="'.newToken().'">';
2343  print '<input type="hidden" name="action" value="setdate">';
2344  print $form->selectDate($object->date, 'order_', '', '', '', "setdate");
2345  print '<input type="submit" class="button button-edit" value="'.$langs->trans('Modify').'">';
2346  print '</form>';
2347  } else {
2348  print $object->date ? dol_print_date($object->date, 'day') : '&nbsp;';
2349  if ($object->hasDelay() && empty($object->delivery_date)) { // If there is a delivery date planned, warning should be on this date
2350  print ' '.img_picto($langs->trans("Late").' : '.$object->showDelay(), "warning");
2351  }
2352  }
2353  print '</td>';
2354  print '</tr>';
2355 
2356  // Delivery date planed
2357  print '<tr><td>';
2358  $editenable = $usercancreate;
2359  print $form->editfieldkey("DateDeliveryPlanned", 'date_livraison', '', $object, $editenable);
2360  print '</td><td class="valuefield">';
2361  if ($action == 'editdate_livraison') {
2362  print '<form name="setdate_livraison" action="'.$_SERVER["PHP_SELF"].'?id='.$object->id.'" method="post">';
2363  print '<input type="hidden" name="token" value="'.newToken().'">';
2364  print '<input type="hidden" name="action" value="setdate_livraison">';
2365  print $form->selectDate($object->delivery_date ? $object->delivery_date : -1, 'liv_', 1, 1, '', "setdate_livraison", 1, 0);
2366  print '<input type="submit" class="button button-edit" value="'.$langs->trans('Modify').'">';
2367  print '</form>';
2368  } else {
2369  print $object->delivery_date ? dol_print_date($object->delivery_date, 'dayhour') : '&nbsp;';
2370  if ($object->hasDelay() && !empty($object->delivery_date)) {
2371  print ' '.img_picto($langs->trans("Late").' : '.$object->showDelay(), "warning");
2372  }
2373  }
2374  print '</td>';
2375  print '</tr>';
2376 
2377  // Delivery delay
2378  print '<tr class="fielddeliverydelay"><td>';
2379  $editenable = $usercancreate;
2380  print $form->editfieldkey("AvailabilityPeriod", 'availability', '', $object, $editenable);
2381  print '</td><td class="valuefield">';
2382  if ($action == 'editavailability') {
2383  $form->form_availability($_SERVER['PHP_SELF'].'?id='.$object->id, $object->availability_id, 'availability_id', 1);
2384  } else {
2385  $form->form_availability($_SERVER['PHP_SELF'].'?id='.$object->id, $object->availability_id, 'none', 1);
2386  }
2387  print '</td></tr>';
2388 
2389  // Shipping Method
2390  if (isModEnabled('expedition')) {
2391  print '<tr><td>';
2392  $editenable = $usercancreate;
2393  print $form->editfieldkey("SendingMethod", 'shippingmethod', '', $object, $editenable);
2394  print '</td><td class="valuefield">';
2395  if ($action == 'editshippingmethod') {
2396  $form->formSelectShippingMethod($_SERVER['PHP_SELF'].'?id='.$object->id, $object->shipping_method_id, 'shipping_method_id', 1);
2397  } else {
2398  $form->formSelectShippingMethod($_SERVER['PHP_SELF'].'?id='.$object->id, $object->shipping_method_id, 'none');
2399  }
2400  print '</td>';
2401  print '</tr>';
2402  }
2403 
2404  // Warehouse
2405  if (!empty($conf->stock->enabled) && !empty($conf->global->WAREHOUSE_ASK_WAREHOUSE_DURING_ORDER)) {
2406  $langs->load('stocks');
2407  require_once DOL_DOCUMENT_ROOT.'/product/class/html.formproduct.class.php';
2408  $formproduct = new FormProduct($db);
2409  print '<tr><td>';
2410  $editenable = $usercancreate;
2411  print $form->editfieldkey("Warehouse", 'warehouse', '', $object, $editenable);
2412  print '</td><td class="valuefield">';
2413  if ($action == 'editwarehouse') {
2414  $formproduct->formSelectWarehouses($_SERVER['PHP_SELF'].'?id='.$object->id, $object->warehouse_id, 'warehouse_id', 1);
2415  } else {
2416  $formproduct->formSelectWarehouses($_SERVER['PHP_SELF'].'?id='.$object->id, $object->warehouse_id, 'none');
2417  }
2418  print '</td>';
2419  print '</tr>';
2420  }
2421 
2422  // Source reason (why we have an order)
2423  print '<tr><td>';
2424  $editenable = $usercancreate;
2425  print $form->editfieldkey("Source", 'demandreason', '', $object, $editenable);
2426  print '</td><td class="valuefield">';
2427  if ($action == 'editdemandreason') {
2428  $form->formInputReason($_SERVER['PHP_SELF'].'?id='.$object->id, $object->demand_reason_id, 'demand_reason_id', 1);
2429  } else {
2430  $form->formInputReason($_SERVER['PHP_SELF'].'?id='.$object->id, $object->demand_reason_id, 'none');
2431  }
2432  print '</td></tr>';
2433 
2434  // Terms of payment
2435  print '<tr><td>';
2436  $editenable = $usercancreate;
2437  print $form->editfieldkey("PaymentConditionsShort", 'conditions', '', $object, $editenable);
2438  print '</td><td class="valuefield">';
2439  if ($action == 'editconditions') {
2440  $form->form_conditions_reglement($_SERVER['PHP_SELF'].'?id='.$object->id, $object->cond_reglement_id, 'cond_reglement_id', 1, '', 1, $object->deposit_percent);
2441  } else {
2442  $form->form_conditions_reglement($_SERVER['PHP_SELF'].'?id='.$object->id, $object->cond_reglement_id, 'none', 1, '', 1, $object->deposit_percent);
2443  }
2444  print '</td>';
2445 
2446  print '</tr>';
2447 
2448  // Mode of payment
2449  print '<tr><td>';
2450  $editenable = $usercancreate;
2451  print $form->editfieldkey("PaymentMode", 'mode', '', $object, $editenable);
2452  print '</td><td class="valuefield">';
2453  if ($action == 'editmode') {
2454  $form->form_modes_reglement($_SERVER['PHP_SELF'].'?id='.$object->id, $object->mode_reglement_id, 'mode_reglement_id', 'CRDT', 1, 1);
2455  } else {
2456  $form->form_modes_reglement($_SERVER['PHP_SELF'].'?id='.$object->id, $object->mode_reglement_id, 'none');
2457  }
2458  print '</td></tr>';
2459 
2460  // Multicurrency
2461  if (!empty($conf->multicurrency->enabled)) {
2462  // Multicurrency code
2463  print '<tr>';
2464  print '<td>';
2465  $editenable = $usercancreate && $object->statut == Commande::STATUS_DRAFT;
2466  print $form->editfieldkey("Currency", 'multicurrencycode', '', $object, $editenable);
2467  print '</td><td class="valuefield">';
2468  if ($action == 'editmulticurrencycode') {
2469  $form->form_multicurrency_code($_SERVER['PHP_SELF'].'?id='.$object->id, $object->multicurrency_code, 'multicurrency_code');
2470  } else {
2471  $form->form_multicurrency_code($_SERVER['PHP_SELF'].'?id='.$object->id, $object->multicurrency_code, 'none');
2472  }
2473  print '</td></tr>';
2474 
2475  // Multicurrency rate
2476  if ($object->multicurrency_code != $conf->currency || $object->multicurrency_tx != 1) {
2477  print '<tr>';
2478  print '<td>';
2479  $editenable = $usercancreate && $object->multicurrency_code && $object->multicurrency_code != $conf->currency && $object->statut == $object::STATUS_DRAFT;
2480  print $form->editfieldkey("CurrencyRate", 'multicurrencyrate', '', $object, $editenable);
2481  print '</td><td class="valuefield">';
2482  if ($action == 'editmulticurrencyrate' || $action == 'actualizemulticurrencyrate') {
2483  if ($action == 'actualizemulticurrencyrate') {
2484  list($object->fk_multicurrency, $object->multicurrency_tx) = MultiCurrency::getIdAndTxFromCode($object->db, $object->multicurrency_code);
2485  }
2486  $form->form_multicurrency_rate($_SERVER['PHP_SELF'].'?id='.$object->id, $object->multicurrency_tx, 'multicurrency_tx', $object->multicurrency_code);
2487  } else {
2488  $form->form_multicurrency_rate($_SERVER['PHP_SELF'].'?id='.$object->id, $object->multicurrency_tx, 'none', $object->multicurrency_code);
2489  if ($object->statut == $object::STATUS_DRAFT && $object->multicurrency_code && $object->multicurrency_code != $conf->currency) {
2490  print '<div class="inline-block"> &nbsp; &nbsp; &nbsp; &nbsp; ';
2491  print '<a href="'.$_SERVER["PHP_SELF"].'?id='.$object->id.'&action=actualizemulticurrencyrate">'.$langs->trans("ActualizeCurrency").'</a>';
2492  print '</div>';
2493  }
2494  }
2495  print '</td></tr>';
2496  }
2497  }
2498 
2499  // TODO Order mode (how we receive order). Not yet implemented
2500  /*
2501  print '<tr><td>';
2502  $editenable = $usercancreate;
2503  print $form->editfieldkey("SourceMode", 'inputmode', '', $object, $editenable);
2504  print '</td><td>';
2505  if ($action == 'editinputmode') {
2506  $form->formInputMode($_SERVER['PHP_SELF'] . '?id=' . $object->id, $object->source, 'input_mode_id', 1);
2507  } else {
2508  $form->formInputMode($_SERVER['PHP_SELF'] . '?id=' . $object->id, $object->source, 'none');
2509  }
2510  print '</td></tr>';
2511  */
2512 
2513  $tmparray = $object->getTotalWeightVolume();
2514  $totalWeight = $tmparray['weight'];
2515  $totalVolume = $tmparray['volume'];
2516  if ($totalWeight) {
2517  print '<tr><td>'.$langs->trans("CalculatedWeight").'</td>';
2518  print '<td class="valuefield">';
2519  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');
2520  print '</td></tr>';
2521  }
2522  if ($totalVolume) {
2523  print '<tr><td>'.$langs->trans("CalculatedVolume").'</td>';
2524  print '<td class="valuefield">';
2525  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');
2526  print '</td></tr>';
2527  }
2528 
2529  // TODO How record was recorded OrderMode (llx_c_input_method)
2530 
2531  // Incoterms
2532  if (!empty($conf->incoterm->enabled)) {
2533  print '<tr><td>';
2534  $editenable = $usercancreate;
2535  print $form->editfieldkey("IncotermLabel", 'incoterm', '', $object, $editenable);
2536  print '</td>';
2537  print '<td class="valuefield">';
2538  if ($action != 'editincoterm') {
2539  print $form->textwithpicto($object->display_incoterms(), $object->label_incoterms, 1);
2540  } else {
2541  print $form->select_incoterms((!empty($object->fk_incoterms) ? $object->fk_incoterms : ''), (!empty($object->location_incoterms) ? $object->location_incoterms : ''), $_SERVER['PHP_SELF'].'?id='.$object->id);
2542  }
2543  print '</td></tr>';
2544  }
2545 
2546  // Bank Account
2547  if (!empty($conf->global->BANK_ASK_PAYMENT_BANK_DURING_ORDER) && !empty($conf->banque->enabled)) {
2548  print '<tr><td>';
2549  $editenable = $usercancreate;
2550  print $form->editfieldkey("BankAccount", 'bankaccount', '', $object, $editenable);
2551  print '</td><td class="valuefield">';
2552  if ($action == 'editbankaccount') {
2553  $form->formSelectAccount($_SERVER['PHP_SELF'].'?id='.$object->id, $object->fk_account, 'fk_account', 1);
2554  } else {
2555  $form->formSelectAccount($_SERVER['PHP_SELF'].'?id='.$object->id, $object->fk_account, 'none');
2556  }
2557  print '</td>';
2558  print '</tr>';
2559  }
2560 
2561  // Other attributes
2562  include DOL_DOCUMENT_ROOT.'/core/tpl/extrafields_view.tpl.php';
2563 
2564  print '</table>';
2565 
2566  print '</div>';
2567  print '<div class="fichehalfright">';
2568  print '<div class="underbanner clearboth"></div>';
2569 
2570  print '<table class="border tableforfield centpercent">';
2571 
2572  if (!empty($conf->multicurrency->enabled) && ($object->multicurrency_code != $conf->currency)) {
2573  // Multicurrency Amount HT
2574  print '<tr><td class="titlefieldmiddle">'.$form->editfieldkey('MulticurrencyAmountHT', 'multicurrency_total_ht', '', $object, 0).'</td>';
2575  print '<td class="valuefield nowrap right amountcard">'.price($object->multicurrency_total_ht, '', $langs, 0, -1, -1, (!empty($object->multicurrency_code) ? $object->multicurrency_code : $conf->currency)).'</td>';
2576  print '</tr>';
2577 
2578  // Multicurrency Amount VAT
2579  print '<tr><td>'.$form->editfieldkey('MulticurrencyAmountVAT', 'multicurrency_total_tva', '', $object, 0).'</td>';
2580  print '<td class="valuefield nowrap right amountcard">'.price($object->multicurrency_total_tva, '', $langs, 0, -1, -1, (!empty($object->multicurrency_code) ? $object->multicurrency_code : $conf->currency)).'</td>';
2581  print '</tr>';
2582 
2583  // Multicurrency Amount TTC
2584  print '<tr><td>'.$form->editfieldkey('MulticurrencyAmountTTC', 'multicurrency_total_ttc', '', $object, 0).'</td>';
2585  print '<td class="valuefield nowrap right amountcard">'.price($object->multicurrency_total_ttc, '', $langs, 0, -1, -1, (!empty($object->multicurrency_code) ? $object->multicurrency_code : $conf->currency)).'</td>';
2586  print '</tr>';
2587  }
2588 
2589  // Total HT
2590  $alert = '';
2591  if (!empty($conf->global->ORDER_MANAGE_MIN_AMOUNT) && $object->total_ht < $object->thirdparty->order_min_amount) {
2592  $alert = ' '.img_warning($langs->trans('OrderMinAmount').': '.price($object->thirdparty->order_min_amount));
2593  }
2594  print '<tr><td class="titlefieldmiddle">'.$langs->trans('AmountHT').'</td>';
2595  print '<td class="valuefield nowrap right amountcard">'.price($object->total_ht, 1, '', 1, -1, -1, $conf->currency).$alert.'</td>';
2596 
2597  // Total VAT
2598  print '<tr><td>'.$langs->trans('AmountVAT').'</td><td class="valuefield nowrap right amountcard">'.price($object->total_tva, 1, '', 1, -1, -1, $conf->currency).'</td></tr>';
2599 
2600  // Amount Local Taxes
2601  if ($mysoc->localtax1_assuj == "1" || $object->total_localtax1 != 0) { // Localtax1
2602  print '<tr><td>'.$langs->transcountry("AmountLT1", $mysoc->country_code).'</td>';
2603  print '<td class="valuefield nowrap right amountcard">'.price($object->total_localtax1, 1, '', 1, -1, -1, $conf->currency).'</td></tr>';
2604  }
2605  if ($mysoc->localtax2_assuj == "1" || $object->total_localtax2 != 0) { // Localtax2 IRPF
2606  print '<tr><td>'.$langs->transcountry("AmountLT2", $mysoc->country_code).'</td>';
2607  print '<td class="valuefield nowrap right amountcard">'.price($object->total_localtax2, 1, '', 1, -1, -1, $conf->currency).'</td></tr>';
2608  }
2609 
2610  // Total TTC
2611  print '<tr><td>'.$langs->trans('AmountTTC').'</td><td class="valuefield nowrap right amountcard">'.price($object->total_ttc, 1, '', 1, -1, -1, $conf->currency).'</td></tr>';
2612 
2613  // Statut
2614  //print '<tr><td>' . $langs->trans('Status') . '</td><td>' . $object->getLibStatut(4) . '</td></tr>';
2615 
2616  print '</table>';
2617 
2618  // Margin Infos
2619  if (!empty($conf->margin->enabled)) {
2620  $formmargin->displayMarginInfos($object);
2621  }
2622 
2623 
2624  print '</div>';
2625  print '</div>'; // Close fichecenter
2626 
2627  print '<div class="clearboth"></div><br>';
2628 
2629  if (!empty($conf->global->MAIN_DISABLE_CONTACTS_TAB)) {
2630  $blocname = 'contacts';
2631  $title = $langs->trans('ContactsAddresses');
2632  include DOL_DOCUMENT_ROOT.'/core/tpl/bloc_showhide.tpl.php';
2633  }
2634 
2635  if (!empty($conf->global->MAIN_DISABLE_NOTES_TAB)) {
2636  $blocname = 'notes';
2637  $title = $langs->trans('Notes');
2638  include DOL_DOCUMENT_ROOT.'/core/tpl/bloc_showhide.tpl.php';
2639  }
2640 
2641  /*
2642  * Lines
2643  */
2644  $result = $object->getLinesArray();
2645 
2646  print '<form name="addproduct" id="addproduct" action="'.$_SERVER["PHP_SELF"].'?id='.$object->id.(($action != 'editline') ? '' : '#line_'.GETPOST('lineid', 'int')).'" method="POST">
2647  <input type="hidden" name="token" value="' . newToken().'">
2648  <input type="hidden" name="action" value="' . (($action != 'editline') ? 'addline' : 'updateline').'">
2649  <input type="hidden" name="mode" value="">
2650  <input type="hidden" name="page_y" value="">
2651  <input type="hidden" name="id" value="' . $object->id.'">';
2652 
2653  if (!empty($conf->use_javascript_ajax) && $object->statut == Commande::STATUS_DRAFT) {
2654  include DOL_DOCUMENT_ROOT.'/core/tpl/ajaxrow.tpl.php';
2655  }
2656 
2657  print '<div class="div-table-responsive-no-min">';
2658  print '<table id="tablelines" class="noborder noshadow" width="100%">';
2659 
2660  // Show object lines
2661  if (!empty($object->lines)) {
2662  $ret = $object->printObjectLines($action, $mysoc, $soc, $lineid, 1);
2663  }
2664 
2665  $numlines = count($object->lines);
2666 
2667  /*
2668  * Form to add new line
2669  */
2670  if ($object->statut == Commande::STATUS_DRAFT && $usercancreate && $action != 'selectlines') {
2671  if ($action != 'editline') {
2672  // Add free products/services
2673 
2674  $parameters = array();
2675  // Note that $action and $object may be modified by hook
2676  $reshook = $hookmanager->executeHooks('formAddObjectLine', $parameters, $object, $action);
2677  if ($reshook < 0) setEventMessages($hookmanager->error, $hookmanager->errors, 'errors');
2678  if (empty($reshook))
2679  $object->formAddObjectLine(1, $mysoc, $soc);
2680  }
2681  }
2682  print '</table>';
2683  print '</div>';
2684 
2685  print "</form>\n";
2686 
2687  print dol_get_fiche_end();
2688 
2689  /*
2690  * Buttons for actions
2691  */
2692  if ($action != 'presend' && $action != 'editline') {
2693  print '<div class="tabsAction">';
2694 
2695  $parameters = array();
2696  // Note that $action and $object may be modified by hook
2697  $reshook = $hookmanager->executeHooks('addMoreActionsButtons', $parameters, $object, $action);
2698  if (empty($reshook)) {
2699  // Reopen a closed order
2700  if (($object->statut == Commande::STATUS_CLOSED || $object->statut == Commande::STATUS_CANCELED) && $usercancreate) {
2701  print dolGetButtonAction('', $langs->trans('ReOpen'), 'default', $_SERVER["PHP_SELF"].'?action=reopen&amp;token='.newToken().'&amp;id='.$object->id, '');
2702  }
2703 
2704  // Send
2705  if (empty($user->socid)) {
2706  if ($object->statut > Commande::STATUS_DRAFT || !empty($conf->global->COMMANDE_SENDBYEMAIL_FOR_ALL_STATUS)) {
2707  if ($usercansend) {
2708  print dolGetButtonAction('', $langs->trans('SendMail'), 'default', $_SERVER["PHP_SELF"].'?action=presend&amp;token='.newToken().'&amp;id='.$object->id.'&amp;mode=init#formmailbeforetitle', '');
2709  } else {
2710  print dolGetButtonAction('', $langs->trans('SendMail'), 'default', $_SERVER['PHP_SELF']. '#', '', false);
2711  }
2712  }
2713  }
2714 
2715  // Valid
2716  if ($object->statut == Commande::STATUS_DRAFT && ($object->total_ttc >= 0 || !empty($conf->global->ORDER_ENABLE_NEGATIVE)) && $numlines > 0 && $usercanvalidate) {
2717  print dolGetButtonAction('', $langs->trans('Validate'), 'default', $_SERVER["PHP_SELF"].'?action=validate&amp;token='.newToken().'&amp;id='.$object->id, '');
2718  }
2719  // Edit
2720  if ($object->statut == Commande::STATUS_VALIDATED && $usercancreate) {
2721  print dolGetButtonAction('', $langs->trans('Modify'), 'default', $_SERVER["PHP_SELF"].'?action=modif&amp;token='.newToken().'&amp;id='.$object->id, '');
2722  }
2723  // Create event
2724  /*if ($conf->agenda->enabled && ! empty($conf->global->MAIN_ADD_EVENT_ON_ELEMENT_CARD))
2725  {
2726  // Add hidden condition because this is not a
2727  // "workflow" action so should appears somewhere else on
2728  // page.
2729  print '<a class="butAction" href="' . DOL_URL_ROOT . '/comm/action/card.php?action=create&amp;origin=' . $object->element . '&amp;originid=' . $object->id . '&amp;socid=' . $object->socid . '">' . $langs->trans("AddAction") . '</a>';
2730  }*/
2731 
2732  // Create a purchase order
2733  if (!empty($conf->global->WORKFLOW_CAN_CREATE_PURCHASE_ORDER_FROM_SALE_ORDER)) {
2734  if (((!empty($conf->fournisseur->enabled) && empty($conf->global->MAIN_USE_NEW_SUPPLIERMOD)) || !empty($conf->supplier_order->enabled)) && $object->statut > Commande::STATUS_DRAFT && $object->statut < Commande::STATUS_CLOSED && $object->getNbOfServicesLines() > 0) {
2735  if ($usercancreatepurchaseorder) {
2736  print dolGetButtonAction('', $langs->trans('AddPurchaseOrder'), 'default', DOL_URL_ROOT.'/fourn/commande/card.php?action=create&amp;origin='.$object->element.'&amp;originid='.$object->id.'&amp;socid='.$object->socid, '');
2737  }
2738  }
2739  }
2740 
2741  // Create intervention
2742  if (!empty($conf->ficheinter->enabled)) {
2743  $langs->load("interventions");
2744 
2745  if ($object->statut > Commande::STATUS_DRAFT && $object->statut < Commande::STATUS_CLOSED && $object->getNbOfServicesLines() > 0) {
2746  if ($user->rights->ficheinter->creer) {
2747  print dolGetButtonAction('', $langs->trans('AddIntervention'), 'default', DOL_URL_ROOT.'/fichinter/card.php?action=create&amp;origin='.$object->element.'&amp;originid='.$object->id.'&amp;socid='.$object->socid, '');
2748  } else {
2749  print dolGetButtonAction($langs->trans('NotAllowed'), $langs->trans('AddIntervention'), 'default', $_SERVER['PHP_SELF']. '#', '', false);
2750  }
2751  }
2752  }
2753 
2754  // Create contract
2755  if (!empty($conf->contrat->enabled) && ($object->statut == Commande::STATUS_VALIDATED || $object->statut == Commande::STATUS_SHIPMENTONPROCESS || $object->statut == Commande::STATUS_CLOSED)) {
2756  $langs->load("contracts");
2757 
2758  if ($user->rights->contrat->creer) {
2759  print dolGetButtonAction('', $langs->trans('AddContract'), 'default', DOL_URL_ROOT.'/contrat/card.php?action=create&amp;origin='.$object->element.'&amp;originid='.$object->id.'&amp;socid='.$object->socid, '');
2760  }
2761  }
2762 
2763  // Ship
2764  $numshipping = 0;
2765  if (isModEnabled('expedition')) {
2766  $numshipping = $object->nb_expedition();
2767 
2768  if ($object->statut > Commande::STATUS_DRAFT && $object->statut < Commande::STATUS_CLOSED && ($object->getNbOfProductsLines() > 0 || !empty($conf->global->STOCK_SUPPORTS_SERVICES))) {
2769  if ((isModEnabled('expedition_bon') && $user->rights->expedition->creer) || ($conf->delivery_note->enabled && $user->rights->expedition->delivery->creer)) {
2770  if ($user->rights->expedition->creer) {
2771  print dolGetButtonAction('', $langs->trans('CreateShipment'), 'default', DOL_URL_ROOT.'/expedition/shipment.php?id='.$object->id, '');
2772  } else {
2773  print dolGetButtonAction($langs->trans('NotAllowed'), $langs->trans('CreateShipment'), 'default', $_SERVER['PHP_SELF']. '#', '', false);
2774  }
2775  } else {
2776  $langs->load("errors");
2777  print dolGetButtonAction($langs->trans('ErrorModuleSetupNotComplete'), $langs->trans('CreateShipment'), 'default', $_SERVER['PHP_SELF']. '#', '', false);
2778  }
2779  }
2780  }
2781 
2782  // Set to shipped
2783  if (($object->statut == Commande::STATUS_VALIDATED || $object->statut == Commande::STATUS_SHIPMENTONPROCESS) && $usercanclose) {
2784  print dolGetButtonAction('', $langs->trans('ClassifyShipped'), 'default', $_SERVER["PHP_SELF"].'?action=shipped&amp;token='.newToken().'&amp;id='.$object->id, '');
2785  }
2786  // Create bill and Classify billed
2787  // Note: Even if module invoice is not enabled, we should be able to use button "Classified billed"
2788  if ($object->statut > Commande::STATUS_DRAFT && !$object->billed && $object->total_ttc >= 0) {
2789  if (isModEnabled('facture') && $user->rights->facture->creer && empty($conf->global->WORKFLOW_DISABLE_CREATE_INVOICE_FROM_ORDER)) {
2790  print dolGetButtonAction('', $langs->trans('CreateBill'), 'default', DOL_URL_ROOT.'/compta/facture/card.php?action=create&amp;token='.newToken().'&amp;origin='.$object->element.'&amp;originid='.$object->id.'&amp;socid='.$object->socid, '');
2791  }
2792  if ($usercancreate && $object->statut >= Commande::STATUS_VALIDATED && empty($conf->global->WORKFLOW_DISABLE_CLASSIFY_BILLED_FROM_ORDER) && empty($conf->global->WORKFLOW_BILL_ON_SHIPMENT)) {
2793  print dolGetButtonAction('', $langs->trans('ClassifyBilled'), 'default', $_SERVER["PHP_SELF"].'?action=classifybilled&amp;token='.newToken().'&amp;id='.$object->id, '');
2794  }
2795  }
2796  if ($object->statut > Commande::STATUS_DRAFT && $object->billed) {
2797  if ($usercancreate && $object->statut >= Commande::STATUS_VALIDATED && empty($conf->global->WORKFLOW_DISABLE_CLASSIFY_BILLED_FROM_ORDER) && empty($conf->global->WORKFLOW_BILL_ON_SHIPMENT)) {
2798  print dolGetButtonAction('', $langs->trans('ClassifyUnBilled'), 'default', $_SERVER["PHP_SELF"].'?action=classifyunbilled&amp;token='.newToken().'&amp;id='.$object->id, '');
2799  }
2800  }
2801  // Clone
2802  if ($usercancreate) {
2803  print dolGetButtonAction('', $langs->trans('ToClone'), 'default', $_SERVER["PHP_SELF"].'?action=clone&amp;token='.newToken().'&amp;id='.$object->id.'&amp;socid='.$object->socid, '');
2804  }
2805 
2806  // Cancel order
2807  if ($object->statut == Commande::STATUS_VALIDATED && !empty($usercancancel)) {
2808  print '<a class="butActionDelete" href="'.$_SERVER["PHP_SELF"].'?id='.$object->id.'&action=cancel&token='.newToken().'">'.$langs->trans("Cancel").'</a>';
2809  }
2810 
2811  // Delete order
2812  if ($usercandelete) {
2813  if ($numshipping == 0) {
2814  print dolGetButtonAction('', $langs->trans('Delete'), 'delete', $_SERVER["PHP_SELF"].'?action=delete&amp;token='.newToken().'&amp;id='.$object->id, '');
2815  } else {
2816  print dolGetButtonAction($langs->trans('ShippingExist'), $langs->trans('Delete'), 'default', $_SERVER['PHP_SELF']. '#', '', false);
2817  }
2818  }
2819  }
2820  print '</div>';
2821  }
2822 
2823  // Select mail models is same action as presend
2824  if (GETPOST('modelselected')) {
2825  $action = 'presend';
2826  }
2827 
2828  if ($action != 'presend') {
2829  print '<div class="fichecenter"><div class="fichehalfleft">';
2830  print '<a name="builddoc"></a>'; // ancre
2831  // Documents
2832  $objref = dol_sanitizeFileName($object->ref);
2833  $relativepath = $objref.'/'.$objref.'.pdf';
2834  $filedir = $conf->commande->multidir_output[$object->entity].'/'.$objref;
2835  $urlsource = $_SERVER["PHP_SELF"]."?id=".$object->id;
2836  $genallowed = $usercanread;
2837  $delallowed = $usercancreate;
2838  print $formfile->showdocuments('commande', $objref, $filedir, $urlsource, $genallowed, $delallowed, $object->model_pdf, 1, 0, 0, 28, 0, '', '', '', $soc->default_lang, '', $object);
2839 
2840 
2841  // Show links to link elements
2842  $linktoelem = $form->showLinkToObjectBlock($object, null, array('order'));
2843 
2844  $compatibleImportElementsList = false;
2845  if ($usercancreate
2846  && $object->statut == Commande::STATUS_DRAFT) {
2847  $compatibleImportElementsList = array('commande', 'propal'); // import from linked elements
2848  }
2849  $somethingshown = $form->showLinkedObjectBlock($object, $linktoelem, $compatibleImportElementsList);
2850 
2851  // Show online payment link
2852  $useonlinepayment = (!empty($conf->paypal->enabled) || !empty($conf->stripe->enabled) || !empty($conf->paybox->enabled));
2853  if (!empty($conf->global->ORDER_HIDE_ONLINE_PAYMENT_ON_ORDER)) {
2854  $useonlinepayment = 0;
2855  }
2856  if ($object->statut != Commande::STATUS_DRAFT && $useonlinepayment) {
2857  print '<br><!-- Link to pay -->';
2858  require_once DOL_DOCUMENT_ROOT.'/core/lib/payments.lib.php';
2859  print showOnlinePaymentUrl('order', $object->ref).'<br>';
2860  }
2861 
2862  print '</div><div class="fichehalfright">';
2863 
2864  // List of actions on element
2865  include_once DOL_DOCUMENT_ROOT.'/core/class/html.formactions.class.php';
2866  $formactions = new FormActions($db);
2867  $somethingshown = $formactions->showactions($object, 'order', $socid, 1);
2868 
2869  print '</div></div>';
2870  }
2871 
2872  // Presend form
2873  $modelmail = 'order_send';
2874  $defaulttopic = 'SendOrderRef';
2875  $diroutput = $conf->commande->multidir_output[$object->entity];
2876  $trackid = 'ord'.$object->id;
2877 
2878  include DOL_DOCUMENT_ROOT.'/core/tpl/card_presend.tpl.php';
2879  }
2880 }
2881 
2882 // End of page
2883 llxFooter();
2884 $db->close();
if(!function_exists('dol_getprefix')) dol_include_once($relpath, $classname= '')
Make an include_once using default root and alternate root if it fails.
File of class to manage predefined price products or services by customer.
GETPOST($paramname, $check= 'alphanohtml', $method=0, $filter=null, $options=null, $noreplace=0)
Return value of a param into GET or POST supervariable.
getDictionaryValue($tablename, $field, $id, $checkentity=false, $rowidfield= 'rowid')
Return the value of a filed into a dictionary for the record $id.
getDolGlobalInt($key, $default=0)
Return dolibarr global constant int value.
Class to manage notifications.
img_edit($titlealt= 'default', $float=0, $other= '')
Show logo editer/modifier fiche.
if(preg_match('/set_([a-z0-9_\-]+)/i', $action, $reg)) if(preg_match('/del_([a-z0-9_\-]+)/i', $action, $reg)) if($action== 'set') elseif($action== 'specimen') elseif($action== 'setmodel') elseif($action== 'del') elseif($action== 'setdoc') $formactions
View.
const STATUS_CLOSED
Closed (Sent, billed or not)
if($cancel &&!$id) if($action== 'add'&&!$cancel) if($action== 'delete') if($id) $form
Actions.
Definition: card.php:142
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...
static createDepositFromOrigin(CommonObject $origin, $date, $payment_terms_id, User $user, $notrigger=0, $autoValidateDeposit=false, $overrideFields=array())
Creates a deposit from a proposal or an order by grouping lines by VAT rates.
Class to manage building of HTML components.
Class to manage products or services.
dol_now($mode= 'auto')
Return date for now.
Class to manage Dolibarr users.
Definition: user.class.php:44
if(!defined('NOREQUIRESOC')) if(!defined('NOREQUIRETRAN')) if(!defined('NOCSRFCHECK')) if(!defined('NOTOKENRENEWAL')) if(!defined('NOREQUIREMENU')) if(!defined('NOREQUIREHTML')) if(!defined('NOREQUIREAJAX')) llxHeader()
Empty header.
Definition: wrapper.php:59
setEventMessage($mesgs, $style= 'mesgs')
Set event message in dol_events session object.
dol_clone($object, $native=0)
Create a clone of instance of object (new instance with same value for properties) With native = 0: P...
dolGetButtonAction($label, $html= '', $actionType= 'default', $url= '', $id= '', $userRight=1, $params=array())
Function dolGetButtonAction.
const STATUS_SHIPMENTONPROCESS
Shipment on process.
get_default_npr(Societe $thirdparty_seller, Societe $thirdparty_buyer, $idprod=0, $idprodfournprice=0)
Fonction qui renvoie si tva doit etre tva percue recuperable.
dol_concatdesc($text1, $text2, $forxml=false, $invert=false)
Concat 2 descriptions with a new line between them (second operand after first one with appropriate n...
get_localtax($vatrate, $local, $thirdparty_buyer="", $thirdparty_seller="", $vatnpr=0)
Return localtax rate for a particular vat, when selling a product with vat $vatrate, from a $thirdparty_buyer to a $thirdparty_seller Note: This function applies same rules than get_default_tva.
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:116
price($amount, $form=0, $outlangs= '', $trunc=1, $rounding=-1, $forcerounding=-1, $currency_code= '')
Function to format a value into an amount for visual output Function used into PDF and HTML pages...
Class with static methods for building HTML components related to products Only components common to ...
static getIdAndTxFromCode($dbs, $code, $date_document= '')
Get id and rate of currency from code.
Class to manage standard extra fields.
setEventMessages($mesg, $mesgs, $style= 'mesgs', $messagekey= '')
Set event messages in dol_events session object.
showDimensionInBestUnit($dimension, $unit, $type, $outputlangs, $round=-1, $forceunitoutput= 'no', $use_short_label=0)
Output a dimension with best unit.
Class to manage generation of HTML components Only common components must be here.
GETPOSTISSET($paramname)
Return true if we are in a context of submitting the parameter $paramname from a POST of a form...
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.
price2num($amount, $rounding= '', $option=0)
Function that return a number with universal decimal format (decimal separator is &#39;...
Class to manage HTML output components for orders Before adding component here, check they are not in...
Classe permettant la generation de composants html autre Only common components are here...
Class to manage building of HTML components.
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 customers orders.
const STATUS_DRAFT
Draft status.
dol_syslog($message, $level=LOG_INFO, $ident=0, $suffixinfilename= '', $restricttologhandler= '', $logcontext=null)
Write log message into outputs.
Class to manage translations.
dol_sanitizeFileName($str, $newstr= '_', $unaccent=1)
Clean a string to use it as a file name.
Class ProductCombination Used to represent a product combination.
Class to offer components to list and upload files.
restrictedArea($user, $features, $objectid=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.
commande_prepare_head(Commande $object)
Prepare array with list of tabs.
Definition: order.lib.php:34
const STATUS_VALIDATED
Validated status.
const TYPE_DEPOSIT
Deposit invoice.
dol_get_fiche_head($links=array(), $active= '', $title= '', $notab=0, $picto= '', $pictoisfullpath=0, $morehtmlright= '', $morecss= '', $limittoshow=0, $moretabssuffix= '')
Show tabs of a record.
dol_print_date($time, $format= '', $tzoutput= 'auto', $outputlangs= '', $encodetooutput=false)
Output date in a string format according to outputlangs (or langs if not defined).
dol_htmlcleanlastbr($stringtodecode)
This function remove all ending and br at end.
dol_print_error($db= '', $error= '', $errors=null)
Displays error message system with all the information to facilitate the diagnosis and the escalation...
get_default_tva(Societe $thirdparty_seller, Societe $thirdparty_buyer, $idprod=0, $idprodfournprice=0)
Function that return vat rate of a product line (according to seller, buyer and product vat rate) VAT...
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.
isModEnabled($module)
Is Dolibarr module enabled.
Class to manage a WYSIWYG editor.
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:73
$formconfirm
if ($action == &#39;delbookkeepingyear&#39;) {
getCountry($searchkey, $withcode= '', $dbtouse=0, $outputlangs= '', $entconv=1, $searchlabel= '')
Return country label, code or id from an id, code or label.
static liste_modeles($db, $maxfilenamelength=0)
Return list of active generation modules.
const STATUS_CANCELED
Canceled status.