dolibarr 20.0.2
card.php
Go to the documentation of this file.
1<?php
2/* Copyright (C) 2002-2005 Rodolphe Quiedeville <rodolphe@quiedeville.org>
3 * Copyright (C) 2004-2020 Laurent Destailleur <eldy@users.sourceforge.net>
4 * Copyright (C) 2004 Christophe Combelles <ccomb@free.fr>
5 * Copyright (C) 2005 Marc Barilley <marc@ocebo.fr>
6 * Copyright (C) 2005-2013 Regis Houssin <regis.houssin@inodbox.com>
7 * Copyright (C) 2010-2023 Juanjo Menent <jmenent@simnandez.es>
8 * Copyright (C) 2013-2022 Philippe Grand <philippe.grand@atoo-net.com>
9 * Copyright (C) 2013 Florian Henry <florian.henry@open-concept.pro>
10 * Copyright (C) 2014-2016 Marcos García <marcosgdf@gmail.com>
11 * Copyright (C) 2016-2023 Alexandre Spangaro <aspangaro@open-dsi.fr>
12 * Copyright (C) 2018-2024 Frédéric France <frederic.france@free.fr>
13 * Copyright (C) 2019 Ferran Marcet <fmarcet@2byte.es>
14 * Copyright (C) 2022 Gauthier VERDOL <gauthier.verdol@atm-consulting.fr>
15 * Copyright (C) 2023 Nick Fragoulis
16 * Copyright (C) 2024 MDW <mdeweerd@users.noreply.github.com>
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// Load Dolibarr environment
39require '../../main.inc.php';
40require_once DOL_DOCUMENT_ROOT.'/core/class/html.formfile.class.php';
41require_once DOL_DOCUMENT_ROOT.'/fourn/class/fournisseur.class.php';
42require_once DOL_DOCUMENT_ROOT.'/core/modules/supplier_invoice/modules_facturefournisseur.php';
43require_once DOL_DOCUMENT_ROOT.'/fourn/class/fournisseur.facture.class.php';
44require_once DOL_DOCUMENT_ROOT.'/fourn/class/fournisseur.facture-rec.class.php';
45require_once DOL_DOCUMENT_ROOT.'/fourn/class/paiementfourn.class.php';
46require_once DOL_DOCUMENT_ROOT.'/core/class/discount.class.php';
47require_once DOL_DOCUMENT_ROOT.'/core/lib/fourn.lib.php';
48require_once DOL_DOCUMENT_ROOT.'/core/lib/files.lib.php';
49require_once DOL_DOCUMENT_ROOT.'/core/lib/date.lib.php';
50require_once DOL_DOCUMENT_ROOT.'/core/class/doleditor.class.php';
51if (isModEnabled("product")) {
52 require_once DOL_DOCUMENT_ROOT.'/product/class/product.class.php';
53 require_once DOL_DOCUMENT_ROOT.'/core/lib/product.lib.php';
54}
55if (isModEnabled('project')) {
56 require_once DOL_DOCUMENT_ROOT.'/projet/class/project.class.php';
57 require_once DOL_DOCUMENT_ROOT.'/core/class/html.formprojet.class.php';
58}
59
60if (isModEnabled('variants')) {
61 require_once DOL_DOCUMENT_ROOT.'/variants/class/ProductCombination.class.php';
62}
63if (isModEnabled('accounting')) {
64 require_once DOL_DOCUMENT_ROOT.'/accountancy/class/accountingjournal.class.php';
65}
66
67
68$langs->loadLangs(array('bills', 'compta', 'suppliers', 'companies', 'products', 'banks', 'admin'));
69if (isModEnabled('incoterm')) {
70 $langs->load('incoterm');
71}
72
73$id = (GETPOSTINT('facid') ? GETPOSTINT('facid') : GETPOSTINT('id'));
74
75$action = GETPOST('action', 'aZ09');
76$confirm = GETPOST("confirm");
77$ref = GETPOST('ref', 'alpha');
78$cancel = GETPOST('cancel', 'alpha');
79$backtopage = GETPOST('backtopage', 'alpha');
80$backtopageforcancel = '';
81
82$lineid = GETPOSTINT('lineid');
83$projectid = GETPOSTINT('projectid');
84$origin = GETPOST('origin', 'alpha');
85$originid = GETPOSTINT('originid');
86$fac_recid = GETPOSTINT('fac_rec');
87$rank = (GETPOSTINT('rank') > 0) ? GETPOSTINT('rank') : -1;
88
89// PDF
90$hidedetails = (GETPOSTINT('hidedetails') ? GETPOSTINT('hidedetails') : (getDolGlobalString('MAIN_GENERATE_DOCUMENTS_HIDE_DETAILS') ? 1 : 0));
91$hidedesc = (GETPOSTINT('hidedesc') ? GETPOSTINT('hidedesc') : (getDolGlobalString('MAIN_GENERATE_DOCUMENTS_HIDE_DESC') ? 1 : 0));
92$hideref = (GETPOSTINT('hideref') ? GETPOSTINT('hideref') : (getDolGlobalString('MAIN_GENERATE_DOCUMENTS_HIDE_REF') ? 1 : 0));
93
94// Initialize technical object to manage hooks of page. Note that conf->hooks_modules contains array of hook context
95$hookmanager->initHooks(array('invoicesuppliercard', 'globalcard'));
96
98$extrafields = new ExtraFields($db);
99
100// fetch optionals attributes and labels
101$extrafields->fetch_name_optionals_label($object->table_element);
102
103// Load object
104if ($id > 0 || !empty($ref)) {
105 $ret = $object->fetch($id, $ref);
106 if ($ret < 0) {
107 dol_print_error($db, $object->error);
108 }
109 $ret = $object->fetch_thirdparty();
110 if ($ret < 0) {
111 dol_print_error($db, $object->error);
112 }
113}
114
115// Security check
116$socid = GETPOSTINT('socid');
117if (!empty($user->socid)) {
118 $socid = $user->socid;
119}
120
121$isdraft = (($object->status == FactureFournisseur::STATUS_DRAFT) ? 1 : 0);
122$result = restrictedArea($user, 'fournisseur', $id, 'facture_fourn', 'facture', 'fk_soc', 'rowid', $isdraft);
123
124// Common permissions
125$usercanread = ($user->hasRight("fournisseur", "facture", "lire") || $user->hasRight("supplier_invoice", "lire"));
126$usercancreate = ($user->hasRight("fournisseur", "facture", "creer") || $user->hasRight("supplier_invoice", "creer"));
127$usercandelete = ($user->hasRight("fournisseur", "facture", "supprimer") || $user->hasRight("supplier_invoice", "supprimer"));
128$usercancreatecontract = $user->hasRight("contrat", "creer");
129
130// Advanced permissions
131$usercanvalidate = ((!getDolGlobalString('MAIN_USE_ADVANCED_PERMS') && !empty($usercancreate)) || (getDolGlobalString('MAIN_USE_ADVANCED_PERMS') && $user->hasRight("fournisseur", "supplier_invoice_advance", "validate")));
132$usercansend = (!getDolGlobalString('MAIN_USE_ADVANCED_PERMS') || $user->hasRight("fournisseur", "supplier_invoice_advance", "send"));
133
134// Permissions for includes
135$permissionnote = $usercancreate; // Used by the include of actions_setnotes.inc.php
136$permissiondellink = $usercancreate; // Used by the include of actions_dellink.inc.php
137$permissiontoedit = $usercancreate; // Used by the include of actions_lineupdown.inc.php
138$permissiontoadd = $usercancreate; // Used by the include of actions_addupdatedelete.inc.php and actions_lineupdown.inc.php
139$permissiontodelete = $usercandelete;
140
141$error = 0;
142
143
144/*
145 * Actions
146 */
147
148$parameters = array('socid' => $socid);
149$reshook = $hookmanager->executeHooks('doActions', $parameters, $object, $action); // Note that $action and $object may have been modified by some hooks
150if ($reshook < 0) {
151 setEventMessages($hookmanager->error, $hookmanager->errors, 'errors');
152}
153
154if (empty($reshook)) {
155 $backurlforlist = DOL_URL_ROOT.'/fourn/facture/list.php';
156
157 if (empty($backtopage) || ($cancel && empty($id))) {
158 if (empty($backtopage) || ($cancel && strpos($backtopage, '__ID__'))) {
159 if (empty($id) && (($action != 'add' && $action != 'create') || $cancel)) {
160 $backtopage = $backurlforlist;
161 } else {
162 $backtopage = DOL_URL_ROOT.'/fourn/facture/card.php?id='.((!empty($id) && $id > 0) ? $id : '__ID__');
163 }
164 }
165 }
166
167 if ($cancel) {
168 if (!empty($backtopageforcancel)) {
169 header("Location: ".$backtopageforcancel);
170 exit;
171 } elseif (!empty($backtopage)) {
172 header("Location: ".$backtopage);
173 exit;
174 }
175 $action = '';
176 }
177
178 include DOL_DOCUMENT_ROOT.'/core/actions_setnotes.inc.php'; // Must be include, not include_once
179
180 include DOL_DOCUMENT_ROOT.'/core/actions_dellink.inc.php'; // Must be include, not include_once
181
182 include DOL_DOCUMENT_ROOT.'/core/actions_lineupdown.inc.php'; // Must be include, not include_once
183
184 // Link invoice to order
185 if (GETPOST('linkedOrder') && empty($cancel) && $id > 0 && $permissiontoadd) {
186 $object->fetch($id);
187 $object->fetch_thirdparty();
188 $result = $object->add_object_linked('order_supplier', GETPOST('linkedOrder'));
189 }
190
191 // Action clone object
192 if ($action == 'confirm_clone' && $confirm == 'yes' && $permissiontoadd) {
193 $objectutil = dol_clone($object, 1); // To avoid to denaturate loaded object when setting some properties for clone. We use native clone to keep this->db valid.
194 '@phan-var-force FactureFournisseur $objectutil'; // Same object type for cloned object
195
196 if (GETPOST('newsupplierref', 'alphanohtml')) {
197 $objectutil->ref_supplier = GETPOST('newsupplierref', 'alphanohtml');
198 }
199 $objectutil->date = dol_mktime(12, 0, 0, GETPOSTINT('newdatemonth'), GETPOSTINT('newdateday'), GETPOSTINT('newdateyear'));
200
201 $result = $objectutil->createFromClone($user, $id);
202 if ($result > 0) {
203 header("Location: ".$_SERVER['PHP_SELF'].'?id='.$result);
204 exit;
205 } else {
206 $langs->load("errors");
207 setEventMessages($objectutil->error, $objectutil->errors, 'errors');
208 $action = '';
209 }
210 } elseif ($action == 'confirm_valid' && $confirm == 'yes' && $usercanvalidate) {
211 $idwarehouse = GETPOST('idwarehouse');
212
213 $object->fetch($id);
214 $object->fetch_thirdparty();
215
216 $qualified_for_stock_change = 0;
217 if (!getDolGlobalString('STOCK_SUPPORTS_SERVICES')) {
218 $qualified_for_stock_change = $object->hasProductsOrServices(2);
219 } else {
220 $qualified_for_stock_change = $object->hasProductsOrServices(1);
221 }
222
223 // Check parameters
224 if (isModEnabled('stock') && getDolGlobalString('STOCK_CALCULATE_ON_SUPPLIER_BILL') && $qualified_for_stock_change) {
225 $langs->load("stocks");
226 if (!$idwarehouse || $idwarehouse == -1) {
227 $error++;
228 setEventMessages($langs->trans('ErrorFieldRequired', $langs->transnoentitiesnoconv("Warehouse")), null, 'errors');
229 $action = '';
230 }
231 }
232
233 if (!$error) {
234 $db->begin();
235
236 $result = $object->validate($user, '', $idwarehouse);
237 if ($result < 0) {
238 $db->rollback();
239
240 setEventMessages($object->error, $object->errors, 'errors');
241 } else {
242 $db->commit();
243
244 // Define output language
245 if (!getDolGlobalString('MAIN_DISABLE_PDF_AUTOUPDATE')) {
246 $outputlangs = $langs;
247 $newlang = '';
248 if (getDolGlobalInt('MAIN_MULTILANGS') && empty($newlang) && GETPOST('lang_id', 'aZ09')) {
249 $newlang = GETPOST('lang_id', 'aZ09');
250 }
251 if (getDolGlobalInt('MAIN_MULTILANGS') && empty($newlang)) {
252 $newlang = $object->thirdparty->default_lang;
253 }
254 if (!empty($newlang)) {
255 $outputlangs = new Translate("", $conf);
256 $outputlangs->setDefaultLang($newlang);
257 }
258 $model = $object->model_pdf;
259 $ret = $object->fetch($id); // Reload to get new records
260
261 $result = $object->generateDocument($model, $outputlangs, $hidedetails, $hidedesc, $hideref);
262 if ($result < 0) {
263 dol_print_error($db, $result);
264 }
265 }
266 }
267 }
268 } elseif ($action == 'confirm_delete' && $confirm == 'yes' && $permissiontodelete) {
269 $object->fetch($id);
270 $object->fetch_thirdparty();
271
272 $isErasable = $object->is_erasable();
273
274 if (($usercandelete && $isErasable > 0) || ($usercancreate && $isErasable == 1)) {
275 $revertstock = GETPOST('revertstock');
276
277 if ($revertstock) {
278 $idwarehouse = GETPOST('idwarehouse');
279
280 $qualified_for_stock_change = 0;
281 if (!getDolGlobalString('STOCK_SUPPORTS_SERVICES')) {
282 $qualified_for_stock_change = $object->hasProductsOrServices(2);
283 } else {
284 $qualified_for_stock_change = $object->hasProductsOrServices(1);
285 }
286
287 // Check parameters
288 if (isModEnabled('stock') && getDolGlobalString('STOCK_CALCULATE_ON_SUPPLIER_BILL') && $qualified_for_stock_change) {
289 $langs->load("stocks");
290 if (!$idwarehouse || $idwarehouse == -1) {
291 $error++;
292 setEventMessages($langs->trans('ErrorFieldRequired', $langs->transnoentitiesnoconv("Warehouse")), null, 'errors');
293 $action = 'delete';
294 } else {
295 $result = $object->setDraft($user, $idwarehouse);
296 if ($result < 0) {
297 $error++;
298 }
299 }
300 }
301 }
302
303 if (!$error) {
304 $result = $object->delete($user);
305 if ($result > 0) {
306 header('Location: list.php?restore_lastsearch_values=1');
307 exit;
308 } else {
309 setEventMessages($object->error, $object->errors, 'errors');
310 }
311 }
312 }
313 } elseif ($action == 'confirm_deleteline' && $confirm == 'yes' && $usercancreate) {
314 // Remove a product line
315 $result = $object->deleteLine($lineid);
316 if ($result > 0) {
317 // reorder lines
318 $object->line_order(true);
319 // Define output language
320 /*$outputlangs = $langs;
321 $newlang = '';
322 if (getDolGlobalInt('MAIN_MULTILANGS') && empty($newlang) && GETPOST('lang_id','aZ09'))
323 $newlang = GETPOST('lang_id','aZ09');
324 if (getDolGlobalInt('MAIN_MULTILANGS') && empty($newlang))
325 $newlang = $object->thirdparty->default_lang;
326 if (!empty($newlang)) {
327 $outputlangs = new Translate("", $conf);
328 $outputlangs->setDefaultLang($newlang);
329 }
330 if (!getDolGlobalStringempty('MAIN_DISABLE_PDF_AUTOUPDATE')) {
331 $ret = $object->fetch($object->id); // Reload to get new records
332 $object->generateDocument($object->model_pdf, $outputlangs, $hidedetails, $hidedesc, $hideref);
333 }*/
334
335 header('Location: '.$_SERVER["PHP_SELF"].'?id='.$object->id);
336 exit;
337 } else {
338 setEventMessages($object->error, $object->errors, 'errors');
339 /* Fix bug 1485 : Reset action to avoid asking again confirmation on failure */
340 $action = '';
341 }
342 } elseif ($action == 'unlinkdiscount' && $usercancreate) {
343 // Delete link of credit note to invoice
344 $discount = new DiscountAbsolute($db);
345 $result = $discount->fetch(GETPOSTINT("discountid"));
346 $discount->unlink_invoice();
347 } elseif ($action == 'confirm_paid' && $confirm == 'yes' && $usercancreate) {
348 $object->fetch($id);
349 $result = $object->setPaid($user);
350 if ($result < 0) {
351 setEventMessages($object->error, $object->errors, 'errors');
352 }
353 } elseif ($action == 'confirm_paid_partially' && $confirm == 'yes' && $usercancreate) {
354 // Classif "paid partially"
355 $object->fetch($id);
356 $close_code = GETPOST("close_code", 'restricthtml');
357 $close_note = GETPOST("close_note", 'restricthtml');
358 if ($close_code) {
359 $result = $object->setPaid($user, $close_code, $close_note);
360 if ($result < 0) {
361 setEventMessages($object->error, $object->errors, 'errors');
362 }
363 } else {
364 setEventMessages($langs->trans("ErrorFieldRequired", $langs->transnoentitiesnoconv("Reason")), null, 'errors');
365 }
366 } elseif ($action == 'confirm_canceled' && $confirm == 'yes' && $usercancreate) {
367 // Classify "abandoned"
368 $object->fetch($id);
369 $close_code = GETPOST("close_code", 'restricthtml');
370 $close_note = GETPOST("close_note", 'restricthtml');
371 if ($close_code) {
372 $result = $object->setCanceled($user, $close_code, $close_note);
373 if ($result < 0) {
374 setEventMessages($object->error, $object->errors, 'errors');
375 }
376 } else {
377 setEventMessages($langs->trans("ErrorFieldRequired", $langs->transnoentitiesnoconv("Reason")), null, 'errors');
378 }
379 }
380
381 // Set supplier ref
382 if ($action == 'setref_supplier' && $usercancreate) {
383 $object->ref_supplier = GETPOST('ref_supplier', 'alpha');
384
385 if ($object->update($user) < 0) {
386 setEventMessages($object->error, $object->errors, 'errors');
387 } else {
388 // Define output language
389 $outputlangs = $langs;
390 $newlang = '';
391 if (getDolGlobalInt('MAIN_MULTILANGS') && empty($newlang) && GETPOST('lang_id', 'aZ09')) {
392 $newlang = GETPOST('lang_id', 'aZ09');
393 }
394 if (getDolGlobalInt('MAIN_MULTILANGS') && empty($newlang)) {
395 $newlang = $object->thirdparty->default_lang;
396 }
397 if (!empty($newlang)) {
398 $outputlangs = new Translate("", $conf);
399 $outputlangs->setDefaultLang($newlang);
400 }
401 if (!getDolGlobalString('MAIN_DISABLE_PDF_AUTOUPDATE')) {
402 $ret = $object->fetch($object->id); // Reload to get new records
403 $object->generateDocument($object->model_pdf, $outputlangs, $hidedetails, $hidedesc, $hideref);
404 }
405 }
406 }
407
408 // payments conditions
409 if ($action == 'setconditions' && $usercancreate) {
410 $object->fetch($id);
411 $object->cond_reglement_code = 0; // To clean property
412 $object->cond_reglement_id = 0; // To clean property
413
414 $error = 0;
415
416 $db->begin();
417
418 if (!$error) {
419 $result = $object->setPaymentTerms(GETPOSTINT('cond_reglement_id'));
420 if ($result < 0) {
421 $error++;
422 setEventMessages($object->error, $object->errors, 'errors');
423 }
424 }
425
426 if (!$error) {
427 $new_date_echeance = $object->calculate_date_lim_reglement();
428 if ($new_date_echeance) {
429 $object->date_echeance = $new_date_echeance;
430 }
431 if ($object->date_echeance < $object->date) {
432 $object->date_echeance = $object->date;
433 }
434 $result = $object->update($user);
435 if ($result < 0) {
436 $error++;
437 setEventMessages($object->error, $object->errors, 'errors');
438 }
439 }
440
441 if ($error) {
442 $db->rollback();
443 } else {
444 $db->commit();
445 }
446 } elseif ($action == 'set_incoterms' && isModEnabled('incoterm') && $usercancreate) {
447 // Set incoterm
448 $result = $object->setIncoterms(GETPOSTINT('incoterm_id'), GETPOST('location_incoterms'));
449 } elseif ($action == 'setmode' && $usercancreate) {
450 // payment mode
451 $result = $object->setPaymentMethods(GETPOSTINT('mode_reglement_id'));
452 } elseif ($action == 'setmulticurrencycode' && $usercancreate) {
453 // Multicurrency Code
454 $result = $object->setMulticurrencyCode(GETPOST('multicurrency_code', 'alpha'));
455 } elseif ($action == 'setmulticurrencyrate' && $usercancreate) {
456 // Multicurrency rate
457 $result = $object->setMulticurrencyRate(price2num(GETPOST('multicurrency_tx', 'alpha')), GETPOSTINT('calculation_mode'));
458 } elseif ($action == 'setbankaccount' && $usercancreate) {
459 // bank account
460 $result = $object->setBankAccount(GETPOSTINT('fk_account'));
461 } elseif ($action == 'setvatreversecharge' && $usercancreate) {
462 // vat reverse charge
463 $vatreversecharge = GETPOST('vat_reverse_charge') == 'on' ? 1 : 0;
464 $result = $object->setVATReverseCharge($vatreversecharge);
465 }
466
467 if ($action == 'settransportmode' && $usercancreate) {
468 // transport mode
469 $result = $object->setTransportMode(GETPOSTINT('transport_mode_id'));
470 } elseif ($action == 'setlabel' && $usercancreate) {
471 // Set label
472 $object->fetch($id);
473 $object->label = GETPOST('label');
474 $result = $object->update($user);
475 if ($result < 0) {
476 dol_print_error($db);
477 }
478 } elseif ($action == 'setdatef' && $usercancreate) {
479 $newdate = dol_mktime(0, 0, 0, GETPOSTINT('datefmonth'), GETPOSTINT('datefday'), GETPOSTINT('datefyear'), 'tzserver');
480 if ($newdate > (dol_now('tzuserrel') + getDolGlobalInt('INVOICE_MAX_FUTURE_DELAY'))) {
481 if (!getDolGlobalString('INVOICE_MAX_FUTURE_DELAY')) {
482 setEventMessages($langs->trans("WarningInvoiceDateInFuture"), null, 'warnings');
483 } else {
484 setEventMessages($langs->trans("WarningInvoiceDateTooFarInFuture"), null, 'warnings');
485 }
486 }
487
488 $object->fetch($id);
489
490 $object->date = $newdate;
491 $date_echence_calc = $object->calculate_date_lim_reglement();
492 if (!empty($object->date_echeance)) {
493 $object->date_echeance = $date_echence_calc;
494 }
495 if ($object->date_echeance && $object->date_echeance < $object->date) {
496 $object->date_echeance = $object->date;
497 }
498
499 $result = $object->update($user);
500 if ($result < 0) {
501 dol_print_error($db, $object->error);
502 }
503 } elseif ($action == 'setdate_lim_reglement' && $usercancreate) {
504 $object->fetch($id);
505 $object->date_echeance = dol_mktime(12, 0, 0, GETPOSTINT('date_lim_reglementmonth'), GETPOSTINT('date_lim_reglementday'), GETPOSTINT('date_lim_reglementyear'));
506 if (!empty($object->date_echeance) && $object->date_echeance < $object->date) {
507 $object->date_echeance = $object->date;
508 setEventMessages($langs->trans("DatePaymentTermCantBeLowerThanObjectDate"), null, 'warnings');
509 }
510 $result = $object->update($user);
511 if ($result < 0) {
512 dol_print_error($db, $object->error);
513 }
514 } elseif ($action == "setabsolutediscount" && $usercancreate) {
515 $db->begin();
516 // We use the credit to reduce amount of invoice
517 if (GETPOSTINT("remise_id")) {
518 $ret = $object->fetch($id);
519 if ($ret > 0) {
520 $result = $object->insert_discount(GETPOSTINT("remise_id"));
521 if ($result < 0) {
522 setEventMessages($object->error, $object->errors, 'errors');
523 }
524 } else {
525 dol_print_error($db, $object->error);
526 }
527 }
528 // We use the credit to reduce remain to pay
529 if (GETPOSTINT("remise_id_for_payment")) {
530 require_once DOL_DOCUMENT_ROOT.'/core/class/discount.class.php';
531 $discount = new DiscountAbsolute($db);
532 $discount->fetch(GETPOSTINT("remise_id_for_payment"));
533
534 //var_dump($object->getRemainToPay(0));
535 //var_dump($discount->amount_ttc);exit;
536 $remaintopay = $object->getRemainToPay(0);
537 if (price2num($discount->amount_ttc) > price2num($remaintopay)) {
538 // TODO Split the discount in 2 automatically
539 $error++;
540 setEventMessages($langs->trans("ErrorDiscountLargerThanRemainToPaySplitItBefore"), null, 'errors');
541 }
542
543 if (!$error) {
544 $result = $discount->link_to_invoice(0, $id);
545 if ($result < 0) {
546 $error++;
547 setEventMessages($discount->error, $discount->errors, 'errors');
548 }
549 }
550 if (!$error) {
551 $newremaintopay = $object->getRemainToPay(0);
552 if ($newremaintopay == 0) {
553 $object->setPaid($user);
554 }
555 }
556 }
557 if (!$error) {
558 $db->commit();
559 } else {
560 $db->rollback();
561 }
562 if (empty($error) && !getDolGlobalString('MAIN_DISABLE_PDF_AUTOUPDATE')) {
563 $outputlangs = $langs;
564 $newlang = '';
565 if (getDolGlobalInt('MAIN_MULTILANGS') && empty($newlang) && GETPOST('lang_id', 'aZ09')) {
566 $newlang = GETPOST('lang_id', 'aZ09');
567 }
568 if (getDolGlobalInt('MAIN_MULTILANGS') && empty($newlang)) {
569 $newlang = $object->thirdparty->default_lang;
570 }
571 if (!empty($newlang)) {
572 $outputlangs = new Translate("", $conf);
573 $outputlangs->setDefaultLang($newlang);
574 }
575 $ret = $object->fetch($id); // Reload to get new records
576
577 $result = $object->generateDocument($object->model_pdf, $outputlangs, $hidedetails, $hidedesc, $hideref);
578 if ($result < 0) {
579 setEventMessages($object->error, $object->errors, 'errors');
580 }
581 }
582 } elseif ($action == 'confirm_converttoreduc' && $confirm == 'yes' && $usercancreate) {
583 // Convertir en reduc
584 $object->fetch($id);
585 $object->fetch_thirdparty();
586 //$object->fetch_lines(); // Already done into fetch
587
588 // Check if there is already a discount (protection to avoid duplicate creation when resubmit post)
589 $discountcheck = new DiscountAbsolute($db);
590 $result = $discountcheck->fetch(0, 0, $object->id);
591
592 $canconvert = 0;
593 if ($object->type == FactureFournisseur::TYPE_DEPOSIT && empty($discountcheck->id)) {
594 $canconvert = 1; // we can convert deposit into discount if deposit is paid (completely, partially or not at all) and not already converted (see real condition into condition used to show button converttoreduc)
595 }
596 if (($object->type == FactureFournisseur::TYPE_CREDIT_NOTE || $object->type == FactureFournisseur::TYPE_STANDARD) && $object->paid == 0 && empty($discountcheck->id)) {
597 $canconvert = 1; // we can convert credit note into discount if credit note is not refunded completely and not already converted and amount of payment is 0 (see also the real condition used as the condition to show button converttoreduc)
598 }
599 if ($canconvert) {
600 $db->begin();
601
602 $amount_ht = $amount_tva = $amount_ttc = array();
603 $multicurrency_amount_ht = $multicurrency_amount_tva = $multicurrency_amount_ttc = array();
604
605 // Loop on each vat rate
606 $i = 0;
607 foreach ($object->lines as $line) {
608 if ($line->product_type < 9 && $line->total_ht != 0) { // Remove lines with product_type greater than or equal to 9 and no need to create discount if amount is null
609 $keyforvatrate = $line->tva_tx.($line->vat_src_code ? ' ('.$line->vat_src_code.')' : '');
610
611 $amount_ht[$keyforvatrate] += $line->total_ht;
612 $amount_tva[$keyforvatrate] += $line->total_tva;
613 $amount_ttc[$keyforvatrate] += $line->total_ttc;
614 $multicurrency_amount_ht[$keyforvatrate] += $line->multicurrency_total_ht;
615 $multicurrency_amount_tva[$keyforvatrate] += $line->multicurrency_total_tva;
616 $multicurrency_amount_ttc[$keyforvatrate] += $line->multicurrency_total_ttc;
617 $i++;
618 }
619 }
620 '@phan-var-force array<string,float> $amount_ht
621 @phan-var-force array<string,float> $amount_tva
622 @phan-var-force array<string,float> $amount_ttc
623 @phan-var-force array<string,float> $multicurrency_amount_ht
624 @phan-var-force array<string,float> $multicurrency_amount_tva
625 @phan-var-force array<string,float> $multicurrency_amount_ttc';
626
627 // If some payments were already done, we change the amount to pay using same prorate
628 if (getDolGlobalString('SUPPLIER_INVOICE_ALLOW_REUSE_OF_CREDIT_WHEN_PARTIALLY_REFUNDED') && $object->type == FactureFournisseur::TYPE_CREDIT_NOTE) {
629 $alreadypaid = $object->getSommePaiement(); // This can be not 0 if we allow to create credit to reuse from credit notes partially refunded.
630 if ($alreadypaid && abs($alreadypaid) < abs($object->total_ttc)) {
631 $ratio = abs(($object->total_ttc - $alreadypaid) / $object->total_ttc);
632 foreach ($amount_ht as $vatrate => $val) {
633 $amount_ht[$vatrate] = price2num($amount_ht[$vatrate] * $ratio, 'MU');
634 $amount_tva[$vatrate] = price2num($amount_tva[$vatrate] * $ratio, 'MU');
635 $amount_ttc[$vatrate] = price2num($amount_ttc[$vatrate] * $ratio, 'MU');
636 $multicurrency_amount_ht[$vatrate] = price2num($multicurrency_amount_ht[$vatrate] * $ratio, 'MU');
637 $multicurrency_amount_tva[$vatrate] = price2num($multicurrency_amount_tva[$vatrate] * $ratio, 'MU');
638 $multicurrency_amount_ttc[$vatrate] = price2num($multicurrency_amount_ttc[$vatrate] * $ratio, 'MU');
639 }
640 }
641 }
642 //var_dump($amount_ht);var_dump($amount_tva);var_dump($amount_ttc);exit;
643
644 // Insert one discount by VAT rate category
645 $discount = new DiscountAbsolute($db);
647 $discount->description = '(CREDIT_NOTE)';
648 } elseif ($object->type == FactureFournisseur::TYPE_DEPOSIT) {
649 $discount->description = '(DEPOSIT)';
651 $discount->description = '(EXCESS PAID)';
652 } else {
653 setEventMessages($langs->trans('CantConvertToReducAnInvoiceOfThisType'), null, 'errors');
654 }
655 $discount->discount_type = 1; // Supplier discount
656 $discount->fk_soc = $object->socid;
657 $discount->socid = $object->socid;
658 $discount->fk_invoice_supplier_source = $object->id;
659
660 $error = 0;
661
663 // If we're on a standard invoice, we have to get excess paid to create a discount in TTC without VAT
664
665 // Total payments
666 $sql = 'SELECT SUM(pf.amount) as total_paiements';
667 $sql .= ' FROM '.MAIN_DB_PREFIX.'paiementfourn_facturefourn as pf, '.MAIN_DB_PREFIX.'paiementfourn as p';
668 $sql .= ' LEFT JOIN '.MAIN_DB_PREFIX.'c_paiement as c ON p.fk_paiement = c.id AND c.entity IN ('.getEntity('c_paiement').')';
669 $sql .= ' WHERE pf.fk_facturefourn = '.((int) $object->id);
670 $sql .= ' AND pf.fk_paiementfourn = p.rowid';
671 $sql .= ' AND p.entity IN ('.getEntity('invoice').')';
672
673 $resql = $db->query($sql);
674 if (!$resql) {
675 dol_print_error($db);
676 }
677
678 $res = $db->fetch_object($resql);
679 $total_paiements = $res->total_paiements;
680
681 // Total credit note and deposit
682 $total_creditnote_and_deposit = 0;
683 $sql = "SELECT re.rowid, re.amount_ht, re.amount_tva, re.amount_ttc,";
684 $sql .= " re.description, re.fk_invoice_supplier_source";
685 $sql .= " FROM ".MAIN_DB_PREFIX."societe_remise_except as re";
686 $sql .= " WHERE fk_invoice_supplier = ".((int) $object->id);
687 $resql = $db->query($sql);
688 if (!empty($resql)) {
689 while ($obj = $db->fetch_object($resql)) {
690 $total_creditnote_and_deposit += $obj->amount_ttc;
691 }
692 } else {
693 dol_print_error($db);
694 }
695
696 $discount->amount_ht = $discount->amount_ttc = $total_paiements + $total_creditnote_and_deposit - $object->total_ttc;
697 $discount->amount_tva = 0;
698 $discount->tva_tx = 0;
699 $discount->vat_src_code = '';
700
701 $result = $discount->create($user);
702 if ($result < 0) {
703 $error++;
704 }
705 }
707 foreach ($amount_ht as $tva_tx => $xxx) {
708 $discount->amount_ht = abs((float) $amount_ht[$tva_tx]);
709 $discount->amount_tva = abs((float) $amount_tva[$tva_tx]);
710 $discount->amount_ttc = abs((float) $amount_ttc[$tva_tx]);
711 $discount->multicurrency_amount_ht = abs((float) $multicurrency_amount_ht[$tva_tx]);
712 $discount->multicurrency_amount_tva = abs((float) $multicurrency_amount_tva[$tva_tx]);
713 $discount->multicurrency_amount_ttc = abs((float) $multicurrency_amount_ttc[$tva_tx]);
714
715 // Clean vat code
716 $reg = array();
717 $vat_src_code = '';
718 if (preg_match('/\‍((.*)\‍)/', $tva_tx, $reg)) {
719 $vat_src_code = $reg[1];
720 $tva_tx = preg_replace('/\s*\‍(.*\‍)/', '', $tva_tx); // Remove code into vatrate.
721 }
722
723 $discount->tva_tx = abs((float) $tva_tx);
724 $discount->vat_src_code = $vat_src_code;
725
726 $result = $discount->create($user);
727 if ($result < 0) {
728 $error++;
729 break;
730 }
731 }
732 }
733
734 if (empty($error)) {
736 // Set invoice as paid
737 $result = $object->setPaid($user);
738 if ($result >= 0) {
739 $db->commit();
740 } else {
741 setEventMessages($object->error, $object->errors, 'errors');
742 $db->rollback();
743 }
744 } else {
745 $db->commit();
746 }
747 } else {
748 setEventMessages($discount->error, $discount->errors, 'errors');
749 $db->rollback();
750 }
751 }
752 } elseif ($action == 'confirm_delete_paiement' && $confirm == 'yes' && $usercancreate) {
753 // Delete payment
754 $object->fetch($id);
755 if ($object->status == FactureFournisseur::STATUS_VALIDATED && $object->paid == 0) {
756 $paiementfourn = new PaiementFourn($db);
757 $result = $paiementfourn->fetch(GETPOST('paiement_id'));
758 if ($result > 0) {
759 $result = $paiementfourn->delete($user);
760 if ($result > 0) {
761 header("Location: ".$_SERVER['PHP_SELF']."?id=".$id);
762 exit;
763 }
764 }
765 if ($result < 0) {
766 setEventMessages($paiementfourn->error, $paiementfourn->errors, 'errors');
767 }
768 }
769 } elseif ($action == 'add' && $usercancreate) {
770 // Insert new invoice in database
771 if ($socid > 0) {
772 $object->socid = GETPOSTINT('socid');
773 }
774 $selectedLines = GETPOST('toselect', 'array');
775
776 $db->begin();
777
778 $error = 0;
779 $tmpproject = 0; // Ensure a value
780
781 // Fill array 'array_options' with data from add form
782 $ret = $extrafields->setOptionalsFromPost(null, $object);
783 if ($ret < 0) {
784 $error++;
785 }
786
787 $dateinvoice = dol_mktime(0, 0, 0, GETPOSTINT('remonth'), GETPOSTINT('reday'), GETPOSTINT('reyear'), 'tzserver'); // If we enter the 02 january, we need to save the 02 january for server
788 $datedue = dol_mktime(0, 0, 0, GETPOSTINT('echmonth'), GETPOSTINT('echday'), GETPOSTINT('echyear'), 'tzserver');
789 //var_dump($dateinvoice.' '.dol_print_date($dateinvoice, 'dayhour'));
790 //var_dump(dol_now('tzuserrel').' '.dol_get_last_hour(dol_now('tzuserrel')).' '.dol_print_date(dol_now('tzuserrel'),'dayhour').' '.dol_print_date(dol_get_last_hour(dol_now('tzuserrel')), 'dayhour'));
791 //var_dump($db->idate($dateinvoice));
792 //exit;
793
794 // Replacement invoice
795 if (GETPOSTINT('type') === '') {
796 setEventMessages($langs->trans("ErrorFieldRequired", $langs->transnoentitiesnoconv("Type")), null, 'errors');
797 $error++;
798 }
799
801 if (empty($dateinvoice)) {
802 setEventMessages($langs->trans('ErrorFieldRequired', $langs->transnoentities('DateInvoice')), null, 'errors');
803 $action = 'create';
804 //$_GET['socid'] = $_POST['socid'];
805 $error++;
806 } elseif ($dateinvoice > (dol_get_last_hour(dol_now('tzuserrel')) + getDolGlobalInt('INVOICE_MAX_FUTURE_DELAY'))) {
807 $error++;
808 setEventMessages($langs->trans("ErrorDateIsInFuture"), null, 'errors');
809 $action = 'create';
810 }
811
812 if (!(GETPOSTINT('fac_replacement') > 0)) {
813 $error++;
814 setEventMessages($langs->trans("ErrorFieldRequired", $langs->transnoentitiesnoconv("ReplaceInvoice")), null, 'errors');
815 }
816
817 if (!$error) {
818 // This is a replacement invoice
819 $result = $object->fetch(GETPOSTINT('fac_replacement'));
820 $object->fetch_thirdparty();
821
822 $object->ref = GETPOST('ref', 'alphanohtml');
823 $object->ref_supplier = GETPOST('ref_supplier', 'alpha');
824 $object->socid = GETPOSTINT('socid');
825 $object->label = GETPOST('label', 'alphanohtml');
826 $object->libelle = $object->label; // deprecated
827 $object->date = $dateinvoice;
828 $object->date_echeance = $datedue;
829 $object->note_public = GETPOST('note_public', 'restricthtml');
830 $object->note_private = GETPOST('note_private', 'restricthtml');
831 $object->cond_reglement_id = GETPOSTINT('cond_reglement_id');
832 $object->mode_reglement_id = GETPOSTINT('mode_reglement_id');
833 $object->fk_account = GETPOSTINT('fk_account');
834 $object->vat_reverse_charge = GETPOST('vat_reverse_charge') == 'on' ? 1 : 0;
835 $object->fk_project = ($tmpproject > 0) ? $tmpproject : null;
836 $object->fk_incoterms = GETPOSTINT('incoterm_id');
837 $object->location_incoterms = GETPOST('location_incoterms', 'alpha');
838 $object->multicurrency_code = GETPOST('multicurrency_code', 'alpha');
839 $object->multicurrency_tx = GETPOSTINT('originmulticurrency_tx');
840 $object->transport_mode_id = GETPOSTINT('transport_mode_id');
841
842 // Proprietes particulieres a facture de replacement
843 $object->fk_facture_source = GETPOSTINT('fac_replacement');
845
846 $id = $object->createFromCurrent($user);
847 if ($id <= 0) {
848 $error++;
849 setEventMessages($object->error, $object->errors, 'errors');
850 }
851 }
852 }
853
854 // Credit note invoice
856 $sourceinvoice = GETPOSTINT('fac_avoir');
857 if (!($sourceinvoice > 0) && !getDolGlobalString('INVOICE_CREDIT_NOTE_STANDALONE')) {
858 $error++;
859 setEventMessages($langs->trans("ErrorFieldRequired", $langs->transnoentitiesnoconv("CorrectInvoice")), null, 'errors');
860 }
861 if (GETPOSTINT('socid') < 1) {
862 setEventMessages($langs->trans('ErrorFieldRequired', $langs->transnoentities('Supplier')), null, 'errors');
863 $action = 'create';
864 $error++;
865 }
866
867 if (empty($dateinvoice)) {
868 setEventMessages($langs->trans('ErrorFieldRequired', $langs->transnoentities('DateInvoice')), null, 'errors');
869 $action = 'create';
870 //$_GET['socid'] = $_POST['socid'];
871 $error++;
872 } elseif ($dateinvoice > (dol_get_last_hour(dol_now('tzuserrel')) + getDolGlobalInt('INVOICE_MAX_FUTURE_DELAY'))) {
873 $error++;
874 setEventMessages($langs->trans("ErrorDateIsInFuture"), null, 'errors');
875 $action = 'create';
876 }
877
878 if (!GETPOST('ref_supplier')) {
879 setEventMessages($langs->trans('ErrorFieldRequired', $langs->transnoentities('RefSupplierBill')), null, 'errors');
880 $action = 'create';
881 //$_GET['socid'] = $_POST['socid'];
882 $error++;
883 }
884
885 if (getDolGlobalInt('INVOICE_SUBTYPE_ENABLED') && empty(GETPOST("subtype"))) {
886 $error++;
887 setEventMessages($langs->trans("ErrorFieldRequired", $langs->transnoentitiesnoconv("InvoiceSubtype")), null, 'errors');
888 $action = 'create';
889 }
890
891 if (!$error) {
892 $tmpproject = GETPOSTINT('projectid');
893
894 // Creation facture
895 $object->ref = GETPOST('ref', 'alphanohtml');
896 $object->ref_supplier = GETPOST('ref_supplier', 'alphanohtml');
897 $object->subtype = GETPOST('subtype', 'alphanohtml');
898 $object->socid = GETPOSTINT('socid');
899 $object->label = GETPOST('label', 'alphanohtml');
900 $object->libelle = $object->label; // Deprecated
901 $object->date = $dateinvoice;
902 $object->date_echeance = $datedue;
903 $object->note_public = GETPOST('note_public', 'restricthtml');
904 $object->note_private = GETPOST('note_private', 'restricthtml');
905 $object->cond_reglement_id = GETPOST('cond_reglement_id');
906 $object->mode_reglement_id = GETPOST('mode_reglement_id');
907 $object->fk_account = GETPOSTINT('fk_account');
908 $object->vat_reverse_charge = GETPOST('vat_reverse_charge') == 'on' ? 1 : 0;
909 $object->fk_project = ($tmpproject > 0) ? $tmpproject : null;
910 $object->fk_incoterms = GETPOSTINT('incoterm_id');
911 $object->location_incoterms = GETPOST('location_incoterms', 'alpha');
912 $object->multicurrency_code = GETPOST('multicurrency_code', 'alpha');
913 $object->multicurrency_tx = GETPOSTINT('originmulticurrency_tx');
914 $object->transport_mode_id = GETPOSTINT('transport_mode_id');
915
916 // Proprietes particulieres a facture avoir
917 $object->fk_facture_source = $sourceinvoice > 0 ? $sourceinvoice : '';
919
920 $id = $object->create($user);
921
922 if ($id <= 0) {
923 $error++;
924 }
925
926 if (GETPOSTINT('invoiceAvoirWithLines') == 1 && $id > 0) {
927 $facture_source = new FactureFournisseur($db); // fetch origin object
928 if ($facture_source->fetch($object->fk_facture_source) > 0) {
929 $fk_parent_line = 0;
930
931 foreach ($facture_source->lines as $line) {
932 // Reset fk_parent_line for no child products and special product
933 if (($line->product_type != 9 && empty($line->fk_parent_line)) || $line->product_type == 9) {
934 $fk_parent_line = 0;
935 }
936
937 $line->fk_facture_fourn = $object->id;
938 $line->fk_parent_line = $fk_parent_line;
939
940 $line->subprice = -$line->subprice; // invert price for object
941 $line->pa_ht = -$line->pa_ht;
942 $line->total_ht = -$line->total_ht;
943 $line->total_tva = -$line->total_tva;
944 $line->total_ttc = -$line->total_ttc;
945 $line->total_localtax1 = -$line->total_localtax1;
946 $line->total_localtax2 = -$line->total_localtax2;
947
948 $result = $line->insert();
949
950 $object->lines[] = $line; // insert new line in current object
951
952 // Defined the new fk_parent_line
953 if ($result > 0 && $line->product_type == 9) {
954 $fk_parent_line = $result;
955 }
956 }
957
958 $object->update_price(1);
959 }
960 }
961
962 if (GETPOSTINT('invoiceAvoirWithPaymentRestAmount') == 1 && $id > 0) {
963 $facture_source = new FactureFournisseur($db); // fetch origin object if not previously defined
964 if ($facture_source->fetch($object->fk_facture_source) > 0) {
965 $totalpaid = $facture_source->getSommePaiement();
966 $totalcreditnotes = $facture_source->getSumCreditNotesUsed();
967 $totaldeposits = $facture_source->getSumDepositsUsed();
968 $remain_to_pay = abs($facture_source->total_ttc - $totalpaid - $totalcreditnotes - $totaldeposits);
969 $desc = $langs->trans('invoiceAvoirLineWithPaymentRestAmount');
970 $retAddLine = $object->addline($desc, $remain_to_pay, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 'TTC');
971
972 if ($retAddLine < 0) {
973 $error++;
974 }
975 }
976 }
977 }
978 } elseif ($fac_recid > 0 && (GETPOST('type') == FactureFournisseur::TYPE_STANDARD || GETPOST('type') == FactureFournisseur::TYPE_DEPOSIT)) {
979 // Standard invoice or Deposit invoice, created from a Predefined template invoice
980 if (empty($dateinvoice)) {
981 $error++;
982 setEventMessages($langs->trans("ErrorFieldRequired", $langs->transnoentitiesnoconv("Date")), null, 'errors');
983 $action = 'create';
984 } elseif ($dateinvoice > (dol_get_last_hour(dol_now('tzuserrel')) + getDolGlobalInt('INVOICE_MAX_FUTURE_DELAY'))) {
985 $error++;
986 setEventMessages($langs->trans("ErrorDateIsInFuture"), null, 'errors');
987 $action = 'create';
988 }
989
990 if (getDolGlobalInt('INVOICE_SUBTYPE_ENABLED') && empty(GETPOST("subtype"))) {
991 $error++;
992 setEventMessages($langs->trans("ErrorFieldRequired", $langs->transnoentitiesnoconv("InvoiceSubtype")), null, 'errors');
993 $action = 'create';
994 }
995
996 if (!$error) {
997 $object->socid = GETPOSTINT('socid');
998 $object->type = GETPOST('type', 'alphanohtml');
999 $object->subtype = GETPOSTINT('subtype');
1000 $object->ref = GETPOST('ref', 'alphanohtml');
1001 $object->date = $dateinvoice;
1002 $object->note_public = trim(GETPOST('note_public', 'restricthtml'));
1003 $object->note_private = trim(GETPOST('note_private', 'restricthtml'));
1004 $object->ref_supplier = GETPOST('ref_supplier', 'alphanohtml');
1005 $object->model_pdf = GETPOST('model', 'alphanohtml');
1006 $object->fk_project = GETPOSTINT('projectid');
1007 $object->cond_reglement_id = (GETPOSTINT('type') == 3 ? 1 : GETPOST('cond_reglement_id'));
1008 $object->mode_reglement_id = GETPOSTINT('mode_reglement_id');
1009 $object->fk_account = GETPOSTINT('fk_account');
1010 $object->amount = (float) price2num(GETPOST('amount')); // FIXME: FactureFournisseur::$amount is deprecated and not used?
1011 //$object->remise_absolue = price2num(GETPOST('remise_absolue'), 'MU');
1012 //$object->remise_percent = price2num(GETPOST('remise_percent'), '', 2);
1013 $object->fk_incoterms = GETPOSTINT('incoterm_id');
1014 $object->location_incoterms = GETPOST('location_incoterms', 'alpha');
1015 $object->multicurrency_code = GETPOST('multicurrency_code', 'alpha');
1016 $object->multicurrency_tx = GETPOSTINT('originmulticurrency_tx');
1017
1018 // Source facture
1019 $object->fac_rec = $fac_recid;
1020 $fac_rec = new FactureFournisseurRec($db);
1021 $fac_rec->fetch($object->fac_rec);
1022 $fac_rec->fetch_lines();
1023 $object->lines = $fac_rec->lines;
1024
1025 $id = $object->create($user); // This include recopy of links from recurring invoice and recurring invoice lines
1026 }
1027 } elseif ($fac_recid <= 0 && (GETPOST('type') == FactureFournisseur::TYPE_STANDARD || GETPOST('type') == FactureFournisseur::TYPE_DEPOSIT)) {
1028 // Standard invoice or Deposit invoice, not from a Predefined template invoice
1029 if (GETPOSTINT('socid') < 1) {
1030 setEventMessages($langs->trans('ErrorFieldRequired', $langs->transnoentities('Supplier')), null, 'errors');
1031 $action = 'create';
1032 $error++;
1033 }
1034
1035 if (empty($dateinvoice)) {
1036 setEventMessages($langs->trans('ErrorFieldRequired', $langs->transnoentities('DateInvoice')), null, 'errors');
1037 $action = 'create';
1038 //$_GET['socid'] = $_POST['socid'];
1039 $error++;
1040 } elseif ($dateinvoice > (dol_get_last_hour(dol_now('tzuserrel')) + getDolGlobalInt('INVOICE_MAX_FUTURE_DELAY'))) {
1041 $error++;
1042 setEventMessages($langs->trans("ErrorDateIsInFuture"), null, 'errors');
1043 $action = 'create';
1044 }
1045
1046 if (!GETPOST('ref_supplier')) {
1047 setEventMessages($langs->trans('ErrorFieldRequired', $langs->transnoentities('RefSupplierBill')), null, 'errors');
1048 $action = 'create';
1049 //$_GET['socid'] = $_POST['socid'];
1050 $error++;
1051 }
1052
1053 if (getDolGlobalInt('INVOICE_SUBTYPE_ENABLED') && empty(GETPOST("subtype"))) {
1054 $error++;
1055 setEventMessages($langs->trans("ErrorFieldRequired", $langs->transnoentitiesnoconv("InvoiceSubtype")), null, 'errors');
1056 $action = 'create';
1057 }
1058
1059 if (!$error) {
1060 $tmpproject = GETPOSTINT('projectid');
1061
1062 // Creation invoice
1063 $object->socid = GETPOSTINT('socid');
1064 $object->type = GETPOST('type', 'alphanohtml');
1065 $object->subtype = GETPOSTINT('subtype');
1066 $object->ref = GETPOST('ref', 'alphanohtml');
1067 $object->ref_supplier = GETPOST('ref_supplier', 'alphanohtml');
1068 $object->socid = GETPOSTINT('socid');
1069 $object->label = GETPOST('label', 'alphanohtml');
1070 $object->libelle = $object->label; // deprecated
1071 $object->date = $dateinvoice;
1072 $object->date_echeance = $datedue;
1073 $object->note_public = GETPOST('note_public', 'restricthtml');
1074 $object->note_private = GETPOST('note_private', 'restricthtml');
1075 $object->cond_reglement_id = GETPOST('cond_reglement_id');
1076 $object->mode_reglement_id = GETPOST('mode_reglement_id');
1077 $object->fk_account = GETPOSTINT('fk_account');
1078 $object->vat_reverse_charge = GETPOST('vat_reverse_charge') == 'on' ? 1 : 0;
1079 $object->fk_project = ($tmpproject > 0) ? $tmpproject : null;
1080 $object->fk_incoterms = GETPOSTINT('incoterm_id');
1081 $object->location_incoterms = GETPOST('location_incoterms', 'alpha');
1082 $object->multicurrency_code = GETPOST('multicurrency_code', 'alpha');
1083 $object->multicurrency_tx = GETPOSTINT('originmulticurrency_tx');
1084 $object->transport_mode_id = GETPOSTINT('transport_mode_id');
1085
1086 // Auto calculation of date due if not filled by user
1087 if (empty($object->date_echeance)) {
1088 $object->date_echeance = $object->calculate_date_lim_reglement();
1089 }
1090
1091 $object->fetch_thirdparty();
1092
1093 // If creation from another object of another module
1094 if (!$error && GETPOST('origin', 'alpha') && GETPOST('originid')) {
1095 // Parse element/subelement (ex: project_task)
1096 $element = $subelement = GETPOST('origin', 'alpha');
1097 /*if (preg_match('/^([^_]+)_([^_]+)/i', GETPOST('origin'),$regs))
1098 {
1099 $element = $regs[1];
1100 $subelement = $regs[2];
1101 }*/
1102
1103 // For compatibility
1104 if ($element == 'order') {
1105 $element = $subelement = 'commande';
1106 }
1107 if ($element == 'propal') {
1108 $element = 'comm/propal';
1109 $subelement = 'propal';
1110 }
1111 if ($element == 'contract') {
1112 $element = $subelement = 'contrat';
1113 }
1114 if ($element == 'order_supplier') {
1115 $element = 'fourn';
1116 $subelement = 'fournisseur.commande';
1117 }
1118 if ($element == 'project') {
1119 $element = 'projet';
1120 }
1121 $object->origin = GETPOST('origin', 'alpha');
1122 $object->origin_id = GETPOSTINT('originid');
1123
1124
1125 require_once DOL_DOCUMENT_ROOT.'/'.$element.'/class/'.$subelement.'.class.php';
1126 $classname = ucfirst($subelement);
1127 if ($classname == 'Fournisseur.commande') {
1128 $classname = 'CommandeFournisseur';
1129 }
1130 $objectsrc = new $classname($db);
1131 $objectsrc->fetch($originid);
1132 $objectsrc->fetch_thirdparty();
1133
1134 if (!empty($object->origin) && !empty($object->origin_id)) {
1135 $object->linkedObjectsIds[$object->origin] = $object->origin_id;
1136 }
1137
1138 // Add also link with order if object is reception
1139 if ($object->origin == 'reception') {
1140 $objectsrc->fetchObjectLinked();
1141
1142 if (count($objectsrc->linkedObjectsIds['order_supplier']) > 0) {
1143 foreach ($objectsrc->linkedObjectsIds['order_supplier'] as $key => $value) {
1144 $object->linkedObjectsIds['order_supplier'] = $value;
1145 }
1146 }
1147 }
1148
1149 $id = $object->create($user);
1150
1151 // Add lines
1152 if ($id > 0) {
1153 require_once DOL_DOCUMENT_ROOT.'/'.$element.'/class/'.$subelement.'.class.php';
1154 $classname = ucfirst($subelement);
1155 if ($classname == 'Fournisseur.commande') {
1156 $classname = 'CommandeFournisseur';
1157 }
1158 $srcobject = new $classname($db);
1159
1160 $result = $srcobject->fetch(GETPOSTINT('originid'));
1161
1162 // If deposit invoice - down payment with 1 line (fixed amount or percent)
1163 $typeamount = GETPOST('typedeposit', 'alpha');
1164 if (GETPOST('type') == FactureFournisseur::TYPE_DEPOSIT && in_array($typeamount, array('amount', 'variable'))) {
1165 $valuedeposit = price2num(GETPOST('valuedeposit', 'alpha'), 'MU');
1166
1167 // Define the array $amountdeposit
1168 $amountdeposit = array();
1169 if (getDolGlobalString('MAIN_DEPOSIT_MULTI_TVA')) {
1170 if ($typeamount == 'amount') {
1171 $amount = $valuedeposit;
1172 } else {
1173 $amount = $srcobject->total_ttc * ((float) $valuedeposit / 100);
1174 }
1175
1176 $TTotalByTva = array();
1177 foreach ($srcobject->lines as &$line) {
1178 if (!empty($line->special_code)) {
1179 continue;
1180 }
1181 $TTotalByTva[$line->tva_tx] += $line->total_ttc;
1182 }
1183 '@phan-var-force array<string,float> $TTotalByTva';
1184
1185 $amount_ttc_diff = 0.;
1186 foreach ($TTotalByTva as $tva => &$total) {
1187 $coef = $total / $srcobject->total_ttc; // Calc coef
1188 $am = $amount * $coef;
1189 $amount_ttc_diff += $am;
1190 $amountdeposit[$tva] += $am / (1 + $tva / 100); // Convert into HT for the addline
1191 }
1192 } else {
1193 if ($typeamount == 'amount') {
1194 $amountdeposit[0] = $valuedeposit;
1195 } elseif ($typeamount == 'variable') {
1196 if ($result > 0) {
1197 $totalamount = 0;
1198 $lines = $srcobject->lines;
1199 $numlines = count($lines);
1200 for ($i = 0; $i < $numlines; $i++) {
1201 $qualified = 1;
1202 if (empty($lines[$i]->qty)) {
1203 $qualified = 0; // We discard qty=0, it is an option
1204 }
1205 if (!empty($lines[$i]->special_code)) {
1206 $qualified = 0; // We discard special_code (frais port, ecotaxe, option, ...)
1207 }
1208 if ($qualified) {
1209 $totalamount += $lines[$i]->total_ht; // Fixme : is it not for the customer ? Shouldn't we take total_ttc ?
1210 $tva_tx = $lines[$i]->tva_tx;
1211 $amountdeposit[$tva_tx] += ($lines[$i]->total_ht * (float) $valuedeposit) / 100;
1212 }
1213 }
1214
1215 if ($totalamount == 0) {
1216 $amountdeposit[0] = 0;
1217 }
1218 } else {
1219 setEventMessages($srcobject->error, $srcobject->errors, 'errors');
1220 $error++;
1221 $amountdeposit[0] = 0;
1222 }
1223 }
1224
1225 $amount_ttc_diff = $amountdeposit[0];
1226 }
1227
1228 foreach ($amountdeposit as $tva => $amount) {
1229 if (empty($amount)) {
1230 continue;
1231 }
1232
1233 $arraylist = array(
1234 'amount' => 'FixAmount',
1235 'variable' => 'VarAmount'
1236 );
1237 $descline = '(DEPOSIT)';
1238 //$descline.= ' - '.$langs->trans($arraylist[$typeamount]);
1239 if ($typeamount == 'amount') {
1240 $descline .= ' ('.price($valuedeposit, 0, $langs, 0, - 1, - 1, (!empty($object->multicurrency_code) ? $object->multicurrency_code : $conf->currency)).')';
1241 } elseif ($typeamount == 'variable') {
1242 $descline .= ' ('.$valuedeposit.'%)';
1243 }
1244
1245 $descline .= ' - '.$srcobject->ref;
1246 $result = $object->addline(
1247 $descline,
1248 $amount, // subprice
1249 $tva, // vat rate
1250 0, // localtax1_tx
1251 0, // localtax2_tx
1252 1, // quantity
1253 getDolGlobalInt('SUPPLIER_INVOICE_PRODUCTID_DEPOSIT', getDolGlobalInt('INVOICE_PRODUCTID_DEPOSIT')), // fk_product
1254 0, // remise_percent
1255 0, // date_start
1256 0, // date_end
1257 0,
1258 0, // info_bits
1259 'HT',
1260 0, // product_type
1261 1,
1262 0,
1263 array(), // array_options
1264 null,
1265 $object->origin,
1266 0,
1267 '',
1268 '0', // special_code
1269 0,
1270 0
1271 //,$langs->trans('Deposit') //Deprecated
1272 );
1273 }
1274
1275 $diff = $object->total_ttc - $amount_ttc_diff;
1276
1277 if (getDolGlobalString('MAIN_DEPOSIT_MULTI_TVA') && $diff != 0) {
1278 $object->fetch_lines();
1279 $subprice_diff = $object->lines[0]->subprice - $diff / (1 + $object->lines[0]->tva_tx / 100);
1280 $object->updateline(
1281 $object->lines[0]->id,
1282 $object->lines[0]->desc,
1283 $subprice_diff,
1284 $object->lines[0]->tva_tx,
1285 $object->lines[0]->localtax1_tx,
1286 $object->lines[0]->localtax2_tx,
1287 $object->lines[0]->qty,
1288 $object->lines[0]->fk_product,
1289 'HT',
1290 $object->lines[0]->info_bits,
1291 $object->lines[0]->product_type,
1292 $object->lines[0]->remise_percent,
1293 0,
1294 $object->lines[0]->date_start,
1295 $object->lines[0]->date_end,
1296 array(), // array_options
1297 0,
1298 0,
1299 '',
1300 100
1301 );
1302 }
1303 } elseif ($result > 0) {
1304 $lines = $srcobject->lines;
1305 if (empty($lines) && method_exists($srcobject, 'fetch_lines')) {
1306 $srcobject->fetch_lines();
1307 $lines = $srcobject->lines;
1308 }
1309
1310 $num = count($lines);
1311 for ($i = 0; $i < $num; $i++) { // TODO handle subprice < 0
1312 if (!in_array($lines[$i]->id, $selectedLines)) {
1313 continue; // Skip unselected lines
1314 }
1315
1316 $desc = ($lines[$i]->desc ? $lines[$i]->desc : $lines[$i]->product_label);
1317 $product_type = ($lines[$i]->product_type ? $lines[$i]->product_type : 0);
1318
1319 // Extrafields
1320 if (method_exists($lines[$i], 'fetch_optionals')) {
1321 $lines[$i]->fetch_optionals();
1322 }
1323
1324 // Dates
1325 // TODO mutualiser
1326 $date_start = $lines[$i]->date_debut_prevue;
1327 if ($lines[$i]->date_debut_reel) {
1328 $date_start = $lines[$i]->date_debut_reel;
1329 }
1330 if ($lines[$i]->date_start) {
1331 $date_start = $lines[$i]->date_start;
1332 }
1333 $date_end = $lines[$i]->date_fin_prevue;
1334 if ($lines[$i]->date_fin_reel) {
1335 $date_end = $lines[$i]->date_fin_reel;
1336 }
1337 if ($lines[$i]->date_end) {
1338 $date_end = $lines[$i]->date_end;
1339 }
1340
1341 $tva_tx = $lines[$i]->tva_tx;
1342 if (!empty($lines[$i]->vat_src_code) && !preg_match('/\‍(/', $tva_tx)) {
1343 $tva_tx .= ' ('.$lines[$i]->vat_src_code.')';
1344 }
1345
1346 // FIXME Missing special_code into addline and updateline methods
1347 $object->special_code = $lines[$i]->special_code;
1348
1349 // FIXME If currency different from main currency, take multicurrency price
1350 if ($object->multicurrency_code != $conf->currency || $object->multicurrency_tx != 1) {
1351 $pu = 0;
1352 $pu_currency = $lines[$i]->multicurrency_subprice;
1353 } else {
1354 $pu = $lines[$i]->subprice;
1355 $pu_currency = 0;
1356 }
1357
1358 // FIXME Missing $lines[$i]->ref_supplier and $lines[$i]->label into addline and updateline methods. They are filled when coming from order for example.
1359 $result = $object->addline(
1360 $desc,
1361 $pu,
1362 $tva_tx,
1363 $lines[$i]->localtax1_tx,
1364 $lines[$i]->localtax2_tx,
1365 $lines[$i]->qty,
1366 $lines[$i]->fk_product,
1367 $lines[$i]->remise_percent,
1368 $date_start,
1369 $date_end,
1370 0,
1371 $lines[$i]->info_bits,
1372 'HT',
1373 $product_type,
1374 $lines[$i]->rang,
1375 0,
1376 $lines[$i]->array_options,
1377 $lines[$i]->fk_unit,
1378 $lines[$i]->id,
1379 $pu_currency,
1380 $lines[$i]->ref_supplier,
1381 $lines[$i]->special_code
1382 );
1383
1384 if ($result < 0) {
1385 $error++;
1386 break;
1387 }
1388 }
1389
1390 // Now reload line
1391 $object->fetch_lines();
1392 } else {
1393 $error++;
1394 }
1395 } else {
1396 $error++;
1397 }
1398 } elseif (!$error) {
1399 $id = $object->create($user);
1400 if ($id < 0) {
1401 $error++;
1402 }
1403 }
1404 }
1405 }
1406
1407 if ($error) {
1408 $langs->load("errors");
1409 $db->rollback();
1410
1411 setEventMessages($object->error, $object->errors, 'errors');
1412 $action = 'create';
1413 //$_GET['socid'] = $_POST['socid'];
1414 } else {
1415 $db->commit();
1416
1417 if (!getDolGlobalString('MAIN_DISABLE_PDF_AUTOUPDATE')) {
1418 $outputlangs = $langs;
1419 $result = $object->generateDocument($object->model_pdf, $outputlangs, $hidedetails, $hidedesc, $hideref);
1420 if ($result < 0) {
1421 dol_print_error($db, $object->error, $object->errors);
1422 exit;
1423 }
1424 }
1425
1426 header("Location: ".$_SERVER['PHP_SELF']."?id=".$id);
1427 exit;
1428 }
1429 } elseif ($action == 'updateline' && $usercancreate) {
1430 // Edit line
1431 $db->begin();
1432
1433 if (! $object->fetch($id) > 0) {
1434 dol_print_error($db);
1435 }
1436 $object->fetch_thirdparty();
1437
1438 $tva_tx = (GETPOST('tva_tx') ? GETPOST('tva_tx') : 0);
1439 $tva_tx = str_replace('*', '', $tva_tx);
1440
1441 if (GETPOST('price_ht') != '' || GETPOST('multicurrency_subprice') != '') {
1442 $up = price2num(GETPOST('price_ht'), '', 2);
1443 $price_base_type = 'HT';
1444 } else {
1445 $up = price2num(GETPOST('price_ttc'), '', 2);
1446 $price_base_type = 'TTC';
1447 }
1448
1449 if (GETPOST('productid') > 0) {
1450 $productsupplier = new ProductFournisseur($db);
1451 if (getDolGlobalString('SUPPLIER_INVOICE_WITH_PREDEFINED_PRICES_ONLY')) {
1452 if (GETPOST('productid') > 0 && $productsupplier->get_buyprice(0, price2num(GETPOST('qty')), GETPOSTINT('productid'), 'restricthtml', GETPOSTINT('socid')) < 0) {
1453 setEventMessages($langs->trans("ErrorQtyTooLowForThisSupplier"), null, 'warnings');
1454 }
1455 }
1456
1457 $prod = new Product($db);
1458 $prod->fetch(GETPOST('productid'));
1459 $label = $prod->description;
1460 if (trim(GETPOST('product_desc', 'restricthtml')) != trim($label)) {
1461 $label = GETPOST('product_desc', 'restricthtml');
1462 }
1463
1464 $type = $prod->type;
1465 } else {
1466 $label = GETPOST('product_desc', 'restricthtml');
1467 $type = GETPOST("type") ? GETPOST("type") : 0;
1468 }
1469
1470 $date_start = dol_mktime(GETPOST('date_starthour'), GETPOST('date_startmin'), GETPOST('date_startsec'), GETPOST('date_startmonth'), GETPOST('date_startday'), GETPOST('date_startyear'));
1471 $date_end = dol_mktime(GETPOST('date_endhour'), GETPOST('date_endmin'), GETPOST('date_endsec'), GETPOST('date_endmonth'), GETPOST('date_endday'), GETPOST('date_endyear'));
1472
1473 // Define info_bits
1474 $info_bits = 0;
1475 if (preg_match('/\*/', $tva_tx)) {
1476 $info_bits |= 0x01;
1477 }
1478
1479 // Define vat_rate
1480 $tva_tx = str_replace('*', '', $tva_tx);
1481 $localtax1_tx = get_localtax($tva_tx, 1, $mysoc, $object->thirdparty);
1482 $localtax2_tx = get_localtax($tva_tx, 2, $mysoc, $object->thirdparty);
1483
1484 $remise_percent = price2num(GETPOST('remise_percent'), '', 2);
1485 $pu_devise = price2num(GETPOST('multicurrency_subprice'), 'MU', 2);
1486
1487 // Extrafields Lines
1488 $extralabelsline = $extrafields->fetch_name_optionals_label($object->table_element_line);
1489 $array_options = $extrafields->getOptionalsFromPost($object->table_element_line);
1490 // Unset extrafield POST Data
1491 if (is_array($extralabelsline)) {
1492 foreach ($extralabelsline as $key => $value) {
1493 unset($_POST["options_".$key]);
1494 }
1495 }
1496
1497 $result = $object->updateline(
1498 GETPOSTINT('lineid'),
1499 $label,
1500 $up,
1501 $tva_tx,
1502 $localtax1_tx,
1503 $localtax2_tx,
1504 price2num(GETPOST('qty'), 'MS'),
1505 GETPOSTINT('productid'),
1506 $price_base_type,
1507 $info_bits,
1508 $type,
1509 $remise_percent,
1510 0,
1511 $date_start,
1512 $date_end,
1513 $array_options,
1514 GETPOST('units', 'alpha'),
1515 $pu_devise,
1516 GETPOST('fourn_ref', 'alpha')
1517 );
1518 if ($result >= 0) {
1519 unset($_POST['label']);
1520 unset($_POST['fourn_ref']);
1521 unset($_POST['date_starthour']);
1522 unset($_POST['date_startmin']);
1523 unset($_POST['date_startsec']);
1524 unset($_POST['date_startday']);
1525 unset($_POST['date_startmonth']);
1526 unset($_POST['date_startyear']);
1527 unset($_POST['date_endhour']);
1528 unset($_POST['date_endmin']);
1529 unset($_POST['date_endsec']);
1530 unset($_POST['date_endday']);
1531 unset($_POST['date_endmonth']);
1532 unset($_POST['date_endyear']);
1533 unset($_POST['price_ttc']);
1534 unset($_POST['price_ht']);
1535
1536 $db->commit();
1537 } else {
1538 $db->rollback();
1539 setEventMessages($object->error, $object->errors, 'errors');
1540 }
1541 } elseif ($action == 'addline' && GETPOST('submitforalllines', 'aZ09') && (GETPOST('alldate_start', 'alpha') || GETPOST('alldate_end', 'alpha')) && $usercancreate) {
1542 // Define date start and date end for all line
1543 $alldate_start = dol_mktime(GETPOST('alldate_starthour'), GETPOST('alldate_startmin'), 0, GETPOST('alldate_startmonth'), GETPOST('alldate_startday'), GETPOST('alldate_startyear'));
1544 $alldate_end = dol_mktime(GETPOST('alldate_endhour'), GETPOST('alldate_endmin'), 0, GETPOST('alldate_endmonth'), GETPOST('alldate_endday'), GETPOST('alldate_endyear'));
1545 foreach ($object->lines as $line) {
1546 if ($line->product_type == 1) { // only service line
1547 $result = $object->updateline($line->id, $line->desc, $line->subprice, $line->tva_tx, $line->localtax1_tx, $line->localtax2_tx, $line->qty, $line->fk_product, 'HT', $line->info_bits, $line->product_type, $line->remise_percent, 0, $alldate_start, $alldate_end, $line->array_options, $line->fk_unit, $line->multicurrency_subprice, $line->ref_supplier, $line->rang);
1548 }
1549 }
1550 } elseif ($action == 'addline' && GETPOST('submitforalllines', 'aZ09') && GETPOST('vatforalllines', 'alpha') != '' && $usercancreate) {
1551 // Define vat_rate
1552 $vat_rate = (GETPOST('vatforalllines') ? GETPOST('vatforalllines') : 0);
1553 $vat_rate = str_replace('*', '', $vat_rate);
1554 $localtax1_rate = get_localtax($vat_rate, 1, $object->thirdparty, $mysoc);
1555 $localtax2_rate = get_localtax($vat_rate, 2, $object->thirdparty, $mysoc);
1556 foreach ($object->lines as $line) {
1557 $result = $object->updateline($line->id, $line->desc, $line->subprice, $vat_rate, $localtax1_rate, $localtax2_rate, $line->qty, $line->fk_product, 'HT', $line->info_bits, $line->product_type, $line->remise_percent, 0, $line->date_start, $line->date_end, $line->array_options, $line->fk_unit, $line->multicurrency_subprice, $line->ref_supplier, $line->rang);
1558 }
1559 } elseif ($action == 'addline' && $usercancreate) {
1560 // Add a product line
1561 $db->begin();
1562
1563 $ret = $object->fetch($id);
1564 if ($ret < 0) {
1565 dol_print_error($db, $object->error);
1566 exit;
1567 }
1568 $ret = $object->fetch_thirdparty();
1569
1570 $langs->load('errors');
1571 $error = 0;
1572
1573 // Set if we used free entry or predefined product
1574 $predef = '';
1575 $product_desc = (GETPOSTISSET('dp_desc') ? GETPOST('dp_desc', 'restricthtml') : '');
1576 $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'));
1577 $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'));
1578
1579 $prod_entry_mode = GETPOST('prod_entry_mode');
1580 if ($prod_entry_mode == 'free') {
1581 $idprod = 0;
1582 } else {
1583 $idprod = GETPOSTINT('idprod');
1584 }
1585
1586 $tva_tx = (GETPOST('tva_tx') ? GETPOST('tva_tx') : 0); // Can be '1.2' or '1.2 (CODE)'
1587
1588 $price_ht = price2num(GETPOST('price_ht'), 'MU', 2);
1589 $price_ht_devise = price2num(GETPOST('multicurrency_price_ht'), 'CU', 2);
1590 $price_ttc = price2num(GETPOST('price_ttc'), 'MU', 2);
1591 $price_ttc_devise = price2num(GETPOST('multicurrency_price_ttc'), 'CU', 2);
1592 $qty = price2num(GETPOST('qty'.$predef, 'alpha'), 'MS');
1593
1594 $remise_percent = (GETPOSTISSET('remise_percent'.$predef) ? price2num(GETPOST('remise_percent'.$predef, 'alpha'), '', 2) : 0);
1595 if (empty($remise_percent)) {
1596 $remise_percent = 0;
1597 }
1598
1599 // Extrafields
1600 $extralabelsline = $extrafields->fetch_name_optionals_label($object->table_element_line);
1601 $array_options = $extrafields->getOptionalsFromPost($object->table_element_line, $predef);
1602 // Unset extrafield
1603 if (is_array($extralabelsline)) {
1604 // Get extra fields
1605 foreach ($extralabelsline as $key => $value) {
1606 unset($_POST["options_".$key]);
1607 }
1608 }
1609
1610 if ($prod_entry_mode == 'free' && GETPOST('price_ht') < 0 && $qty < 0) {
1611 setEventMessages($langs->trans('ErrorBothFieldCantBeNegative', $langs->transnoentitiesnoconv('UnitPrice'), $langs->transnoentitiesnoconv('Qty')), null, 'errors');
1612 $error++;
1613 }
1614 if ($prod_entry_mode == 'free' && !GETPOST('idprodfournprice') && GETPOST('type') < 0) {
1615 setEventMessages($langs->trans('ErrorFieldRequired', $langs->transnoentitiesnoconv('Type')), null, 'errors');
1616 $error++;
1617 }
1618 if ($prod_entry_mode == 'free' && GETPOST('price_ht') === '' && GETPOST('price_ttc') === '' && $price_ht_devise === '') { // Unit price can be 0 but not ''
1619 setEventMessages($langs->trans('ErrorFieldRequired', $langs->transnoentitiesnoconv('UnitPrice')), null, 'errors');
1620 $error++;
1621 }
1622 if ($prod_entry_mode == 'free' && !GETPOST('dp_desc')) {
1623 setEventMessages($langs->trans('ErrorFieldRequired', $langs->transnoentitiesnoconv('Description')), null, 'errors');
1624 $error++;
1625 }
1626 if (!GETPOST('qty', 'alpha')) { // 0 is NOT allowed for invoices
1627 setEventMessages($langs->trans('ErrorFieldRequired', $langs->transnoentitiesnoconv('Qty')), null, 'errors');
1628 $error++;
1629 }
1630
1631 if (!$error && isModEnabled('variants') && $prod_entry_mode != 'free') {
1632 if ($combinations = GETPOST('combinations', 'array')) {
1633 //Check if there is a product with the given combination
1634 $prodcomb = new ProductCombination($db);
1635
1636 if ($res = $prodcomb->fetchByProductCombination2ValuePairs($idprod, $combinations)) {
1637 $idprod = $res->fk_product_child;
1638 } else {
1639 setEventMessages($langs->trans('ErrorProductCombinationNotFound'), null, 'errors');
1640 $error++;
1641 }
1642 }
1643 }
1644
1645 if ($prod_entry_mode != 'free' && empty($error)) { // With combolist mode idprodfournprice is > 0 or -1. With autocomplete, idprodfournprice is > 0 or ''
1646 $productsupplier = new ProductFournisseur($db);
1647
1648 $idprod = 0;
1649 if (GETPOST('idprodfournprice', 'alpha') == -1 || GETPOST('idprodfournprice', 'alpha') == '') {
1650 $idprod = -99; // Same behaviour than with combolist. When not select idprodfournprice is now -99 (to avoid conflict with next action that may return -1, -2, ...)
1651 }
1652
1653 $reg = array();
1654 if (preg_match('/^idprod_([0-9]+)$/', GETPOST('idprodfournprice', 'alpha'), $reg)) {
1655 $idprod = $reg[1];
1656 $res = $productsupplier->fetch($idprod); // Load product from its id
1657 // Call to init some price properties of $productsupplier
1658 // So if a supplier price already exists for another thirdparty (first one found), we use it as reference price
1659 if (getDolGlobalString('SUPPLIER_TAKE_FIRST_PRICE_IF_NO_PRICE_FOR_CURRENT_SUPPLIER')) {
1660 $fksoctosearch = 0;
1661 $productsupplier->get_buyprice(0, -1, $idprod, 'none', $fksoctosearch); // We force qty to -1 to be sure to find if a supplier price exist
1662 if ($productsupplier->fourn_socid != $socid) { // The price we found is for another supplier, so we clear supplier price
1663 $productsupplier->ref_supplier = '';
1664 }
1665 } else {
1666 $fksoctosearch = $object->thirdparty->id;
1667 $productsupplier->get_buyprice(0, -1, $idprod, 'none', $fksoctosearch); // We force qty to -1 to be sure to find if a supplier price exist
1668 }
1669 } elseif (GETPOST('idprodfournprice', 'alpha') > 0) {
1670 $qtytosearch = $qty; // Just to see if a price exists for the quantity. Not used to found vat.
1671 //$qtytosearch=-1; // We force qty to -1 to be sure to find if a supplier price exist
1672 $idprod = $productsupplier->get_buyprice(GETPOST('idprodfournprice', 'alpha'), $qtytosearch);
1673 $res = $productsupplier->fetch($idprod);
1674 }
1675
1676 if ($idprod > 0) {
1677 $label = $productsupplier->label;
1678 // Define output language
1679 if (getDolGlobalInt('MAIN_MULTILANGS') && getDolGlobalString('PRODUIT_TEXTS_IN_THIRDPARTY_LANGUAGE')) {
1680 $outputlangs = $langs;
1681 $newlang = '';
1682 if (empty($newlang) && GETPOST('lang_id', 'aZ09')) {
1683 $newlang = GETPOST('lang_id', 'aZ09');
1684 }
1685 if (empty($newlang)) {
1686 $newlang = $object->thirdparty->default_lang;
1687 }
1688 if (!empty($newlang)) {
1689 $outputlangs = new Translate("", $conf);
1690 $outputlangs->setDefaultLang($newlang);
1691 }
1692 $desc = (!empty($productsupplier->multilangs[$outputlangs->defaultlang]["description"])) ? $productsupplier->multilangs[$outputlangs->defaultlang]["description"] : $productsupplier->description;
1693 } else {
1694 $desc = $productsupplier->description;
1695 }
1696 // if we use supplier description of the products
1697 if (!empty($productsupplier->desc_supplier) && getDolGlobalString('PRODUIT_FOURN_TEXTS')) {
1698 $desc = $productsupplier->desc_supplier;
1699 }
1700
1701 //If text set in desc is the same as product descpription (as now it's preloaded) we add it only one time
1702 if (trim($product_desc) == trim($desc) && getDolGlobalString('PRODUIT_AUTOFILL_DESC')) {
1703 $product_desc = '';
1704 }
1705 if (!empty($product_desc) && getDolGlobalString('MAIN_NO_CONCAT_DESCRIPTION')) {
1706 $desc = $product_desc;
1707 }
1708 if (!empty($product_desc) && trim($product_desc) != trim($desc)) {
1709 $desc = dol_concatdesc($desc, $product_desc, '', getDolGlobalString('MAIN_CHANGE_ORDER_CONCAT_DESCRIPTION'));
1710 }
1711
1712 $ref_supplier = $productsupplier->ref_supplier;
1713
1714 // Get vat rate
1715 if (!GETPOSTISSET('tva_tx')) { // If vat rate not provided from the form (the form has the priority)
1716 $tva_tx = get_default_tva($object->thirdparty, $mysoc, $productsupplier->id, GETPOST('idprodfournprice', 'alpha'));
1717 $tva_npr = get_default_npr($object->thirdparty, $mysoc, $productsupplier->id, GETPOST('idprodfournprice', 'alpha'));
1718 }
1719 if (empty($tva_tx) || empty($tva_npr)) {
1720 $tva_npr = 0;
1721 }
1722 $localtax1_tx = get_localtax($tva_tx, 1, $mysoc, $object->thirdparty, $tva_npr);
1723 $localtax2_tx = get_localtax($tva_tx, 2, $mysoc, $object->thirdparty, $tva_npr);
1724
1725 $type = $productsupplier->type;
1726 if (GETPOST('price_ht') != '' || GETPOST('multicurrency_price_ht') != '') {
1727 $price_base_type = 'HT';
1728 $pu = price2num($price_ht, 'MU');
1729 $pu_devise = price2num($price_ht_devise, 'CU');
1730 } elseif (GETPOST('price_ttc') != '' || GETPOST('multicurrency_price_ttc') != '') {
1731 $price_base_type = 'TTC';
1732 $pu = price2num($price_ttc, 'MU');
1733 $pu_devise = price2num($price_ttc_devise, 'CU');
1734 } else {
1735 $price_base_type = ($productsupplier->fourn_price_base_type ? $productsupplier->fourn_price_base_type : 'HT');
1736 if (empty($object->multicurrency_code) || ($productsupplier->fourn_multicurrency_code != $object->multicurrency_code)) { // If object is in a different currency and price not in this currency
1737 $pu = $productsupplier->fourn_pu;
1738 $pu_devise = 0;
1739 } else {
1740 $pu = $productsupplier->fourn_pu;
1741 $pu_devise = $productsupplier->fourn_multicurrency_unitprice;
1742 }
1743 }
1744
1745 $ref_supplier = $productsupplier->ref_supplier;
1746
1747 if (empty($pu)) {
1748 $pu = 0; // If pu is '' or null, we force to have a numeric value
1749 }
1750
1751 $result = $object->addline(
1752 $desc,
1753 $pu,
1754 $tva_tx,
1755 $localtax1_tx,
1756 $localtax2_tx,
1757 $qty,
1758 $idprod,
1759 $remise_percent,
1760 $date_start,
1761 $date_end,
1762 0,
1763 $tva_npr,
1764 $price_base_type,
1765 $type,
1766 min($rank, count($object->lines) + 1),
1767 0,
1768 $array_options,
1769 $productsupplier->fk_unit,
1770 0,
1771 $pu_devise,
1772 GETPOST('fourn_ref', 'alpha'),
1773 0
1774 );
1775 }
1776 if ($idprod == -99 || $idprod == 0) {
1777 // Product not selected
1778 $error++;
1779 $langs->load("errors");
1780 setEventMessages($langs->trans("ErrorFieldRequired", $langs->transnoentitiesnoconv("ProductOrService")), null, 'errors');
1781 }
1782 if ($idprod == -1) {
1783 // Quantity too low
1784 $error++;
1785 $langs->load("errors");
1786 setEventMessages($langs->trans("ErrorQtyTooLowForThisSupplier"), null, 'errors');
1787 }
1788 } elseif (empty($error)) { // $price_ht is already set
1789 $tva_npr = (preg_match('/\*/', $tva_tx) ? 1 : 0);
1790 $tva_tx = str_replace('*', '', $tva_tx);
1791 $label = (GETPOST('product_label') ? GETPOST('product_label') : '');
1792 $desc = $product_desc;
1793 $type = GETPOST('type');
1794 $ref_supplier = GETPOST('fourn_ref', 'alpha');
1795
1796 $fk_unit = GETPOST('units', 'alpha');
1797
1798 if (!preg_match('/\‍((.*)\‍)/', $tva_tx)) {
1799 $tva_tx = price2num($tva_tx); // $txtva can have format '5,1' or '5.1' or '5.1(XXX)', we must clean only if '5,1'
1800 }
1801
1802 // Local Taxes
1803 $localtax1_tx = get_localtax($tva_tx, 1, $mysoc, $object->thirdparty);
1804 $localtax2_tx = get_localtax($tva_tx, 2, $mysoc, $object->thirdparty);
1805
1806 if (GETPOST('price_ht') != '' || GETPOST('multicurrency_price_ht') != '') {
1807 $pu_ht = price2num($price_ht, 'MU'); // $pu_ht must be rounded according to settings
1808 } else {
1809 $pu_ttc = price2num(GETPOST('price_ttc'), 'MU');
1810 $pu_ht = price2num((float) $pu_ttc / (1 + ((float) $tva_tx / 100)), 'MU'); // $pu_ht must be rounded according to settings
1811 }
1812 $price_base_type = 'HT';
1813 $pu_devise = price2num($price_ht_devise, 'CU');
1814
1815 $result = $object->addline($product_desc, $pu_ht, $tva_tx, $localtax1_tx, $localtax2_tx, $qty, 0, $remise_percent, $date_start, $date_end, 0, $tva_npr, $price_base_type, $type, -1, 0, $array_options, $fk_unit, 0, $pu_devise, $ref_supplier);
1816 }
1817
1818 //print "xx".$tva_tx; exit;
1819 if (!$error && $result > 0) {
1820 $db->commit();
1821
1822 // Define output language
1823 if (!getDolGlobalString('MAIN_DISABLE_PDF_AUTOUPDATE')) {
1824 $outputlangs = $langs;
1825 $newlang = '';
1826 if (getDolGlobalInt('MAIN_MULTILANGS') && empty($newlang) && GETPOST('lang_id', 'aZ09')) {
1827 $newlang = GETPOST('lang_id', 'aZ09');
1828 }
1829 if (getDolGlobalInt('MAIN_MULTILANGS') && empty($newlang)) {
1830 $newlang = $object->thirdparty->default_lang;
1831 }
1832 if (!empty($newlang)) {
1833 $outputlangs = new Translate("", $conf);
1834 $outputlangs->setDefaultLang($newlang);
1835 }
1836 $model = $object->model_pdf;
1837 $ret = $object->fetch($id); // Reload to get new records
1838
1839 $result = $object->generateDocument($model, $outputlangs, $hidedetails, $hidedesc, $hideref);
1840 if ($result < 0) {
1841 dol_print_error($db, $result);
1842 }
1843 }
1844
1845 unset($_POST ['prod_entry_mode']);
1846
1847 unset($_POST['qty']);
1848 unset($_POST['type']);
1849 unset($_POST['remise_percent']);
1850 unset($_POST['pu']);
1851 unset($_POST['price_ht']);
1852 unset($_POST['multicurrency_price_ht']);
1853 unset($_POST['price_ttc']);
1854 unset($_POST['fourn_ref']);
1855 unset($_POST['tva_tx']);
1856 unset($_POST['label']);
1857 unset($localtax1_tx);
1858 unset($localtax2_tx);
1859 unset($_POST['np_marginRate']);
1860 unset($_POST['np_markRate']);
1861 unset($_POST['dp_desc']);
1862 unset($_POST['idprodfournprice']);
1863 unset($_POST['units']);
1864
1865 unset($_POST['date_starthour']);
1866 unset($_POST['date_startmin']);
1867 unset($_POST['date_startsec']);
1868 unset($_POST['date_startday']);
1869 unset($_POST['date_startmonth']);
1870 unset($_POST['date_startyear']);
1871 unset($_POST['date_endhour']);
1872 unset($_POST['date_endmin']);
1873 unset($_POST['date_endsec']);
1874 unset($_POST['date_endday']);
1875 unset($_POST['date_endmonth']);
1876 unset($_POST['date_endyear']);
1877 } else {
1878 $db->rollback();
1879 setEventMessages($object->error, $object->errors, 'errors');
1880 }
1881
1882 $action = '';
1883 } elseif ($action == 'classin' && $usercancreate) {
1884 $object->fetch($id);
1885 $result = $object->setProject($projectid);
1886 } elseif ($action == 'confirm_edit' && $confirm == 'yes' && $usercancreate) {
1887 // Set invoice to draft status
1888 $object->fetch($id);
1889
1890 $totalpaid = $object->getSommePaiement();
1891 $resteapayer = $object->total_ttc - $totalpaid;
1892
1893 // We check that lines of invoices are exported in accountancy
1894 $ventilExportCompta = $object->getVentilExportCompta();
1895
1896 if (!$ventilExportCompta) {
1897 // We verify that no payment was done
1898 if ($resteapayer == price2num($object->total_ttc, 'MT', 1) && $object->status == FactureFournisseur::STATUS_VALIDATED) {
1899 $idwarehouse = GETPOST('idwarehouse');
1900
1901 $object->fetch_thirdparty();
1902
1903 $qualified_for_stock_change = 0;
1904 if (!getDolGlobalString('STOCK_SUPPORTS_SERVICES')) {
1905 $qualified_for_stock_change = $object->hasProductsOrServices(2);
1906 } else {
1907 $qualified_for_stock_change = $object->hasProductsOrServices(1);
1908 }
1909
1910 // Check parameters
1911 if (isModEnabled('stock') && getDolGlobalString('STOCK_CALCULATE_ON_SUPPLIER_BILL') && $qualified_for_stock_change) {
1912 $langs->load("stocks");
1913 if (!$idwarehouse || $idwarehouse == -1) {
1914 $error++;
1915 setEventMessages($langs->trans('ErrorFieldRequired', $langs->transnoentitiesnoconv("Warehouse")), null, 'errors');
1916 $action = '';
1917 }
1918 }
1919
1920 $object->setDraft($user, $idwarehouse);
1921
1922 // Define output language
1923 if (!getDolGlobalString('MAIN_DISABLE_PDF_AUTOUPDATE')) {
1924 $outputlangs = $langs;
1925 $newlang = '';
1926 if (getDolGlobalInt('MAIN_MULTILANGS') && empty($newlang) && GETPOST('lang_id', 'aZ09')) {
1927 $newlang = GETPOST('lang_id', 'aZ09');
1928 }
1929 if (getDolGlobalInt('MAIN_MULTILANGS') && empty($newlang)) {
1930 $newlang = $object->thirdparty->default_lang;
1931 }
1932 if (!empty($newlang)) {
1933 $outputlangs = new Translate("", $conf);
1934 $outputlangs->setDefaultLang($newlang);
1935 }
1936 $model = $object->model_pdf;
1937 $ret = $object->fetch($id); // Reload to get new records
1938
1939 $result = $object->generateDocument($model, $outputlangs, $hidedetails, $hidedesc, $hideref);
1940 if ($result < 0) {
1941 dol_print_error($db, $result);
1942 }
1943 }
1944
1945 $action = '';
1946 }
1947 }
1948 } elseif ($action == 'reopen' && $usercancreate) {
1949 // Set invoice to validated/unpaid status
1950 $result = $object->fetch($id);
1952 || ($object->status == FactureFournisseur::STATUS_ABANDONED && $object->close_code != 'replaced')) {
1953 $result = $object->setUnpaid($user);
1954 if ($result > 0) {
1955 header('Location: '.$_SERVER["PHP_SELF"].'?id='.$id);
1956 exit;
1957 } else {
1958 setEventMessages($object->error, $object->errors, 'errors');
1959 }
1960 }
1961 }
1962
1963 // Actions when printing a doc from card
1964 include DOL_DOCUMENT_ROOT.'/core/actions_printing.inc.php';
1965
1966 // Actions to send emails
1967 $triggersendname = 'BILL_SUPPLIER_SENTBYMAIL';
1968 $paramname = 'id';
1969 $autocopy = 'MAIN_MAIL_AUTOCOPY_SUPPLIER_INVOICE_TO';
1970 $trackid = 'sinv'.$object->id;
1971 include DOL_DOCUMENT_ROOT.'/core/actions_sendmails.inc.php';
1972
1973 // Actions to build doc
1974 $upload_dir = $conf->fournisseur->facture->dir_output;
1975 $permissiontoadd = $usercancreate;
1976 include DOL_DOCUMENT_ROOT.'/core/actions_builddoc.inc.php';
1977
1978 // Make calculation according to calculationrule
1979 if ($action == 'calculate' && $usercancreate) {
1980 $calculationrule = GETPOST('calculationrule');
1981
1982 $object->fetch($id);
1983 $object->fetch_thirdparty();
1984 $result = $object->update_price(0, (($calculationrule == 'totalofround') ? '0' : '1'), 0, $object->thirdparty);
1985 if ($result <= 0) {
1986 dol_print_error($db, $result);
1987 exit;
1988 }
1989 }
1990 if ($action == 'update_extras' && $usercancreate) {
1991 $object->oldcopy = dol_clone($object, 2);
1992
1993 // Fill array 'array_options' with data from add form
1994 $ret = $extrafields->setOptionalsFromPost(null, $object, GETPOST('attribute', 'restricthtml'));
1995 if ($ret < 0) {
1996 $error++;
1997 }
1998
1999 // Actions on extra fields
2000 if (!$error) {
2001 $result = $object->insertExtraFields('BILL_SUPPLIER_MODIFY');
2002 if ($result < 0) {
2003 $error++;
2004 setEventMessages($object->error, $object->errors, 'errors');
2005 }
2006 }
2007
2008 if ($error) {
2009 $action = 'edit_extras';
2010 }
2011 }
2012
2013 if (getDolGlobalString('MAIN_DISABLE_CONTACTS_TAB') && $usercancreate) {
2014 if ($action == 'addcontact') {
2015 $result = $object->fetch($id);
2016
2017 if ($result > 0 && $id > 0) {
2018 $contactid = (GETPOST('userid') ? GETPOST('userid') : GETPOST('contactid'));
2019 $typeid = (GETPOST('typecontact') ? GETPOST('typecontact') : GETPOST('type'));
2020 $result = $object->add_contact($contactid, $typeid, GETPOST("source", 'aZ09'));
2021 }
2022
2023 if ($result >= 0) {
2024 header("Location: ".$_SERVER['PHP_SELF']."?id=".$object->id);
2025 exit;
2026 } else {
2027 if ($object->error == 'DB_ERROR_RECORD_ALREADY_EXISTS') {
2028 $langs->load("errors");
2029 setEventMessages($langs->trans("ErrorThisContactIsAlreadyDefinedAsThisType"), null, 'errors');
2030 } else {
2031 setEventMessages($object->error, $object->errors, 'errors');
2032 }
2033 }
2034 } elseif ($action == 'swapstatut') {
2035 // bascule du statut d'un contact
2036 if ($object->fetch($id)) {
2037 $result = $object->swapContactStatus(GETPOSTINT('ligne'));
2038 } else {
2039 dol_print_error($db);
2040 }
2041 } elseif ($action == 'deletecontact') {
2042 // Efface un contact
2043 $object->fetch($id);
2044 $result = $object->delete_contact(GETPOSTINT("lineid"));
2045
2046 if ($result >= 0) {
2047 header("Location: ".$_SERVER['PHP_SELF']."?id=".$object->id);
2048 exit;
2049 } else {
2050 dol_print_error($db);
2051 }
2052 }
2053 }
2054}
2055
2056
2057/*
2058 * View
2059 */
2060
2061$form = new Form($db);
2062$formfile = new FormFile($db);
2063$bankaccountstatic = new Account($db);
2064$paymentstatic = new PaiementFourn($db);
2065if (isModEnabled('project')) {
2066 $formproject = new FormProjets($db);
2067}
2068
2069$now = dol_now();
2070
2071$title = $object->ref." - ".$langs->trans('Card');
2072if ($action == 'create') {
2073 $title = $langs->trans("NewSupplierInvoice");
2074}
2075$help_url = 'EN:Module_Suppliers_Invoices|FR:Module_Fournisseurs_Factures|ES:Módulo_Facturas_de_proveedores|DE:Modul_Lieferantenrechnungen';
2076llxHeader('', $title, $help_url);
2077
2078// Mode creation
2079if ($action == 'create') {
2080 $facturestatic = new FactureFournisseur($db);
2081 $selectedLines = array(); // Ensure initialised
2082
2083 print load_fiche_titre($langs->trans('NewSupplierInvoice'), '', 'supplier_invoice');
2084
2086
2087 $currency_code = $conf->currency;
2088
2089 $societe = '';
2090 if (GETPOSTINT('socid') > 0) {
2091 $societe = new Societe($db);
2092 $societe->fetch(GETPOSTINT('socid'));
2093 if (isModEnabled("multicurrency") && !empty($societe->multicurrency_code)) {
2094 $currency_code = $societe->multicurrency_code;
2095 }
2096 }
2097
2098 if (!empty($origin) && !empty($originid)) {
2099 // Parse element/subelement (ex: project_task)
2100 $element = $subelement = $origin;
2101
2102 if ($element == 'project') {
2103 $projectid = $originid;
2104 $element = 'projet';
2105 }
2106
2107 // For compatibility
2108 if ($element == 'order') {
2109 $element = $subelement = 'commande';
2110 }
2111 if ($element == 'propal') {
2112 $element = 'comm/propal';
2113 $subelement = 'propal';
2114 }
2115 if ($element == 'contract') {
2116 $element = $subelement = 'contrat';
2117 }
2118 if ($element == 'order_supplier') {
2119 $element = 'fourn';
2120 $subelement = 'fournisseur.commande';
2121 }
2122
2123 require_once DOL_DOCUMENT_ROOT.'/'.$element.'/class/'.$subelement.'.class.php';
2124 $classname = ucfirst($subelement);
2125 if ($classname == 'Fournisseur.commande') {
2126 $classname = 'CommandeFournisseur';
2127 }
2128 $objectsrc = new $classname($db);
2129 '@phan-var-force Project|Commande|Propal|Facture|Contrat|CommandeFournisseur|CommonObject $objectsrc';
2130 $objectsrc->fetch($originid);
2131 $objectsrc->fetch_thirdparty();
2132
2133 $projectid = (!empty($objectsrc->fk_project) ? $objectsrc->fk_project : '');
2134 //$ref_client = (!empty($objectsrc->ref_client)?$object->ref_client:'');
2135 $soc = $objectsrc->thirdparty;
2136
2137 $cond_reglement_id = 0;
2138 $mode_reglement_id = 0;
2139 $fk_account = 0;
2140 //$remise_percent = 0;
2141 //$remise_absolue = 0;
2142 $transport_mode_id = 0;
2143
2144 // set from object source
2145 if (!empty($objectsrc->cond_reglement_id)) {
2146 $cond_reglement_id = $objectsrc->cond_reglement_id;
2147 }
2148 if (!empty($objectsrc->mode_reglement_id)) {
2149 $mode_reglement_id = $objectsrc->mode_reglement_id;
2150 }
2151 if (!empty($objectsrc->fk_account)) {
2152 $fk_account = $objectsrc->fk_account;
2153 }
2154 if (!empty($objectsrc->transport_mode_id)) {
2155 $transport_mode_id = $objectsrc->transport_mode_id;
2156 }
2157
2158 if (empty($cond_reglement_id)
2159 || empty($mode_reglement_id)
2160 || empty($fk_account)
2161 || empty($transport_mode_id)
2162 ) {
2163 if ($origin == 'reception') {
2164 // try to get from source of reception (supplier order)
2165 if (!isset($objectsrc->supplier_order)) {
2166 $objectsrc->fetch_origin();
2167 }
2168
2169 if (!empty($objectsrc->origin_object)) {
2170 $originObject = $objectsrc->origin_object;
2171 if (empty($cond_reglement_id) && !empty($originObject->cond_reglement_id)) {
2172 $cond_reglement_id = $originObject->cond_reglement_id;
2173 }
2174 if (empty($mode_reglement_id) && !empty($originObject->mode_reglement_id)) {
2175 $mode_reglement_id = $originObject->mode_reglement_id;
2176 }
2177 if (empty($fk_account) && !empty($originObject->fk_account)) {
2178 $fk_account = $originObject->fk_account;
2179 }
2180 if (empty($transport_mode_id) && !empty($originObject->transport_mode_id)) {
2181 $transport_mode_id = $originObject->transport_mode_id;
2182 }
2183 }
2184 }
2185
2186 // try to get from third-party of source object
2187 if (!empty($soc)) {
2188 if (empty($cond_reglement_id) && !empty($soc->cond_reglement_supplier_id)) {
2189 $cond_reglement_id = $soc->cond_reglement_supplier_id;
2190 }
2191 if (empty($mode_reglement_id) && !empty($soc->mode_reglement_supplier_id)) {
2192 $mode_reglement_id = $soc->mode_reglement_supplier_id;
2193 }
2194 if (empty($fk_account) && !empty($soc->fk_account)) {
2195 $fk_account = $soc->fk_account;
2196 }
2197 if (empty($transport_mode_id) && !empty($soc->transport_mode_id)) {
2198 $transport_mode_id = $soc->transport_mode_id;
2199 }
2200 }
2201 }
2202
2203 if (isModEnabled("multicurrency")) {
2204 if (!empty($objectsrc->multicurrency_code)) {
2205 $currency_code = $objectsrc->multicurrency_code;
2206 }
2207 if (getDolGlobalString('MULTICURRENCY_USE_ORIGIN_TX') && !empty($objectsrc->multicurrency_tx)) {
2208 $currency_tx = $objectsrc->multicurrency_tx;
2209 }
2210 }
2211
2212 $datetmp = dol_mktime(12, 0, 0, GETPOSTINT('remonth'), GETPOSTINT('reday'), GETPOSTINT('reyear'));
2213 $dateinvoice = ($datetmp == '' ? (!getDolGlobalString('MAIN_AUTOFILL_DATE') ? -1 : '') : $datetmp);
2214 $datetmp = dol_mktime(12, 0, 0, GETPOSTINT('echmonth'), GETPOSTINT('echday'), GETPOSTINT('echyear'));
2215 $datedue = ($datetmp == '' ? -1 : $datetmp);
2216
2217 // Replicate extrafields
2218 $objectsrc->fetch_optionals();
2219 $object->array_options = $objectsrc->array_options;
2220 } else {
2221 $cond_reglement_id = !empty($societe->cond_reglement_supplier_id) ? $societe->cond_reglement_supplier_id : 0;
2222 $mode_reglement_id = !empty($societe->mode_reglement_supplier_id) ? $societe->mode_reglement_supplier_id : 0;
2223 $vat_reverse_charge = (empty($societe) ? '' : $societe->vat_reverse_charge);
2224 $transport_mode_id = !empty($societe->transport_mode_supplier_id) ? $societe->transport_mode_supplier_id : 0;
2225 $fk_account = !empty($societe->fk_account) ? $societe->fk_account : 0;
2226 $datetmp = dol_mktime(12, 0, 0, GETPOSTINT('remonth'), GETPOSTINT('reday'), GETPOSTINT('reyear'));
2227 $dateinvoice = ($datetmp == '' ? (getDolGlobalInt('MAIN_AUTOFILL_DATE') ? '' : -1) : $datetmp);
2228 $datetmp = dol_mktime(12, 0, 0, GETPOSTINT('echmonth'), GETPOSTINT('echday'), GETPOSTINT('echyear'));
2229 $datedue = ($datetmp == '' ? -1 : $datetmp);
2230
2231 if (isModEnabled("multicurrency") && !empty($societe->multicurrency_code)) {
2232 $currency_code = $societe->multicurrency_code;
2233 }
2234 }
2235
2236 // when payment condition is empty (means not override by payment condition form a other object, like third-party), try to use default value
2237 if (empty($cond_reglement_id)) {
2238 $cond_reglement_id = GETPOST("cond_reglement_id");
2239 }
2240
2241 // when payment mode is empty (means not override by payment condition form a other object, like third-party), try to use default value
2242 if (empty($mode_reglement_id)) {
2243 $mode_reglement_id = GETPOST("mode_reglement_id");
2244 }
2245
2246 // If form was posted (but error returned), we must reuse the value posted in priority (standard Dolibarr behaviour)
2247 if (!GETPOST('changecompany')) {
2248 if (GETPOSTISSET('cond_reglement_id')) {
2249 $cond_reglement_id = GETPOSTINT('cond_reglement_id');
2250 }
2251 if (GETPOSTISSET('mode_reglement_id')) {
2252 $mode_reglement_id = GETPOSTINT('mode_reglement_id');
2253 }
2254 if (GETPOSTISSET('cond_reglement_id')) {
2255 $fk_account = GETPOSTINT('fk_account');
2256 }
2257 }
2258
2259 $note_public = $object->getDefaultCreateValueFor('note_public', ((!empty($origin) && !empty($originid) && is_object($objectsrc) && getDolGlobalString('FACTUREFOURN_REUSE_NOTES_ON_CREATE_FROM')) ? $objectsrc->note_public : null));
2260 $note_private = $object->getDefaultCreateValueFor('note_private', ((!empty($origin) && !empty($originid) && is_object($objectsrc) && getDolGlobalString('FACTUREFOURN_REUSE_NOTES_ON_CREATE_FROM')) ? $objectsrc->note_private : null));
2261
2262 if ($origin == 'contrat') {
2263 $langs->load("admin");
2264 $text = $langs->trans("ToCreateARecurringInvoice");
2265 $text .= ' '.$langs->trans("ToCreateARecurringInvoiceGene", $langs->transnoentitiesnoconv("MenuFinancial"), $langs->transnoentitiesnoconv("SupplierBills"), $langs->transnoentitiesnoconv("ListOfTemplates"));
2266 if (!getDolGlobalString('INVOICE_DISABLE_AUTOMATIC_RECURRING_INVOICE')) {
2267 $text .= ' '.$langs->trans("ToCreateARecurringInvoiceGeneAuto", $langs->transnoentitiesnoconv('Module2300Name'));
2268 }
2269 print info_admin($text, 0, 0, 0, 'opacitymedium').'<br>';
2270 }
2271
2272 print '<form name="add" action="'.$_SERVER["PHP_SELF"].'" method="post">';
2273 print '<input type="hidden" name="token" value="'.newToken().'">';
2274 print '<input type="hidden" name="action" value="add">';
2275 print '<input type="hidden" name="changecompany" value="0">'; // will be set to 1 by javascript so we know post is done after a company change
2276
2277 if (!empty($societe->id) && $societe->id > 0) {
2278 print '<input type="hidden" name="socid" value="'.$societe->id.'">'."\n";
2279 }
2280 print '<input type="hidden" name="origin" value="'.$origin.'">';
2281 print '<input type="hidden" name="originid" value="'.$originid.'">';
2282 if (!empty($currency_tx)) {
2283 print '<input type="hidden" name="originmulticurrency_tx" value="'.$currency_tx.'">';
2284 }
2285 print '<input type="hidden" name="backtopage" value="'.$backtopage.'">';
2286
2287 print dol_get_fiche_head();
2288
2289 // Call Hook tabContentCreateSupplierInvoice
2290 $parameters = array();
2291 // Note that $action and $object may be modified by hook
2292 $reshook = $hookmanager->executeHooks('tabContentCreateSupplierInvoice', $parameters, $object, $action);
2293 if (empty($reshook)) {
2294 print '<table class="border centpercent">';
2295
2296 // Ref
2297 print '<tr><td class="titlefieldcreate">'.$langs->trans('Ref').'</td><td>'.$langs->trans('Draft').'</td></tr>';
2298
2299 $exampletemplateinvoice = new FactureFournisseurRec($db);
2300 $invoice_predefined = new FactureFournisseurRec($db);
2301 if (empty($origin) && empty($originid) && $fac_recid > 0) {
2302 $invoice_predefined->fetch($fac_recid);
2303 }
2304
2305 // Third party
2306 print '<tr><td class="fieldrequired">'.$langs->trans('Supplier').'</td>';
2307 print '<td>';
2308
2309 if (!empty($societe->id) && $societe->id > 0 && ($fac_recid <= 0 || !empty($invoice_predefined->frequency))) {
2310 $absolute_discount = $societe->getAvailableDiscounts(null, '', 0, 1);
2311 print $societe->getNomUrl(1, 'supplier');
2312 print '<input type="hidden" name="socid" value="'.$societe->id.'">';
2313 } else {
2314 $filter = '((s.fournisseur:=:1) AND (s.status:=:1))';
2315 print img_picto('', 'company', 'class="pictofixedwidth"').$form->select_company(empty($societe->id) ? 0 : $societe->id, 'socid', $filter, 'SelectThirdParty', 1, 0, array(), 0, 'minwidth175 widthcentpercentminusxx maxwidth500');
2316 // reload page to retrieve supplier information
2317 if (!getDolGlobalString('RELOAD_PAGE_ON_SUPPLIER_CHANGE_DISABLED')) {
2318 print '<script type="text/javascript">
2319 $(document).ready(function() {
2320 $("#socid").change(function() {
2321 console.log("We have changed the company - Reload page");
2322 // reload page
2323 $("input[name=action]").val("create");
2324 $("input[name=changecompany]").val("1");
2325 $("form[name=add]").submit();
2326 });
2327 });
2328 </script>';
2329 }
2330 if ($fac_recid <= 0) {
2331 print ' <a href="'.DOL_URL_ROOT.'/societe/card.php?action=create&client=0&fournisseur=1&backtopage='.urlencode($_SERVER["PHP_SELF"].'?action=create').'"><span class="fa fa-plus-circle valignmiddle paddingleft" title="'.$langs->trans("AddThirdParty").'"></span></a>';
2332 }
2333 }
2334 print '</td></tr>';
2335
2336 // Overwrite some values if creation of invoice is from a predefined invoice
2337 if (empty($origin) && empty($originid) && $fac_recid > 0) {
2338 $invoice_predefined->fetch($fac_recid);
2339
2340 $dateinvoice = $invoice_predefined->date_when; // To use next gen date by default later
2341 if (empty($projectid)) {
2342 $projectid = $invoice_predefined->fk_project;
2343 }
2344 $cond_reglement_id = $invoice_predefined->cond_reglement_id;
2345 $mode_reglement_id = $invoice_predefined->mode_reglement_id;
2346 $fk_account = $invoice_predefined->fk_account;
2347 $note_public = $invoice_predefined->note_public;
2348 $note_private = $invoice_predefined->note_private;
2349
2350 if (!empty($invoice_predefined->multicurrency_code)) {
2351 $currency_code = $invoice_predefined->multicurrency_code;
2352 }
2353 if (!empty($invoice_predefined->multicurrency_tx)) {
2354 $currency_tx = $invoice_predefined->multicurrency_tx;
2355 }
2356
2357 $sql = 'SELECT r.rowid, r.titre as title, r.total_ttc';
2358 $sql .= ' FROM '.MAIN_DB_PREFIX.'facture_fourn_rec as r';
2359 $sql .= ' WHERE r.fk_soc = '. (int) $invoice_predefined->socid;
2360
2361 $resql = $db->query($sql);
2362 if ($resql) {
2363 $num = $db->num_rows($resql);
2364 $i = 0;
2365
2366 if ($num > 0) {
2367 print '<tr><td>'.$langs->trans('CreateFromRepeatableInvoice').'</td><td>';
2368 //print '<input type="hidden" name="fac_rec" id="fac_rec" value="'.$fac_recid.'">';
2369 print '<select class="flat" id="fac_rec" name="fac_rec">'; // We may want to change the template to use
2370 print '<option value="0" selected></option>';
2371 while ($i < $num) {
2372 $objp = $db->fetch_object($resql);
2373 print '<option value="'.$objp->rowid.'"';
2374 if ($fac_recid == $objp->rowid) {
2375 print ' selected';
2376 $exampletemplateinvoice->fetch($fac_recid);
2377 }
2378 print '>'.$objp->title.' ('.price($objp->total_ttc).' '.$langs->trans("TTC").')</option>';
2379 $i++;
2380 }
2381 print '</select>';
2382 // Option to reload page to retrieve customer information. Note, this clear other input
2383 if (!getDolGlobalString('RELOAD_PAGE_ON_TEMPLATE_CHANGE_DISABLED')) {
2384 print '<script type="text/javascript">
2385 $(document).ready(function() {
2386 $("#fac_rec").change(function() {
2387 console.log("We have changed the template invoice - Reload page");
2388 // reload page
2389 $("input[name=action]").val("create");
2390 $("form[name=add]").submit();
2391 });
2392 });
2393 </script>';
2394 }
2395 print '</td></tr>';
2396 }
2397 $db->free($resql);
2398 } else {
2399 dol_print_error($db);
2400 }
2401 }
2402
2403 // Ref supplier
2404 print '<tr><td class="fieldrequired">'.$langs->trans('RefSupplierBill').'</td><td><input name="ref_supplier" value="'.(GETPOSTISSET('ref_supplier') ? GETPOST('ref_supplier') : (!empty($objectsrc->ref_supplier) ? $objectsrc->ref_supplier : '')).'" type="text"';
2405 if (!empty($societe->id) && $societe->id > 0) {
2406 print ' autofocus';
2407 }
2408 print '></td>';
2409 print '</tr>';
2410
2411 print '<tr><td class="tdtop fieldrequired">'.$langs->trans('Type').'</td><td>';
2412
2413 print '<div class="tagtable">'."\n";
2414
2415 // Standard invoice
2416 print '<div class="tagtr listofinvoicetype"><div class="tagtd listofinvoicetype">';
2417 $tmp = '<input type="radio" id="radio_standard" name="type" value="0"'.(GETPOSTINT('type') ? '' : 'checked').'> ';
2418 $desc = $form->textwithpicto($tmp.'<label for="radio_standard">'.$langs->trans("InvoiceStandardAsk").'</label>', $langs->transnoentities("InvoiceStandardDesc"), 1, 'help', '', 0, 3);
2419 print $desc;
2420 print '</div></div>';
2421
2422 if (empty($origin) || ($origin == 'order_supplier' && !empty($originid))) {
2423 // Deposit - Down payment
2424 if (!getDolGlobalString('INVOICE_DISABLE_DEPOSIT')) {
2425 print '<div class="tagtr listofinvoicetype"><div class="tagtd listofinvoicetype">';
2426 $tmp = '<input type="radio" id="radio_deposit" name="type" value="3"' . (GETPOSTINT('type') == 3 ? ' checked' : '') . '> ';
2427 print '<script type="text/javascript">
2428 jQuery(document).ready(function() {
2429 jQuery("#typestandardinvoice, #valuestandardinvoice").click(function() {
2430 jQuery("#radio_standard").prop("checked", true);
2431 });
2432 jQuery("#typedeposit, #valuedeposit").click(function() {
2433 jQuery("#radio_deposit").prop("checked", true);
2434 });
2435 jQuery("#typedeposit").change(function() {
2436 console.log("We change type of down payment");
2437 jQuery("#radio_deposit").prop("checked", true);
2438 setRadioForTypeOfInvoice();
2439 });
2440 jQuery("#radio_standard, #radio_deposit, #radio_replacement, #radio_template").change(function() {
2441 setRadioForTypeOfInvoice();
2442 });
2443 function setRadioForTypeOfInvoice() {
2444 console.log("Change radio");
2445 if (jQuery("#radio_deposit").prop("checked") && (jQuery("#typedeposit").val() == \'amount\' || jQuery("#typedeposit").val() == \'variable\')) {
2446 jQuery(".checkforselect").prop("disabled", true);
2447 jQuery(".checkforselect").prop("checked", false);
2448 } else {
2449 jQuery(".checkforselect").prop("disabled", false);
2450 jQuery(".checkforselect").prop("checked", true);
2451 }
2452 }
2453 });
2454 </script>';
2455
2456 $tmp = $tmp.'<label for="radio_deposit" >'.$langs->trans("InvoiceDeposit").'</label>';
2457 // @phan-suppress-next-line PhanPluginSuspiciousParamOrder
2458 $desc = $form->textwithpicto($tmp, $langs->transnoentities("InvoiceDepositDesc"), 1, 'help', '', 0, 3);
2459 print '<table class="nobordernopadding"><tr>';
2460 print '<td>';
2461 print $desc;
2462 print '</td>';
2463 if ($origin == 'order_supplier') {
2464 print '<td class="nowrap" style="padding-left: 15px">';
2465 $arraylist = array(
2466 'amount' => $langs->transnoentitiesnoconv('FixAmount', $langs->transnoentitiesnoconv('Deposit')),
2467 'variable' => $langs->transnoentitiesnoconv('VarAmountOneLine', $langs->transnoentitiesnoconv('Deposit')),
2468 'variablealllines' => $langs->transnoentitiesnoconv('VarAmountAllLines')
2469 );
2470 print $form->selectarray('typedeposit', $arraylist, GETPOST('typedeposit', 'aZ09'), 0, 0, 0, '', 1);
2471 print '</td>';
2472 print '<td class="nowrap" style="padding-left: 5px">';
2473 print '<span class="opacitymedium paddingleft">'.$langs->trans("AmountOrPercent").'</span><input type="text" id="valuedeposit" name="valuedeposit" class="width75 right" value="' . GETPOSTINT('valuedeposit') . '"/>';
2474 print '</td>';
2475 }
2476 print '</tr></table>';
2477
2478 print '</div></div>';
2479 }
2480 }
2481
2482 /* Not yet supported for supplier
2483 if ($societe->id > 0)
2484 {
2485 // Replacement
2486 if (empty($conf->global->INVOICE_DISABLE_REPLACEMENT))
2487 {
2488 // Type invoice
2489 $facids = $facturestatic->list_replacable_supplier_invoices($societe->id);
2490 if ($facids < 0) {
2491 dol_print_error($db, $facturestatic->error, $facturestatic->errors);
2492 exit();
2493 }
2494 $options = "";
2495 foreach ($facids as $facparam)
2496 {
2497 $options .= '<option value="' . $facparam ['id'] . '"';
2498 if ($facparam ['id'] == GETPOST('fac_replacement') {
2499 $options .= ' selected';
2500 }
2501 $options .= '>' . $facparam ['ref'];
2502 $options .= ' (' . $facturestatic->LibStatut(0, $facparam ['status']) . ')';
2503 $options .= '</option>';
2504 }
2505
2506 print '<!-- replacement line -->';
2507 print '<div class="tagtr listofinvoicetype"><div class="tagtd listofinvoicetype">';
2508 $tmp='<input type="radio" name="type" id="radio_replacement" value="1"' . (GETPOST('type') == 1 ? ' checked' : '');
2509 if (! $options) $tmp.=' disabled';
2510 $tmp.='> ';
2511 print '<script type="text/javascript">
2512 jQuery(document).ready(function() {
2513 jQuery("#fac_replacement").change(function() {
2514 jQuery("#radio_replacement").prop("checked", true);
2515 });
2516 });
2517 </script>';
2518 $text = $tmp.$langs->trans("InvoiceReplacementAsk") . ' ';
2519 $text .= '<select class="flat" name="fac_replacement" id="fac_replacement"';
2520 if (! $options)
2521 $text .= ' disabled';
2522 $text .= '>';
2523 if ($options) {
2524 $text .= '<option value="-1">&nbsp;</option>';
2525 $text .= $options;
2526 } else {
2527 $text .= '<option value="-1">' . $langs->trans("NoReplacableInvoice") . '</option>';
2528 }
2529 $text .= '</select>';
2530 $desc = $form->textwithpicto($text, $langs->transnoentities("InvoiceReplacementDesc"), 1, 'help', '', 0, 3);
2531 print $desc;
2532 print '</div></div>';
2533 }
2534 }
2535 else
2536 {
2537 print '<div class="tagtr listofinvoicetype"><div class="tagtd listofinvoicetype">';
2538 $tmp='<input type="radio" name="type" id="radio_replacement" value="0" disabled> ';
2539 $text = $tmp.$langs->trans("InvoiceReplacement") . ' ';
2540 $text.= '('.$langs->trans("YouMustCreateInvoiceFromSupplierThird").') ';
2541 $desc = $form->textwithpicto($text, $langs->transnoentities("InvoiceReplacementDesc"), 1, 'help', '', 0, 3);
2542 print $desc;
2543 print '</div></div>';
2544 }
2545 */
2546
2547 if (empty($origin)) {
2548 if (!empty($societe->id) && $societe->id > 0) {
2549 // Credit note
2550 if (!getDolGlobalString('INVOICE_DISABLE_CREDIT_NOTE')) {
2551 // Show link for credit note
2552 $facids = $facturestatic->list_qualified_avoir_supplier_invoices($societe->id);
2553 if ($facids < 0) {
2554 dol_print_error($db, $facturestatic->error, $facturestatic->errors);
2555 exit;
2556 }
2557 $optionsav = "";
2558 $newinvoice_static = new FactureFournisseur($db);
2559 foreach ($facids as $key => $valarray) {
2560 $newinvoice_static->id = $key;
2561 $newinvoice_static->ref = $valarray ['ref'];
2562 $newinvoice_static->status = $valarray ['status'];
2563 $newinvoice_static->statut = $valarray ['status'];
2564 $newinvoice_static->type = $valarray ['type'];
2565 $newinvoice_static->paid = $valarray ['paye'];
2566 $newinvoice_static->paye = $valarray ['paye'];
2567
2568 $optionsav .= '<option value="'.$key.'"';
2569 if ($key == GETPOSTINT('fac_avoir')) {
2570 $optionsav .= ' selected';
2571 }
2572 $optionsav .= '>';
2573 $optionsav .= $newinvoice_static->ref;
2574 $optionsav .= ' ('.$newinvoice_static->getLibStatut(1, $valarray ['paymentornot']).')';
2575 $optionsav .= '</option>';
2576 }
2577
2578 print '<div class="tagtr listofinvoicetype"><div class="tagtd listofinvoicetype">';
2579 $tmp = '<input type="radio" id="radio_creditnote" name="type" value="2"'.(GETPOST('type') == 2 ? ' checked' : '');
2580 if (!$optionsav && !getDolGlobalString('INVOICE_CREDIT_NOTE_STANDALONE')) {
2581 $tmp .= ' disabled';
2582 }
2583 $tmp .= '> ';
2584 // Show credit note options only if we checked credit note
2585 print '<script type="text/javascript">
2586 jQuery(document).ready(function() {
2587 if (! jQuery("#radio_creditnote").is(":checked"))
2588 {
2589 jQuery("#credit_note_options").hide();
2590 }
2591 jQuery("#radio_creditnote").click(function() {
2592 jQuery("#credit_note_options").show();
2593 });
2594 jQuery("#radio_standard, #radio_replacement, #radio_deposit").click(function() {
2595 jQuery("#credit_note_options").hide();
2596 });
2597 });
2598 </script>';
2599 $text = $tmp.'<label for="radio_creditnote">'.$langs->transnoentities("InvoiceAvoirAsk").'</label> ';
2600 // $text.='<input type="text" value="">';
2601 $text .= '<select class="flat valignmiddle" name="fac_avoir" id="fac_avoir"';
2602 if (!$optionsav) {
2603 $text .= ' disabled';
2604 }
2605 $text .= '>';
2606 if ($optionsav) {
2607 $text .= '<option value="-1"></option>';
2608 $text .= $optionsav;
2609 } else {
2610 $text .= '<option value="-1">'.$langs->trans("NoInvoiceToCorrect").'</option>';
2611 }
2612 $text .= '</select>';
2613 $desc = $form->textwithpicto($text, $langs->transnoentities("InvoiceAvoirDesc"), 1, 'help', '', 0, 3);
2614 print $desc;
2615
2616 print '<div id="credit_note_options" class="clearboth">';
2617 print '&nbsp;&nbsp;&nbsp; <input type="checkbox" name="invoiceAvoirWithLines" id="invoiceAvoirWithLines" value="1" onclick="if($(this).is(\':checked\') ) { $(\'#radio_creditnote\').prop(\'checked\', true); $(\'#invoiceAvoirWithPaymentRestAmount\').removeAttr(\'checked\'); }" '.(GETPOSTINT('invoiceAvoirWithLines') > 0 ? 'checked' : '').' /> ';
2618 print '<label for="invoiceAvoirWithLines">'.$langs->trans('invoiceAvoirWithLines')."</label>";
2619 print '<br>&nbsp;&nbsp;&nbsp; <input type="checkbox" name="invoiceAvoirWithPaymentRestAmount" id="invoiceAvoirWithPaymentRestAmount" value="1" onclick="if($(this).is(\':checked\') ) { $(\'#radio_creditnote\').prop(\'checked\', true); $(\'#invoiceAvoirWithLines\').removeAttr(\'checked\'); }" '.(GETPOSTINT('invoiceAvoirWithPaymentRestAmount') > 0 ? 'checked' : '').' /> ';
2620 print '<label for="invoiceAvoirWithPaymentRestAmount">'.$langs->trans('invoiceAvoirWithPaymentRestAmount')."</label>";
2621 print '</div>';
2622
2623 print '</div></div>';
2624 }
2625 } else {
2626 print '<div class="tagtr listofinvoicetype"><div class="tagtd listofinvoicetype">';
2627 if (!getDolGlobalString('INVOICE_CREDIT_NOTE_STANDALONE')) {
2628 $tmp = '<input type="radio" name="type" id="radio_creditnote" value="0" disabled> ';
2629 } else {
2630 $tmp = '<input type="radio" name="type" id="radio_creditnote" value="2"> ';
2631 }
2632 $text = $tmp.$langs->trans("InvoiceAvoir").' ';
2633 $text .= '<span class="opacitymedium">('.$langs->trans("YouMustCreateInvoiceFromSupplierThird").')</span> ';
2634 $desc = $form->textwithpicto($text, $langs->transnoentities("InvoiceAvoirDesc"), 1, 'help', '', 0, 3);
2635 print $desc;
2636 print '</div></div>'."\n";
2637 }
2638 }
2639
2640 print '</div>';
2641
2642 print '</td></tr>';
2643
2644
2645 // Invoice Subtype
2646 if (getDolGlobalInt('INVOICE_SUBTYPE_ENABLED')) {
2647 print '<tr><td class="fieldrequired">'.$langs->trans('InvoiceSubtype').'</td><td colspan="2">';
2648 print $form->getSelectInvoiceSubtype(GETPOST('subtype'), 'subtype', 1, 0, '');
2649 print '</td></tr>';
2650 }
2651
2652 if (!empty($societe->id) && $societe->id > 0) {
2653 // Discounts for third party
2654 print '<tr><td>'.$langs->trans('Discounts').'</td><td>';
2655
2656 $thirdparty = $societe;
2657 $discount_type = 1;
2658 $backtopage = urlencode($_SERVER["PHP_SELF"].'?socid='.$societe->id.'&action='.$action.'&origin='.GETPOST('origin').'&originid='.GETPOST('originid'));
2659 include DOL_DOCUMENT_ROOT.'/core/tpl/object_discounts.tpl.php';
2660
2661 print '</td></tr>';
2662 }
2663
2664 // Label
2665 print '<tr><td>'.$langs->trans('Label').'</td><td><input class="minwidth200" name="label" value="'.dol_escape_htmltag(GETPOST('label')).'" type="text"></td></tr>';
2666
2667 // Date invoice
2668 print '<tr><td class="fieldrequired">'.$langs->trans('DateInvoice').'</td><td>';
2669 print img_picto('', 'action', 'class="pictofixedwidth"');
2670 print $form->selectDate($dateinvoice, '', 0, 0, 0, "add", 1, 1);
2671 print '</td></tr>';
2672
2673 // Payment term
2674 print '<tr><td class="nowrap">'.$langs->trans('PaymentConditionsShort').'</td><td>';
2675 print img_picto('', 'payment', 'class="pictofixedwidth"');
2676 print $form->getSelectConditionsPaiements($cond_reglement_id, 'cond_reglement_id', -1, 1);
2677
2678 print '</td></tr>';
2679
2680 // Due date
2681 print '<tr><td>'.$langs->trans('DateMaxPayment').'</td><td>';
2682 print img_picto('', 'action', 'class="pictofixedwidth"');
2683 print $form->selectDate($datedue, 'ech', 0, 0, 0, "add", 1, 1);
2684 print '</td></tr>';
2685
2686 // Payment mode
2687 print '<tr><td>'.$langs->trans('PaymentMode').'</td><td>';
2688 print img_picto('', 'bank', 'class="pictofixedwidth"');
2689 $form->select_types_paiements($mode_reglement_id, 'mode_reglement_id', 'DBIT', 0, 1, 0, 0, 1, 'maxwidth200 widthcentpercentminusx');
2690 print '</td></tr>';
2691
2692 // Bank Account
2693 if (isModEnabled("bank")) {
2694 print '<tr><td>'.$langs->trans('BankAccount').'</td><td>';
2695 // when bank account is empty (means not override by payment mode form a other object, like third-party), try to use default value
2696 print img_picto('', 'bank_account', 'class="pictofixedwidth"').$form->select_comptes($fk_account, 'fk_account', 0, '', 1, '', 0, 'maxwidth200 widthcentpercentminusx', 1);
2697 print '</td></tr>';
2698 }
2699
2700 // Project
2701 if (isModEnabled('project')) {
2702 $formproject = new FormProjets($db);
2703
2704 $langs->load('projects');
2705 print '<tr><td>'.$langs->trans('Project').'</td><td>';
2706 print img_picto('', 'project', 'class="pictofixedwidth"').$formproject->select_projects((!getDolGlobalString('PROJECT_CAN_ALWAYS_LINK_TO_ALL_SUPPLIERS') ? $societe->id : -1), $projectid, 'projectid', 0, 0, 1, 1, 0, 0, 0, '', 1, 0, 'maxwidth500 widthcentpercentminusxx');
2707 print ' <a href="'.DOL_URL_ROOT.'/projet/card.php?socid='.(!empty($soc->id) ? $soc->id : 0).'&action=create&status=1&backtopage='.urlencode($_SERVER["PHP_SELF"].'?action=create&socid='.(!empty($soc->id) ? $soc->id : 0).($fac_recid > 0 ? '&fac_rec='.$fac_recid : '')).'"><span class="fa fa-plus-circle valignmiddle" title="'.$langs->trans("AddProject").'"></span></a>';
2708 print '</td></tr>';
2709 }
2710
2711 // Incoterms
2712 if (isModEnabled('incoterm')) {
2713 print '<tr>';
2714 print '<td><label for="incoterm_id">'.$form->textwithpicto($langs->trans("IncotermLabel"), !empty($objectsrc->label_incoterms) ? $objectsrc->label_incoterms : '', 1).'</label></td>';
2715 print '<td colspan="3" class="maxwidthonsmartphone">';
2716 print img_picto('', 'incoterm', 'class="pictofixedwidth"');
2717 print $form->select_incoterms(GETPOSTISSET('incoterm_id') ? GETPOST('incoterm_id', 'alphanohtml') : (!empty($objectsrc->fk_incoterms) ? $objectsrc->fk_incoterms : ''), GETPOSTISSET('location_incoterms') ? GETPOST('location_incoterms', 'alphanohtml') : (!empty($objectsrc->location_incoterms) ? $objectsrc->location_incoterms : ''));
2718 print '</td></tr>';
2719 }
2720
2721 // Vat reverse-charge by default
2722 if (getDolGlobalString('ACCOUNTING_FORCE_ENABLE_VAT_REVERSE_CHARGE')) {
2723 require_once DOL_DOCUMENT_ROOT . '/core/lib/company.lib.php';
2724 print '<tr><td>' . $langs->trans('VATReverseCharge') . '</td><td>';
2725 // Try to propose to use VAT reverse charge even if the VAT reverse charge is not activated in the supplier card, if this corresponds to the context of use, the activation is proposed
2726 if (GETPOSTISSET('vat_reverse_charge')) { // Check if form was submitted previously
2727 $vat_reverse_charge = (GETPOST('vat_reverse_charge', 'alpha') == 'on' || GETPOST('vat_reverse_charge', 'alpha') == '1') ? 1 : 0;
2728 } elseif ($vat_reverse_charge == 1 || $societe->vat_reverse_charge == 1 || ($societe->country_code != 'FR' && isInEEC($societe) && !empty($societe->tva_intra))) {
2729 $vat_reverse_charge = 1;
2730 } else {
2731 $vat_reverse_charge = 0;
2732 }
2733
2734 print '<input type="checkbox" name="vat_reverse_charge"'. (!empty($vat_reverse_charge) ? ' checked ' : '') . '>';
2735 print '</td></tr>';
2736 }
2737
2738 // Multicurrency
2739 if (isModEnabled("multicurrency")) {
2740 print '<tr>';
2741 print '<td>'.$form->editfieldkey('Currency', 'multicurrency_code', '', $object, 0).'</td>';
2742 print '<td class="maxwidthonsmartphone">';
2743 print img_picto('', 'currency', 'class="pictofixedwidth"');
2744 $used_currency_code = $currency_code;
2745 if (!GETPOST('changecompany')) {
2746 $used_currency_code = GETPOSTISSET('multicurrency_code') ? GETPOST('multicurrency_code', 'alpha') : $currency_code;
2747 }
2748 print $form->selectMultiCurrency($used_currency_code, 'multicurrency_code');
2749 print '</td></tr>';
2750 }
2751
2752 // Help of substitution key
2753 $htmltext = '';
2754 if ($fac_recid > 0) {
2755 $dateexample = $dateinvoice;
2756 if (empty($dateexample)) {
2757 $dateexample = dol_now();
2758 }
2759 $substitutionarray = array(
2760 '__TOTAL_HT__' => $langs->trans("AmountHT").' ('.$langs->trans("Example").': '.price($exampletemplateinvoice->total_ht).')',
2761 '__TOTAL_TTC__' => $langs->trans("AmountTTC").' ('.$langs->trans("Example").': '.price($exampletemplateinvoice->total_ttc).')',
2762 '__INVOICE_PREVIOUS_MONTH__' => $langs->trans("PreviousMonthOfInvoice").' ('.$langs->trans("Example").': '.dol_print_date(dol_time_plus_duree($dateexample, -1, 'm'), '%m').')',
2763 '__INVOICE_MONTH__' => $langs->trans("MonthOfInvoice").' ('.$langs->trans("Example").': '.dol_print_date($dateexample, '%m').')',
2764 '__INVOICE_NEXT_MONTH__' => $langs->trans("NextMonthOfInvoice").' ('.$langs->trans("Example").': '.dol_print_date(dol_time_plus_duree($dateexample, 1, 'm'), '%m').')',
2765 '__INVOICE_PREVIOUS_MONTH_TEXT__' => $langs->trans("TextPreviousMonthOfInvoice").' ('.$langs->trans("Example").': '.dol_print_date(dol_time_plus_duree($dateexample, -1, 'm'), '%B').')',
2766 '__INVOICE_MONTH_TEXT__' => $langs->trans("TextMonthOfInvoice").' ('.$langs->trans("Example").': '.dol_print_date($dateexample, '%B').')',
2767 '__INVOICE_NEXT_MONTH_TEXT__' => $langs->trans("TextNextMonthOfInvoice").' ('.$langs->trans("Example").': '.dol_print_date(dol_time_plus_duree($dateexample, 1, 'm'), '%B').')',
2768 '__INVOICE_PREVIOUS_YEAR__' => $langs->trans("PreviousYearOfInvoice").' ('.$langs->trans("Example").': '.dol_print_date(dol_time_plus_duree($dateexample, -1, 'y'), '%Y').')',
2769 '__INVOICE_YEAR__' => $langs->trans("YearOfInvoice").' ('.$langs->trans("Example").': '.dol_print_date($dateexample, '%Y').')',
2770 '__INVOICE_NEXT_YEAR__' => $langs->trans("NextYearOfInvoice").' ('.$langs->trans("Example").': '.dol_print_date(dol_time_plus_duree($dateexample, 1, 'y'), '%Y').')'
2771 );
2772
2773 $htmltext = '<i>'.$langs->trans("FollowingConstantsWillBeSubstituted").':<br>';
2774 foreach ($substitutionarray as $key => $val) {
2775 $htmltext .= $key.' = '.$langs->trans($val).'<br>';
2776 }
2777 $htmltext .= '</i>';
2778 }
2779
2780 // Intracomm report
2781 if (isModEnabled('intracommreport')) {
2782 $langs->loadLangs(array("intracommreport"));
2783 print '<!-- If module intracomm on -->'."\n";
2784 print '<tr><td>'.$langs->trans('IntracommReportTransportMode').'</td><td>';
2785 $form->selectTransportMode(GETPOSTISSET('transport_mode_id') ? GETPOST('transport_mode_id') : $transport_mode_id, 'transport_mode_id');
2786 print '</td></tr>';
2787 }
2788
2789 if (empty($reshook)) {
2790 print $object->showOptionals($extrafields, 'create');
2791 }
2792
2793 // Public note
2794 print '<tr><td>'.$langs->trans('NotePublic').'</td>';
2795 print '<td>';
2796 $doleditor = new DolEditor('note_public', (GETPOSTISSET('note_public') ? GETPOST('note_public', 'restricthtml') : $note_public), '', 80, 'dolibarr_notes', 'In', 0, false, !getDolGlobalString('FCKEDITOR_ENABLE_NOTE_PUBLIC') ? 0 : 1, ROWS_3, '90%');
2797 print $doleditor->Create(1);
2798 print '</td>';
2799 // print '<td><textarea name="note" wrap="soft" cols="60" rows="'.ROWS_5.'"></textarea></td>';
2800 print '</tr>';
2801
2802 // Private note
2803 print '<tr><td>'.$langs->trans('NotePrivate').'</td>';
2804 print '<td>';
2805 $doleditor = new DolEditor('note_private', (GETPOSTISSET('note_private') ? GETPOST('note_private', 'restricthtml') : $note_private), '', 80, 'dolibarr_notes', 'In', 0, false, !getDolGlobalString('FCKEDITOR_ENABLE_NOTE_PRIVATE') ? 0 : 1, ROWS_3, '90%');
2806 print $doleditor->Create(1);
2807 print '</td>';
2808 // print '<td><textarea name="note" wrap="soft" cols="60" rows="'.ROWS_5.'"></textarea></td>';
2809 print '</tr>';
2810
2811
2812 if (!empty($objectsrc) && is_object($objectsrc)) {
2813 print "\n<!-- ".$classname." info -->";
2814 print "\n";
2815 print '<input type="hidden" name="amount" value="'.$objectsrc->total_ht.'">'."\n";
2816 print '<input type="hidden" name="total" value="'.$objectsrc->total_ttc.'">'."\n";
2817 print '<input type="hidden" name="tva" value="'.$objectsrc->total_tva.'">'."\n";
2818 print '<input type="hidden" name="origin" value="'.$objectsrc->element.'">';
2819 print '<input type="hidden" name="originid" value="'.$objectsrc->id.'">';
2820
2821 $txt = $langs->trans($classname);
2822 if ($classname == 'CommandeFournisseur') {
2823 $langs->load('orders');
2824 $txt = $langs->trans("SupplierOrder");
2825 }
2826 print '<tr><td>'.$txt.'</td><td>'.$objectsrc->getNomUrl(1);
2827 // We check if Origin document (id and type is known) has already at least one invoice attached to it
2828 $objectsrc->fetchObjectLinked($originid, $origin, null, 'invoice_supplier');
2829
2830 $invoice_supplier = $objectsrc->linkedObjects['invoice_supplier'];
2831 '@phan-var-force null|FactureFournisseur[] $invoice_supplier';
2832
2833 // count function need a array as argument (Note: the array must implement Countable too)
2834 if (is_array($invoice_supplier)) {
2835 $cntinvoice = count($invoice_supplier);
2836
2837 if ($cntinvoice >= 1) {
2838 setEventMessages('WarningBillExist', null, 'warnings');
2839 echo ' ('.$langs->trans('LatestRelatedBill').end($invoice_supplier)->getNomUrl(1).')';
2840 }
2841 }
2842
2843 print '</td></tr>';
2844 print '<tr><td>'.$langs->trans('AmountHT').'</td><td>'.price($objectsrc->total_ht).'</td></tr>';
2845 print '<tr><td>'.$langs->trans('AmountVAT').'</td><td>'.price($objectsrc->total_tva)."</td></tr>";
2846 if ($mysoc->localtax1_assuj == "1" || $object->total_localtax1 != 0) { //Localtax1
2847 print '<tr><td>'.$langs->transcountry("AmountLT1", $mysoc->country_code).'</td><td>'.price($objectsrc->total_localtax1)."</td></tr>";
2848 }
2849
2850 if ($mysoc->localtax2_assuj == "1" || $object->total_localtax2 != 0) { //Localtax2
2851 print '<tr><td>'.$langs->transcountry("AmountLT2", $mysoc->country_code).'</td><td>'.price($objectsrc->total_localtax2)."</td></tr>";
2852 }
2853 print '<tr><td>'.$langs->trans('AmountTTC').'</td><td>'.price($objectsrc->total_ttc)."</td></tr>";
2854
2855 if (isModEnabled("multicurrency")) {
2856 print '<tr><td>'.$langs->trans('MulticurrencyAmountHT').'</td><td>'.price($objectsrc->multicurrency_total_ht).'</td></tr>';
2857 print '<tr><td>'.$langs->trans('MulticurrencyAmountVAT').'</td><td>'.price($objectsrc->multicurrency_total_tva)."</td></tr>";
2858 print '<tr><td>'.$langs->trans('MulticurrencyAmountTTC').'</td><td>'.price($objectsrc->multicurrency_total_ttc)."</td></tr>";
2859 }
2860 }
2861
2862 // Other options
2863 $parameters = array();
2864 $reshook = $hookmanager->executeHooks('formObjectOptions', $parameters, $object, $action); // Note that $action and $object may have been modified by hook
2865 print $hookmanager->resPrint;
2866
2867
2868 print "</table>\n";
2869 }
2870
2871 print dol_get_fiche_end();
2872
2873 print $form->buttonsSaveCancel("CreateDraft");
2874
2875 // Show origin lines
2876 if (!empty($objectsrc) && is_object($objectsrc)) {
2877 print '<br>';
2878
2879 $title = $langs->trans('ProductsAndServices');
2880 print load_fiche_titre($title);
2881
2882 print '<div class="div-table-responsive-no-min">';
2883 print '<table class="noborder centpercent">';
2884
2885 $objectsrc->printOriginLinesList('', $selectedLines);
2886
2887 print '</table>';
2888 print '</div>';
2889 }
2890
2891 print "</form>\n";
2892} else {
2893 if ($id > 0 || !empty($ref)) {
2894 //
2895 // View or edit mode
2896 //
2897 $now = dol_now();
2898
2899 $productstatic = new Product($db);
2900
2901 $result = $object->fetch($id, $ref);
2902 if ($result <= 0) {
2903 $langs->load("errors");
2904 print $langs->trans("ErrorRecordNotFound");
2905 llxFooter();
2906 $db->close();
2907 exit;
2908 }
2909
2910 $result = $object->fetch_thirdparty();
2911 if ($result < 0) {
2912 dol_print_error($db, $object->error, $object->errors);
2913 exit;
2914 }
2915
2916 $societe = $object->thirdparty;
2917
2918 $totalpaid = $object->getSommePaiement();
2919 $totalcreditnotes = $object->getSumCreditNotesUsed();
2920 $totaldeposits = $object->getSumDepositsUsed();
2921 // print "totalpaid=".$totalpaid." totalcreditnotes=".$totalcreditnotes." totaldeposts=".$totaldeposits."
2922 // selleruserrevenuestamp=".$selleruserevenustamp;
2923
2924 // We can also use bcadd to avoid pb with floating points
2925 // For example print 239.2 - 229.3 - 9.9; does not return 0.
2926 // $resteapayer=bcadd($object->total_ttc,$totalpaid,$conf->global->MAIN_MAX_DECIMALS_TOT);
2927 // $resteapayer=bcadd($resteapayer,$totalavoir,$conf->global->MAIN_MAX_DECIMALS_TOT);
2928 $resteapayer = price2num($object->total_ttc - $totalpaid - $totalcreditnotes - $totaldeposits, 'MT');
2929
2930 // Multicurrency
2931 $multicurrency_resteapayer = 0;
2932 if (isModEnabled("multicurrency")) {
2933 $multicurrency_totalpaid = $object->getSommePaiement(1);
2934 $multicurrency_totalcreditnotes = $object->getSumCreditNotesUsed(1);
2935 $multicurrency_totaldeposits = $object->getSumDepositsUsed(1);
2936 $multicurrency_resteapayer = price2num($object->multicurrency_total_ttc - $multicurrency_totalpaid - $multicurrency_totalcreditnotes - $multicurrency_totaldeposits, 'MT');
2937 // Code to fix case of corrupted data
2938 // TODO We should not need this. Also data comes from not reliable value of $object->multicurrency_total_ttc that may be wrong if it was
2939 // calculated by summing lines that were in a currency for some of them and into another for others (lines from discount/down payment into another currency for example)
2940 if ($resteapayer == 0 && $multicurrency_resteapayer != 0 && $object->multicurrency_code != $conf->currency) {
2941 $resteapayer = price2num((float) $multicurrency_resteapayer / $object->multicurrency_tx, 'MT');
2942 }
2943 }
2944
2945 if ($object->paid) {
2946 $resteapayer = 0;
2947 }
2948 $resteapayeraffiche = $resteapayer;
2949
2950 if (getDolGlobalString('FACTURE_SUPPLIER_DEPOSITS_ARE_JUST_PAYMENTS')) { // Never use this
2951 $filterabsolutediscount = "fk_invoice_supplier_source IS NULL"; // If we want deposit to be subtracted to payments only and not to total of final invoice
2952 $filtercreditnote = "fk_invoice_supplier_source IS NOT NULL"; // If we want deposit to be subtracted to payments only and not to total of final invoice
2953 } else {
2954 $filterabsolutediscount = "fk_invoice_supplier_source IS NULL OR (description LIKE '(DEPOSIT)%' AND description NOT LIKE '(EXCESS PAID)%')";
2955 $filtercreditnote = "fk_invoice_supplier_source IS NOT NULL AND (description NOT LIKE '(DEPOSIT)%' OR description LIKE '(EXCESS PAID)%')";
2956 }
2957
2958 $absolute_discount = $societe->getAvailableDiscounts(null, $filterabsolutediscount, 0, 1);
2959 $absolute_creditnote = $societe->getAvailableDiscounts(null, $filtercreditnote, 0, 1);
2960 $absolute_discount = price2num($absolute_discount, 'MT');
2961 $absolute_creditnote = price2num($absolute_creditnote, 'MT');
2962
2963 /*
2964 * View card
2965 */
2966 $objectidnext = $object->getIdReplacingInvoice();
2967
2969 $titre = $langs->trans('SupplierInvoice');
2970
2971 print dol_get_fiche_head($head, 'card', $titre, -1, 'supplier_invoice', 0, '', '', 0, '', 1);
2972
2973 $formconfirm = '';
2974
2975 // Confirmation de la conversion de l'avoir en reduc
2976 if ($action == 'converttoreduc') {
2977 $type_fac = '';
2979 $type_fac = 'ExcessPaid';
2980 } elseif ($object->type == FactureFournisseur::TYPE_CREDIT_NOTE) {
2981 $type_fac = 'CreditNote';
2982 } elseif ($object->type == FactureFournisseur::TYPE_DEPOSIT) {
2983 $type_fac = 'Deposit';
2984 }
2985 $text = $langs->trans('ConfirmConvertToReducSupplier', strtolower($langs->transnoentities($type_fac)));
2986 $text .= '<br>'.$langs->trans('ConfirmConvertToReducSupplier2');
2987 $formconfirm = $form->formconfirm($_SERVER['PHP_SELF'].'?facid='.$object->id, $langs->trans('ConvertToReduc'), $text, 'confirm_converttoreduc', '', "yes", 2);
2988 }
2989
2990 // Clone confirmation
2991 if ($action == 'clone') {
2992 // Create an array for form
2993 $formquestion = array(
2994 array('type' => 'text', 'name' => 'newsupplierref', 'label' => $langs->trans("RefSupplierBill"), 'value' => $langs->trans("CopyOf").' '.$object->ref_supplier),
2995 array('type' => 'date', 'name' => 'newdate', 'label' => $langs->trans("Date"), 'value' => dol_now())
2996 );
2997 // Ask confirmation to clone
2998 $formconfirm = $form->formconfirm($_SERVER["PHP_SELF"].'?id='.$object->id, $langs->trans('ToClone'), $langs->trans('ConfirmCloneInvoice', $object->ref), 'confirm_clone', $formquestion, 'yes', 1, 250);
2999 }
3000
3001 // Confirmation of validation
3002 if ($action == 'valid') {
3003 // We check if number is temporary number
3004 if (preg_match('/^[\‍(]?PROV/i', $object->ref) || empty($object->ref)) {
3005 // empty should not happened, but when it occurs, the test save life
3006 $numref = $object->getNextNumRef($societe);
3007 } else {
3008 $numref = $object->ref;
3009 }
3010
3011 if ($numref < 0) {
3012 setEventMessages($object->error, $object->errors, 'errors');
3013 $action = '';
3014 } else {
3015 $text = $langs->trans('ConfirmValidateBill', $numref);
3016 /*if (isModEnabled('notification'))
3017 {
3018 require_once DOL_DOCUMENT_ROOT .'/core/class/notify.class.php';
3019 $notify=new Notify($db);
3020 $text.='<br>';
3021 $text.=$notify->confirmMessage('BILL_SUPPLIER_VALIDATE',$object->socid, $object);
3022 }*/
3023 $formquestion = array();
3024
3025 $qualified_for_stock_change = 0;
3026 if (!getDolGlobalString('STOCK_SUPPORTS_SERVICES')) {
3027 $qualified_for_stock_change = $object->hasProductsOrServices(2);
3028 } else {
3029 $qualified_for_stock_change = $object->hasProductsOrServices(1);
3030 }
3031
3032 if (isModEnabled('stock') && getDolGlobalString('STOCK_CALCULATE_ON_SUPPLIER_BILL') && $qualified_for_stock_change) {
3033 $langs->load("stocks");
3034 require_once DOL_DOCUMENT_ROOT.'/product/class/html.formproduct.class.php';
3035 $formproduct = new FormProduct($db);
3036 $warehouse = new Entrepot($db);
3037 $warehouse_array = $warehouse->list_array();
3038 if (count($warehouse_array) == 1) {
3039 $label = $object->type == FactureFournisseur::TYPE_CREDIT_NOTE ? $langs->trans("WarehouseForStockDecrease", current($warehouse_array)) : $langs->trans("WarehouseForStockIncrease", current($warehouse_array));
3040 $value = '<input type="hidden" id="idwarehouse" name="idwarehouse" value="'.key($warehouse_array).'">';
3041 } else {
3042 $label = $object->type == FactureFournisseur::TYPE_CREDIT_NOTE ? $langs->trans("SelectWarehouseForStockDecrease") : $langs->trans("SelectWarehouseForStockIncrease");
3043 $value = $formproduct->selectWarehouses(GETPOST('idwarehouse') ? GETPOST('idwarehouse') : 'ifone', 'idwarehouse', '', 1);
3044 }
3045 $formquestion = array(
3046 array('type' => 'other', 'name' => 'idwarehouse', 'label' => $label, 'value' => $value)
3047 );
3048 }
3049
3050 $formconfirm = $form->formconfirm($_SERVER["PHP_SELF"].'?id='.$object->id, $langs->trans('ValidateBill'), $text, 'confirm_valid', $formquestion, 1, 1);
3051 }
3052 }
3053
3054 // Confirmation edit (back to draft)
3055 if ($action == 'edit') {
3056 $formquestion = array();
3057
3058 $qualified_for_stock_change = 0;
3059 if (!getDolGlobalString('STOCK_SUPPORTS_SERVICES')) {
3060 $qualified_for_stock_change = $object->hasProductsOrServices(2);
3061 } else {
3062 $qualified_for_stock_change = $object->hasProductsOrServices(1);
3063 }
3064 if (isModEnabled('stock') && getDolGlobalString('STOCK_CALCULATE_ON_SUPPLIER_BILL') && $qualified_for_stock_change) {
3065 $langs->load("stocks");
3066 require_once DOL_DOCUMENT_ROOT.'/product/class/html.formproduct.class.php';
3067 $formproduct = new FormProduct($db);
3068 $warehouse = new Entrepot($db);
3069 $warehouse_array = $warehouse->list_array();
3070 if (count($warehouse_array) == 1) {
3071 $label = $object->type == FactureFournisseur::TYPE_CREDIT_NOTE ? $langs->trans("WarehouseForStockIncrease", current($warehouse_array)) : $langs->trans("WarehouseForStockDecrease", current($warehouse_array));
3072 $value = '<input type="hidden" id="idwarehouse" name="idwarehouse" value="'.key($warehouse_array).'">';
3073 } else {
3074 $label = $object->type == FactureFournisseur::TYPE_CREDIT_NOTE ? $langs->trans("SelectWarehouseForStockIncrease") : $langs->trans("SelectWarehouseForStockDecrease");
3075 $value = $formproduct->selectWarehouses(GETPOST('idwarehouse') ? GETPOST('idwarehouse') : 'ifone', 'idwarehouse', '', 1);
3076 }
3077 $formquestion = array(
3078 array('type' => 'other', 'name' => 'idwarehouse', 'label' => $label, 'value' => $value)
3079 );
3080 }
3081 $formconfirm = $form->formconfirm($_SERVER["PHP_SELF"].'?id='.$object->id, $langs->trans('UnvalidateBill'), $langs->trans('ConfirmUnvalidateBill', $object->ref), 'confirm_edit', $formquestion, 1, 1);
3082 }
3083
3084 // Confirmation set paid
3085 if ($action == 'paid' && ($resteapayer <= 0 || (getDolGlobalString('SUPPLIER_INVOICE_CAN_SET_PAID_EVEN_IF_PARTIALLY_PAID') && $resteapayer == $object->total_ttc))) {
3086 $formconfirm = $form->formconfirm($_SERVER["PHP_SELF"].'?id='.$object->id, $langs->trans('ClassifyPaid'), $langs->trans('ConfirmClassifyPaidBill', $object->ref), 'confirm_paid', '', 0, 1);
3087 }
3088
3089 if ($action == 'paid' && $resteapayer > 0 && (!getDolGlobalString('SUPPLIER_INVOICE_CAN_SET_PAID_EVEN_IF_PARTIALLY_PAID') || $resteapayer != $object->total_ttc)) {
3090 $close = array();
3091 // Code
3092 $i = 0;
3093 $close[$i]['code'] = 'discount_vat'; // escompte
3094 $i++;
3095 $close[$i]['code'] = 'badsupplier';
3096 $i++;
3097 $close[$i]['code'] = 'other';
3098 $i++;
3099 // Help
3100 $i = 0;
3101 $close[$i]['label'] = $langs->trans("HelpEscompte").'<br><br>'.$langs->trans("ConfirmClassifyPaidPartiallyReasonDiscountVatDesc");
3102 $i++;
3103 $close[$i]['label'] = $langs->trans("ConfirmClassifyPaidPartiallyReasonBadSupplierDesc");
3104 $i++;
3105 $close[$i]['label'] = $langs->trans("Other");
3106 $i++;
3107 // Text
3108 $i = 0;
3109 $close[$i]['reason'] = $form->textwithpicto($langs->transnoentities("ConfirmClassifyPaidPartiallyReasonDiscount", $resteapayer, $langs->trans("Currency".$conf->currency)), $close[$i]['label'], 1);
3110 $i++;
3111 $close[$i]['reason'] = $form->textwithpicto($langs->transnoentities("ConfirmClassifyPaidPartiallyReasonBadCustomer", $resteapayer, $langs->trans("Currency".$conf->currency)), $close[$i]['label'], 1);
3112 $i++;
3113 $close[$i]['reason'] = $form->textwithpicto($langs->transnoentities("Other"), $close[$i]['label'], 1);
3114 $i++;
3115 // arrayreasons[code]=reason
3116 $arrayreasons = array();
3117 foreach ($close as $key => $val) {
3118 $arrayreasons[$close[$key]['code']] = $close[$key]['reason'];
3119 }
3120
3121 // Create a form table
3122 $formquestion = array('text' => $langs->trans("ConfirmClassifyPaidPartiallyQuestion"), 0 => array('type' => 'radio', 'name' => 'close_code', 'label' => $langs->trans("Reason"), 'values' => $arrayreasons), 1 => array('type' => 'text', 'name' => 'close_note', 'label' => $langs->trans("Comment"), 'value' => '', 'morecss' => 'minwidth300'));
3123 // Incomplete payment. We ask if the reason is discount or other
3124 $formconfirm = $form->formconfirm($_SERVER["PHP_SELF"].'?facid='.$object->id, $langs->trans('ClassifyPaid'), $langs->trans('ConfirmClassifyPaidPartially', $object->ref), 'confirm_paid_partially', $formquestion, "yes", 1, 310);
3125 }
3126
3127 // Confirmation of the abandoned classification
3128 if ($action == 'canceled') {
3129 // Code
3130 $close[1]['code'] = 'badsupplier';
3131 $close[2]['code'] = 'abandon';
3132 // Help
3133 $close[1]['label'] = $langs->trans("ConfirmClassifyPaidPartiallyReasonBadSupplierDesc");
3134 $close[2]['label'] = $langs->trans("ConfirmClassifyAbandonReasonOtherDesc");
3135 // Text
3136 $close[1]['reason'] = $form->textwithpicto($langs->transnoentities("ConfirmClassifyPaidPartiallyReasonBadSupplier", $object->ref), $close[1]['label'], 1);
3137 $close[2]['reason'] = $form->textwithpicto($langs->transnoentities("ConfirmClassifyAbandonReasonOther"), $close[2]['label'], 1);
3138 // arrayreasons
3139 $arrayreasons[$close[1]['code']] = $close[1]['reason'];
3140 $arrayreasons[$close[2]['code']] = $close[2]['reason'];
3141
3142 // Create a form table
3143 $formquestion = array('text' => $langs->trans("ConfirmCancelBillQuestion"), 0 => array('type' => 'radio', 'name' => 'close_code', 'label' => $langs->trans("Reason"), 'values' => $arrayreasons), 1 => array('type' => 'text', 'name' => 'close_note', 'label' => $langs->trans("Comment"), 'value' => '', 'morecss' => 'minwidth300'));
3144
3145 $formconfirm = $form->formconfirm($_SERVER['PHP_SELF'].'?id='.$object->id, $langs->trans('CancelBill'), $langs->trans('ConfirmCancelBill', $object->ref), 'confirm_canceled', $formquestion, "yes", 1, 280);
3146 }
3147
3148 // Confirmation de la suppression de la facture fournisseur
3149 if ($action == 'delete') {
3150 $formquestion = array();
3151
3152 $qualified_for_stock_change = 0;
3153 if (!getDolGlobalString('STOCK_SUPPORTS_SERVICES')) {
3154 $qualified_for_stock_change = $object->hasProductsOrServices(2);
3155 } else {
3156 $qualified_for_stock_change = $object->hasProductsOrServices(1);
3157 }
3158
3159 if (isModEnabled('stock') && getDolGlobalString('STOCK_CALCULATE_ON_SUPPLIER_BILL') && $qualified_for_stock_change) {
3160 $langs->load("stocks");
3161 require_once DOL_DOCUMENT_ROOT.'/product/class/html.formproduct.class.php';
3162 $formproduct = new FormProduct($db);
3163 $warehouse = new Entrepot($db);
3164 $warehouse_array = $warehouse->list_array();
3165
3166 $selectwarehouse = '<span class="questionrevertstock hidden">';
3167 if (count($warehouse_array) == 1) {
3168 $label = $object->type == FactureFournisseur::TYPE_CREDIT_NOTE ? $langs->trans("WarehouseForStockIncrease", current($warehouse_array)) : $langs->trans("WarehouseForStockDecrease", current($warehouse_array));
3169 $selectwarehouse .= '<input type="hidden" id="idwarehouse" name="idwarehouse" value="'.key($warehouse_array).'">';
3170 } else {
3171 $label = $object->type == FactureFournisseur::TYPE_CREDIT_NOTE ? $langs->trans("SelectWarehouseForStockIncrease") : $langs->trans("SelectWarehouseForStockDecrease");
3172 $selectwarehouse .= $formproduct->selectWarehouses(GETPOST('idwarehouse') ? GETPOST('idwarehouse') : 'ifone', 'idwarehouse', '', 1);
3173 }
3174 $selectwarehouse .= '</span>';
3175
3176 $selectyesno = array(0 => $langs->trans('No'), 1 => $langs->trans('Yes'));
3177
3178 print '<script type="text/javascript">
3179 $(document).ready(function() {
3180 $("#revertstock").change(function() {
3181 if(this.value > 0) {
3182 $(".questionrevertstock").removeClass("hidden");
3183 } else {
3184 $(".questionrevertstock").addClass("hidden");
3185 }
3186 });
3187 });
3188 </script>';
3189
3190 $formquestion = array(
3191 array('type' => 'select', 'name' => 'revertstock', 'label' => $langs->trans("RevertProductsToStock"), 'select_show_empty' => 0, 'values' => $selectyesno),
3192 array('type' => 'other', 'name' => 'idwarehouse', 'label' => $label, 'value' => $selectwarehouse, 'tdclass' => 'questionrevertstock hidden')
3193 );
3194 }
3195
3196 $formconfirm = $form->formconfirm($_SERVER["PHP_SELF"].'?id='.$object->id, $langs->trans('DeleteBill'), $langs->trans('ConfirmDeleteBill'), 'confirm_delete', $formquestion, 1, 1);
3197 }
3198 if ($action == 'deletepayment') {
3199 $payment_id = GETPOST('paiement_id');
3200 $formconfirm = $form->formconfirm($_SERVER["PHP_SELF"].'?id='.$object->id.'&paiement_id='.$payment_id, $langs->trans('DeletePayment'), $langs->trans('ConfirmDeletePayment'), 'confirm_delete_paiement', '', 0, 1);
3201 }
3202
3203 // Confirmation to delete line
3204 if ($action == 'ask_deleteline') {
3205 $formconfirm = $form->formconfirm($_SERVER["PHP_SELF"].'?id='.$object->id.'&lineid='.$lineid, $langs->trans('DeleteProductLine'), $langs->trans('ConfirmDeleteProductLine'), 'confirm_deleteline', '', 0, 1);
3206 }
3207
3208 $parameters = array('formConfirm' => $formconfirm, 'lineid' => $lineid);
3209 $reshook = $hookmanager->executeHooks('formConfirm', $parameters, $object, $action); // Note that $action and $object may have been modified by hook
3210 if (empty($reshook)) {
3211 $formconfirm .= $hookmanager->resPrint;
3212 } elseif ($reshook > 0) {
3213 $formconfirm = $hookmanager->resPrint;
3214 }
3215
3216 // Print form confirm
3217 print $formconfirm;
3218
3219
3220 // Supplier invoice card
3221 $linkback = '<a href="'.DOL_URL_ROOT.'/fourn/facture/list.php?restore_lastsearch_values=1'.(!empty($socid) ? '&socid='.$socid : '').'">'.$langs->trans("BackToList").'</a>';
3222
3223 $morehtmlref = '<div class="refidno">';
3224 // Ref supplier
3225 $morehtmlref .= $form->editfieldkey("RefSupplierBill", 'ref_supplier', $object->ref_supplier, $object, $usercancreate, 'string', '', 0, 1);
3226 $morehtmlref .= $form->editfieldval("RefSupplierBill", 'ref_supplier', $object->ref_supplier, $object, $usercancreate, 'string', '', null, null, '', 1);
3227 // Thirdparty
3228 $morehtmlref .= '<br>'.$object->thirdparty->getNomUrl(1, 'supplier');
3229 if (!getDolGlobalString('MAIN_DISABLE_OTHER_LINK') && $object->thirdparty->id > 0) {
3230 $morehtmlref .= ' <div class="inline-block valignmiddle">(<a class="valignmiddle" href="'.DOL_URL_ROOT.'/fourn/facture/list.php?socid='.((int) $object->thirdparty->id).'&search_company='.urlencode($object->thirdparty->name).'">'.$langs->trans("OtherBills").'</a>)</div>';
3231 }
3232 // Project
3233 if (isModEnabled('project')) {
3234 $langs->load("projects");
3235 $morehtmlref .= '<br>';
3236 if ($permissiontoadd) {
3237 $morehtmlref .= img_picto($langs->trans("Project"), 'project', 'class="pictofixedwidth"');
3238 if ($action != 'classify') {
3239 $morehtmlref .= '<a class="editfielda" href="'.$_SERVER['PHP_SELF'].'?action=classify&token='.newToken().'&id='.((int) $object->id).'">'.img_edit($langs->transnoentitiesnoconv('SetProject')).'</a> ';
3240 }
3241 $morehtmlref .= $form->form_project($_SERVER['PHP_SELF'].'?id='.$object->id, (!getDolGlobalString('PROJECT_CAN_ALWAYS_LINK_TO_ALL_SUPPLIERS') ? $object->socid : -1), $object->fk_project, ($action == 'classify' ? 'projectid' : 'none'), 0, 0, 0, 1, '', 'maxwidth300');
3242 } else {
3243 if (!empty($object->fk_project)) {
3244 $proj = new Project($db);
3245 $proj->fetch($object->fk_project);
3246 $morehtmlref .= $proj->getNomUrl(1);
3247 if ($proj->title) {
3248 $morehtmlref .= '<span class="opacitymedium"> - '.dol_escape_htmltag($proj->title).'</span>';
3249 }
3250 }
3251 }
3252 }
3253 $morehtmlref .= '</div>';
3254
3255 $object->totalpaid = $totalpaid; // To give a chance to dol_banner_tab to use already paid amount to show correct status
3256
3257 dol_banner_tab($object, 'ref', $linkback, 1, 'ref', 'ref', $morehtmlref);
3258
3259 // Call Hook tabContentViewSupplierInvoice
3260 $parameters = array();
3261 // Note that $action and $object may be modified by hook
3262 $reshook = $hookmanager->executeHooks('tabContentViewSupplierInvoice', $parameters, $object, $action);
3263 if (empty($reshook)) {
3264 print '<div class="fichecenter">';
3265 print '<div class="fichehalfleft">';
3266 print '<div class="underbanner clearboth"></div>';
3267
3268 print '<table class="border tableforfield centpercent">';
3269
3270 // Type
3271 print '<tr><td class="titlefield">'.$langs->trans('Type').'</td><td>';
3272 print '<span class="badgeneutral">';
3273 print $object->getLibType();
3274 print '</span>';
3275 if ($object->subtype > 0) {
3276 print ' '.$object->getSubtypeLabel('facture_fourn');
3277 }
3279 $facreplaced = new FactureFournisseur($db);
3280 $facreplaced->fetch($object->fk_facture_source);
3281 print ' <span class="opacitymediumbycolor paddingleft">'.$langs->transnoentities("ReplaceInvoice", $facreplaced->getNomUrl(1)).'</span>';
3282 }
3284 if ($object->fk_facture_source > 0) {
3285 $facusing = new FactureFournisseur($db);
3286 $facusing->fetch($object->fk_facture_source);
3287 print ' <span class="opacitymediumbycolor paddingleft">'.$langs->transnoentities("CorrectInvoice", $facusing->getNomUrl(1)).'</span>';
3288 } else {
3289 $langs->load("errors");
3290 print ' <span class="opacitymediumbycolor paddingleft">'.$langs->transnoentities("WarningCorrectedInvoiceNotFound").'</span>';
3291 }
3292 }
3293
3294 $facidavoir = $object->getListIdAvoirFromInvoice();
3295 if (count($facidavoir) > 0) {
3296 $invoicecredits = array();
3297 foreach ($facidavoir as $id) {
3298 $facavoir = new FactureFournisseur($db);
3299 $facavoir->fetch($id);
3300 $invoicecredits[] = $facavoir->getNomUrl(1);
3301 }
3302 print ' <span class="opacitymediumbycolor paddingleft">'.$langs->transnoentities("InvoiceHasAvoir") . (count($invoicecredits) ? ' ' : '') . implode(',', $invoicecredits);
3303 print '</span>';
3304 }
3305 if (isset($objectidnext) && $objectidnext > 0) {
3306 $facthatreplace = new FactureFournisseur($db);
3307
3308 $facthatreplace->fetch($objectidnext);
3309 print ' <span class="opacitymediumbycolor paddingleft">'.str_replace('{s1}', $facthatreplace->getNomUrl(1), $langs->transnoentities("ReplacedByInvoice", '{s1}')).'</span>';
3310 }
3312 $discount = new DiscountAbsolute($db);
3313 $result = $discount->fetch(0, 0, $object->id);
3314 if ($result > 0) {
3315 print ' <span class="opacitymediumbycolor paddingleft">';
3316 $s = $langs->trans("CreditNoteConvertedIntoDiscount", '{s1}', '{s2}');
3317 $s = str_replace('{s1}', $object->getLibType(1), $s);
3318 $s = str_replace('{s2}', $discount->getNomUrl(1, 'discount'), $s);
3319 print $s;
3320 print '</span><br>';
3321 }
3322 }
3323
3324 if ($object->fk_fac_rec_source > 0) {
3325 $tmptemplate = new FactureFournisseurRec($db);
3326 $result = $tmptemplate->fetch($object->fk_fac_rec_source);
3327 if ($result > 0) {
3328 print ' <span class="opacitymediumbycolor paddingleft">';
3329 $link = '<a href="'.DOL_URL_ROOT.'/fourn/facture/card-rec.php?facid='.$tmptemplate->id.'">'.dol_escape_htmltag($tmptemplate->title).'</a>';
3330 $s = $langs->transnoentities("GeneratedFromSupplierTemplate", $link);
3331
3332 print $s;
3333 print '</span>';
3334 }
3335 }
3336 print '</td></tr>';
3337
3338
3339 // Relative and absolute discounts
3340 print '<!-- Discounts -->'."\n";
3341 print '<tr><td>'.$langs->trans('DiscountStillRemaining');
3342 print '</td><td>';
3343
3344 $thirdparty = $societe;
3345 $discount_type = 1;
3346 include DOL_DOCUMENT_ROOT.'/core/tpl/object_discounts.tpl.php';
3347
3348 print '</td></tr>';
3349
3350 // Label
3351 print '<tr>';
3352 print '<td>'.$form->editfieldkey("Label", 'label', $object->label, $object, $usercancreate).'</td>';
3353 print '<td>'.$form->editfieldval("Label", 'label', $object->label, $object, $usercancreate).'</td>';
3354 print '</tr>';
3355
3356 //$form_permission = ($object->status < FactureFournisseur::STATUS_CLOSED) && $usercancreate && ($object->getSommePaiement() <= 0);
3357 $form_permission = ($object->status < FactureFournisseur::STATUS_CLOSED) && $usercancreate;
3358
3359 // Date
3360 print '<tr><td>';
3361 print $form->editfieldkey("DateInvoice", 'datef', $object->date, $object, $form_permission, 'datepicker');
3362 print '</td><td colspan="3">';
3363 print $form->editfieldval("Date", 'datef', $object->date, $object, $form_permission, 'datepicker');
3364 print '</td>';
3365
3366 // Default terms of the settlement
3367 $langs->load('bills');
3368 print '<tr><td class="nowrap">';
3369 print '<table class="nobordernopadding centpercent"><tr><td class="nowrap">';
3370 print $langs->trans('PaymentConditions');
3371 print '<td>';
3372 if ($action != 'editconditions' && $form_permission) {
3373 print '<td class="right"><a class="editfielda reposition" href="'.$_SERVER["PHP_SELF"].'?action=editconditions&token='.newToken().'&id='.$object->id.'">'.img_edit($langs->trans('SetConditions'), 1).'</a></td>';
3374 }
3375 print '</tr></table>';
3376 print '</td><td>';
3377 if ($action == 'editconditions') {
3378 $form->form_conditions_reglement($_SERVER['PHP_SELF'].'?id='.$object->id, $object->cond_reglement_id, 'cond_reglement_id');
3379 } else {
3380 $form->form_conditions_reglement($_SERVER['PHP_SELF'].'?id='.$object->id, $object->cond_reglement_id, 'none');
3381 }
3382 print "</td>";
3383 print '</tr>';
3384
3385 // Due date
3386 print '<tr><td>';
3387 print $form->editfieldkey("DateMaxPayment", 'date_lim_reglement', $object->date_echeance, $object, $form_permission, 'datepicker');
3388 print '</td><td>';
3389 print $form->editfieldval("DateMaxPayment", 'date_lim_reglement', $object->date_echeance, $object, $form_permission, 'datepicker');
3390 if ($action != 'editdate_lim_reglement' && $object->hasDelay()) {
3391 print img_warning($langs->trans('Late'));
3392 }
3393 print '</td>';
3394
3395 // Mode of payment
3396 $langs->load('bills');
3397 print '<tr><td class="nowrap">';
3398 print '<table class="nobordernopadding centpercent"><tr><td class="nowrap">';
3399 print $langs->trans('PaymentMode');
3400 print '</td>';
3401 if ($action != 'editmode' && $form_permission) {
3402 print '<td class="right"><a class="editfielda" href="'.$_SERVER["PHP_SELF"].'?action=editmode&token='.newToken().'&id='.$object->id.'">'.img_edit($langs->trans('SetMode'), 1).'</a></td>';
3403 }
3404 print '</tr></table>';
3405 print '</td><td>';
3406 if ($action == 'editmode') {
3407 $form->form_modes_reglement($_SERVER['PHP_SELF'].'?id='.$object->id, $object->mode_reglement_id, 'mode_reglement_id', 'DBIT', 1, 1);
3408 } else {
3409 $form->form_modes_reglement($_SERVER['PHP_SELF'].'?id='.$object->id, $object->mode_reglement_id, 'none');
3410 }
3411 print '</td></tr>';
3412
3413 // Multicurrency
3414 if (isModEnabled("multicurrency")) {
3415 // Multicurrency code
3416 print '<tr>';
3417 print '<td>';
3418 print '<table class="nobordernopadding" width="100%"><tr><td>';
3419 print $form->editfieldkey('Currency', 'multicurrency_code', '', $object, 0);
3420 print '</td>';
3421 if ($action != 'editmulticurrencycode' && $object->status == $object::STATUS_DRAFT) {
3422 print '<td class="right"><a class="editfielda" href="'.$_SERVER["PHP_SELF"].'?action=editmulticurrencycode&token='.newToken().'&id='.$object->id.'">'.img_edit($langs->transnoentitiesnoconv('SetMultiCurrencyCode'), 1).'</a></td>';
3423 }
3424 print '</tr></table>';
3425 print '</td><td>';
3426 if ($action == 'editmulticurrencycode') {
3427 $form->form_multicurrency_code($_SERVER['PHP_SELF'].'?id='.$object->id, $object->multicurrency_code, 'multicurrency_code');
3428 } else {
3429 $form->form_multicurrency_code($_SERVER['PHP_SELF'].'?id='.$object->id, $object->multicurrency_code, 'none');
3430 }
3431 print '</td></tr>';
3432
3433 // Multicurrency rate
3434 if ($object->multicurrency_code != $conf->currency || $object->multicurrency_tx != 1) {
3435 print '<tr>';
3436 print '<td>';
3437 print '<table class="nobordernopadding centpercent"><tr><td>';
3438 print $form->editfieldkey('CurrencyRate', 'multicurrency_tx', '', $object, 0);
3439 print '</td>';
3440 if ($action != 'editmulticurrencyrate' && $object->status == $object::STATUS_DRAFT && $object->multicurrency_code && $object->multicurrency_code != $conf->currency) {
3441 print '<td class="right"><a class="editfielda" href="'.$_SERVER["PHP_SELF"].'?action=editmulticurrencyrate&token='.newToken().'&id='.$object->id.'">'.img_edit($langs->transnoentitiesnoconv('SetMultiCurrencyCode'), 1).'</a></td>';
3442 }
3443 print '</tr></table>';
3444 print '</td><td>';
3445 if ($action == 'editmulticurrencyrate' || $action == 'actualizemulticurrencyrate') {
3446 if ($action == 'actualizemulticurrencyrate') {
3447 list($object->fk_multicurrency, $object->multicurrency_tx) = MultiCurrency::getIdAndTxFromCode($object->db, $object->multicurrency_code);
3448 }
3449 $form->form_multicurrency_rate($_SERVER['PHP_SELF'].'?id='.$object->id, $object->multicurrency_tx, 'multicurrency_tx', $object->multicurrency_code);
3450 } else {
3451 $form->form_multicurrency_rate($_SERVER['PHP_SELF'].'?id='.$object->id, $object->multicurrency_tx, 'none', $object->multicurrency_code);
3452 if ($object->status == $object::STATUS_DRAFT && $object->multicurrency_code && $object->multicurrency_code != $conf->currency) {
3453 print '<div class="inline-block"> &nbsp; &nbsp; &nbsp; &nbsp; ';
3454 print '<a href="'.$_SERVER["PHP_SELF"].'?id='.$object->id.'&action=actualizemulticurrencyrate">'.$langs->trans("ActualizeCurrency").'</a>';
3455 print '</div>';
3456 }
3457 }
3458 print '</td></tr>';
3459 }
3460 }
3461
3462 // Bank Account
3463 if (isModEnabled("bank")) {
3464 print '<tr><td class="nowrap">';
3465 print '<table width="100%" class="nobordernopadding"><tr><td class="nowrap">';
3466 print $langs->trans('BankAccount');
3467 print '<td>';
3468 if ($action != 'editbankaccount' && $usercancreate) {
3469 print '<td class="right"><a class="editfielda" href="'.$_SERVER["PHP_SELF"].'?action=editbankaccount&token='.newToken().'&id='.$object->id.'">'.img_edit($langs->trans('SetBankAccount'), 1).'</a></td>';
3470 }
3471 print '</tr></table>';
3472 print '</td><td>';
3473 if ($action == 'editbankaccount') {
3474 $form->formSelectAccount($_SERVER['PHP_SELF'].'?id='.$object->id, $object->fk_account, 'fk_account', 1);
3475 } else {
3476 $form->formSelectAccount($_SERVER['PHP_SELF'].'?id='.$object->id, $object->fk_account, 'none');
3477 }
3478 print "</td>";
3479 print '</tr>';
3480 }
3481
3482 // Vat reverse-charge by default
3483 if (getDolGlobalString('ACCOUNTING_FORCE_ENABLE_VAT_REVERSE_CHARGE')) {
3484 print '<tr><td class="nowrap">';
3485 print '<table width="100%" class="nobordernopadding"><tr><td class="nowrap">';
3486 print $langs->trans('VATReverseCharge');
3487 print '<td>';
3488 if ($action != 'editvatreversecharge' && $usercancreate) {
3489 print '<td class="right"><a class="editfielda" href="'.$_SERVER["PHP_SELF"].'?action=editvatreversecharge&amp;id='.$object->id.'">'.img_edit($langs->trans('SetVATReverseCharge'), 1).'</a></td>';
3490 }
3491 print '</tr></table>';
3492 print '</td><td>';
3493 if ($action == 'editvatreversecharge') {
3494 print '<form method="post" action="'.$_SERVER['PHP_SELF'].'?id='.$object->id.'">';
3495 print '<input type="hidden" name="action" value="setvatreversecharge">';
3496 print '<input type="hidden" name="token" value="'.newToken().'">';
3497
3498 print '<input type="checkbox" name="vat_reverse_charge"' . ($object->vat_reverse_charge == '1' ? ' checked ' : '') . '>';
3499
3500 print '<input type="submit" class="button valignmiddle" value="'.$langs->trans("Modify").'">';
3501 print '</form>';
3502 } else {
3503 print '<input type="checkbox" name="vat_reverse_charge"'. ($object->vat_reverse_charge == '1' ? ' checked ' : '') . ' disabled>';
3504 }
3505 print '</td></tr>';
3506 }
3507
3508 // Incoterms
3509 if (isModEnabled('incoterm')) {
3510 print '<tr><td>';
3511 print '<table width="100%" class="nobordernopadding"><tr><td>';
3512 print $langs->trans('IncotermLabel');
3513 print '<td><td class="right">';
3514 if ($usercancreate) {
3515 print '<a class="editfielda" href="'.DOL_URL_ROOT.'/fourn/facture/card.php?facid='.$object->id.'&action=editincoterm&token='.newToken().'">'.img_edit().'</a>';
3516 } else {
3517 print '&nbsp;';
3518 }
3519 print '</td></tr></table>';
3520 print '</td>';
3521 print '<td>';
3522 if ($action != 'editincoterm') {
3523 print $form->textwithpicto($object->display_incoterms(), $object->label_incoterms, 1);
3524 } else {
3525 print $form->select_incoterms((!empty($object->fk_incoterms) ? $object->fk_incoterms : ''), (!empty($object->location_incoterms) ? $object->location_incoterms : ''), $_SERVER['PHP_SELF'].'?id='.$object->id);
3526 }
3527 print '</td></tr>';
3528 }
3529
3530 // Intracomm report
3531 if (isModEnabled('intracommreport')) {
3532 $langs->loadLangs(array("intracommreport"));
3533 print '<!-- If module intracomm on -->'."\n";
3534 print '<tr><td>';
3535 print '<table class="nobordernopadding centpercent"><tr><td>';
3536 print $langs->trans('IntracommReportTransportMode');
3537 print '</td>';
3538 if ($action != 'edittransportmode' && ($user->hasRight("fournisseur", "facture", "creer") || $user->hasRight("supplier_invoice", "creer"))) {
3539 print '<td class="right"><a class="editfielda" href="'.$_SERVER["PHP_SELF"].'?action=edittransportmode&token='.newToken().'&id='.$object->id.'">'.img_edit().'</a></td>';
3540 }
3541 print '</tr></table>';
3542 print '</td>';
3543 print '<td>';
3544 if ($action == 'edittransportmode') {
3545 $form->formSelectTransportMode($_SERVER['PHP_SELF'].'?id='.$object->id, $object->transport_mode_id, 'transport_mode_id', 1, 1);
3546 } else {
3547 $form->formSelectTransportMode($_SERVER['PHP_SELF'].'?id='.$object->id, $object->transport_mode_id, 'none');
3548 }
3549 print '</td></tr>';
3550 }
3551
3552 // Other attributes
3553 $cols = 2;
3554 if ($object->status != $object::STATUS_DRAFT) {
3555 $disableedit = 1;
3556 $disableremove = 1;
3557 }
3558 include DOL_DOCUMENT_ROOT.'/core/tpl/extrafields_view.tpl.php';
3559
3560 print '</table>';
3561 print '</div>';
3562
3563 print '<div class="fichehalfright">';
3564 print '<div class="underbanner clearboth"></div>';
3565
3566 print '<table class="border tableforfield centpercent">';
3567
3568 print '<tr>';
3569 print '<td class="titlefieldmiddle">' . $langs->trans('AmountHT') . '</td>';
3570 print '<td class="nowrap amountcard right">' . price($object->total_ht, 0, $langs, 0, -1, -1, $conf->currency) . '</td>';
3571 if (isModEnabled("multicurrency") && ($object->multicurrency_code && $object->multicurrency_code != $conf->currency)) {
3572 print '<td class="nowrap amountcard right">' . price($object->multicurrency_total_ht, 0, $langs, 0, -1, -1, $object->multicurrency_code) . '</td>';
3573 }
3574 print '</tr>';
3575
3576 print '<tr>';
3577 print '<td>' . $langs->trans('AmountVAT') . '</td>';
3578 print '<td class="nowrap amountcard right">';
3579 if (GETPOST('calculationrule')) {
3580 $calculationrule = GETPOST('calculationrule', 'alpha');
3581 } else {
3582 $calculationrule = (!getDolGlobalString('MAIN_ROUNDOFTOTAL_NOT_TOTALOFROUND') ? 'totalofround' : 'roundoftotal');
3583 }
3584 if ($calculationrule == 'totalofround') {
3585 $calculationrulenum = 1;
3586 } else {
3587 $calculationrulenum = 2;
3588 }
3589 // Show link for "recalculate"
3590 if ($object->getVentilExportCompta() == 0) {
3591 $s = '<span class="hideonsmartphone opacitymedium">' . $langs->trans("ReCalculate") . ' </span>';
3592 $s .= '<a href="' . $_SERVER["PHP_SELF"] . '?id=' . $object->id . '&action=calculate&token='.newToken().'&calculationrule=totalofround">' . $langs->trans("Mode1") . '</a>';
3593 $s .= ' / ';
3594 $s .= '<a href="' . $_SERVER["PHP_SELF"] . '?id=' . $object->id . '&action=calculate&token='.newToken().'&calculationrule=roundoftotal">' . $langs->trans("Mode2") . '</a>';
3595 print '<div class="inline-block">';
3596 print $form->textwithtooltip($s, $langs->trans("CalculationRuleDesc", $calculationrulenum) . '<br>' . $langs->trans("CalculationRuleDescSupplier"), 2, 1, img_picto('', 'help'), '', 3, '', 0, 'recalculate');
3597 print '&nbsp; &nbsp; &nbsp; &nbsp;';
3598 print '</div>';
3599 }
3600 print price($object->total_tva, 1, $langs, 0, -1, -1, $conf->currency);
3601 print '</td>';
3602 if (isModEnabled("multicurrency") && ($object->multicurrency_code && $object->multicurrency_code != $conf->currency)) {
3603 print '<td class="nowrap amountcard right">' . price($object->multicurrency_total_tva, 0, $langs, 0, -1, -1, $object->multicurrency_code) . '</td>';
3604 }
3605 print '</tr>';
3606
3607 if ($societe->localtax1_assuj == "1") { //Localtax1
3608 print '<tr>';
3609 print '<td>' . $langs->transcountry("AmountLT1", $societe->country_code) . '</td>';
3610 print '<td class="nowrap amountcard right">' . price($object->total_localtax1, 1, $langs, 0, -1, -1, $conf->currency) . '</td>';
3611 print '</tr>';
3612 }
3613 if ($societe->localtax2_assuj == "1") { //Localtax2
3614 print '<tr>';
3615 print '<td>' . $langs->transcountry("AmountLT2", $societe->country_code) . '</td>';
3616 print '<td class="nowrap amountcard right">' . price($object->total_localtax2, 1, $langs, 0, -1, -1, $conf->currency) . '</td>';
3617 print '</tr>';
3618 }
3619
3620 print '<tr>';
3621 print '<td>' . $langs->trans('AmountTTC') . '</td>';
3622 print '<td class="nowrap amountcard right">' . price($object->total_ttc, 0, $langs, 0, -1, -1, $conf->currency) . '</td>';
3623 if (isModEnabled("multicurrency") && ($object->multicurrency_code && $object->multicurrency_code != $conf->currency)) {
3624 print '<td class="nowrap amountcard right">' . price($object->multicurrency_total_ttc, 0, $langs, 0, -1, -1, $object->multicurrency_code) . '</td>';
3625 }
3626 print '</tr>';
3627
3628 print '</table>';
3629
3630
3631 // List of payments
3632
3633 $totalpaid = 0;
3634
3635 $sign = 1;
3637 $sign = - 1;
3638 }
3639
3640 $nbrows = 9;
3641 $nbcols = 3;
3642 if (isModEnabled('project')) {
3643 $nbrows++;
3644 }
3645 if (isModEnabled("bank")) {
3646 $nbrows++;
3647 $nbcols++;
3648 }
3649 if (isModEnabled('incoterm')) {
3650 $nbrows++;
3651 }
3652 if (isModEnabled("multicurrency")) {
3653 $nbrows += 5;
3654 }
3655
3656 // Local taxes
3657 if ($societe->localtax1_assuj == "1") {
3658 $nbrows++;
3659 }
3660 if ($societe->localtax2_assuj == "1") {
3661 $nbrows++;
3662 }
3663
3664 $sql = 'SELECT p.datep as dp, p.ref, p.num_paiement as num_payment, p.rowid, p.fk_bank,';
3665 $sql .= ' c.id as payment_type, c.code as payment_code,';
3666 $sql .= ' pf.amount,';
3667 $sql .= ' ba.rowid as baid, ba.ref as baref, ba.label, ba.number as banumber, ba.account_number, ba.fk_accountancy_journal';
3668 $sql .= ' FROM '.MAIN_DB_PREFIX.'paiementfourn as p';
3669 $sql .= ' LEFT JOIN '.MAIN_DB_PREFIX.'bank as b ON p.fk_bank = b.rowid';
3670 $sql .= ' LEFT JOIN '.MAIN_DB_PREFIX.'bank_account as ba ON b.fk_account = ba.rowid';
3671 $sql .= ' LEFT JOIN '.MAIN_DB_PREFIX.'c_paiement as c ON p.fk_paiement = c.id';
3672 $sql .= ' LEFT JOIN '.MAIN_DB_PREFIX.'paiementfourn_facturefourn as pf ON pf.fk_paiementfourn = p.rowid';
3673 $sql .= ' WHERE pf.fk_facturefourn = '.((int) $object->id);
3674 $sql .= ' ORDER BY p.datep, p.tms';
3675
3676 $result = $db->query($sql);
3677 if ($result) {
3678 $num = $db->num_rows($result);
3679 $i = 0;
3680
3681 print '<div class="div-table-responsive-no-min">';
3682 print '<table class="noborder paymenttable centpercent">';
3683 print '<tr class="liste_titre">';
3684 print '<td class="liste_titre">'.($object->type == FactureFournisseur::TYPE_CREDIT_NOTE ? $langs->trans("PaymentsBack") : $langs->trans('Payments')).'</td>';
3685 print '<td>'.$langs->trans('Date').'</td>';
3686 print '<td>'.$langs->trans('Type').'</td>';
3687 if (isModEnabled("bank")) {
3688 print '<td class="right">'.$langs->trans('BankAccount').'</td>';
3689 }
3690 print '<td class="right">'.$langs->trans('Amount').'</td>';
3691 print '<td width="18">&nbsp;</td>';
3692 print '</tr>';
3693
3694 if ($num > 0) {
3695 while ($i < $num) {
3696 $objp = $db->fetch_object($result);
3697
3698 $paymentstatic->id = $objp->rowid;
3699 $paymentstatic->datepaye = $db->jdate($objp->dp);
3700 $paymentstatic->ref = ($objp->ref ? $objp->ref : $objp->rowid);
3701 $paymentstatic->num_payment = $objp->num_payment;
3702
3703 $paymentstatic->paiementcode = $objp->payment_code;
3704 $paymentstatic->type_code = $objp->payment_code;
3705 $paymentstatic->type_label = $objp->payment_type;
3706
3707 print '<tr class="oddeven">';
3708 print '<td class="nowraponall">';
3709 print $paymentstatic->getNomUrl(1);
3710 print '</td>';
3711 print '<td>'.dol_print_date($db->jdate($objp->dp), 'day').'</td>';
3712 $s = $form->form_modes_reglement('', $objp->payment_type, 'none', '', 1, 0, '', 1).' '.$objp->num_payment;
3713 print '<td class="tdoverflowmax125" title="'.dol_escape_htmltag($s).'">';
3714 print $s;
3715 print '</td>';
3716 if (isModEnabled("bank")) {
3717 $bankaccountstatic->id = $objp->baid;
3718 $bankaccountstatic->ref = $objp->baref;
3719 $bankaccountstatic->label = $objp->baref;
3720 $bankaccountstatic->number = $objp->banumber;
3721
3722 if (isModEnabled('accounting')) {
3723 $bankaccountstatic->account_number = $objp->account_number;
3724
3725 $accountingjournal = new AccountingJournal($db);
3726 $accountingjournal->fetch($objp->fk_accountancy_journal);
3727 $bankaccountstatic->accountancy_journal = $accountingjournal->getNomUrl(0, 1, 1, '', 1);
3728 }
3729
3730 print '<td class="right">';
3731 if ($objp->baid > 0) {
3732 print $bankaccountstatic->getNomUrl(1, 'transactions');
3733 }
3734 print '</td>';
3735 }
3736 print '<td class="right">'.price($sign * $objp->amount).'</td>';
3737 print '<td class="center">';
3738 if ($object->status == FactureFournisseur::STATUS_VALIDATED && $object->paid == 0 && $user->socid == 0) {
3739 print '<a href="'.$_SERVER["PHP_SELF"].'?id='.$object->id.'&action=deletepayment&token='.newToken().'&paiement_id='.$objp->rowid.'">';
3740 print img_delete();
3741 print '</a>';
3742 }
3743 print '</td>';
3744 print '</tr>';
3745 $totalpaid += $objp->amount;
3746 $i++;
3747 }
3748 } else {
3749 print '<tr class="oddeven"><td colspan="'.$nbcols.'"><span class="opacitymedium">'.$langs->trans("None").'</span></td><td></td><td></td></tr>';
3750 }
3751
3752 /*
3753 if ($object->paid == 0)
3754 {
3755 print '<tr><td colspan="'.$nbcols.'" class="right">'.$langs->trans('AlreadyPaid').' :</td><td class="right">'.price($totalpaid).'</td><td></td></tr>';
3756 print '<tr><td colspan="'.$nbcols.'" class="right">'.$langs->trans("Billed").' :</td><td class="right">'.price($object->total_ttc).'</td><td></td></tr>';
3757
3758 $resteapayer = $object->total_ttc - $totalpaid;
3759
3760 print '<tr><td colspan="'.$nbcols.'" class="right">'.$langs->trans('RemainderToPay').' :</td>';
3761 print '<td class="right'.($resteapayer?' amountremaintopay':'').'">'.price($resteapayer).'</td><td></td></tr>';
3762 }
3763 */
3764
3765 $db->free($result);
3766 } else {
3767 dol_print_error($db);
3768 }
3769
3771 // Total already paid
3772 print '<tr><td colspan="'.$nbcols.'" class="right">';
3773 print '<span class="opacitymedium">';
3775 print $langs->trans('AlreadyPaidNoCreditNotesNoDeposits');
3776 } else {
3777 print $langs->trans('AlreadyPaid');
3778 }
3779 print '</span>';
3780 print '</td><td class="right"'.(($totalpaid > 0) ? ' class="amountalreadypaid"' : '').'>'.price($totalpaid).'</td><td>&nbsp;</td></tr>';
3781
3782 //$resteapayer = $object->total_ttc - $totalpaid;
3783 $resteapayeraffiche = $resteapayer;
3784
3785 $cssforamountpaymentcomplete = 'amountpaymentcomplete';
3786
3787 // Loop on each credit note or deposit amount applied
3788 $creditnoteamount = 0;
3789 $depositamount = 0;
3790
3791 $sql = "SELECT re.rowid, re.amount_ht, re.amount_tva, re.amount_ttc,";
3792 $sql .= " re.description, re.fk_invoice_supplier_source";
3793 $sql .= " FROM ".MAIN_DB_PREFIX."societe_remise_except as re";
3794 $sql .= " WHERE fk_invoice_supplier = ".((int) $object->id);
3795 $resql = $db->query($sql);
3796 if ($resql) {
3797 $num = $db->num_rows($resql);
3798 $i = 0;
3799 $invoice = new FactureFournisseur($db);
3800 while ($i < $num) {
3801 $obj = $db->fetch_object($resql);
3802 $invoice->fetch($obj->fk_invoice_supplier_source);
3803 print '<tr><td colspan="'.$nbcols.'" class="right">';
3804 if ($invoice->type == FactureFournisseur::TYPE_CREDIT_NOTE) {
3805 print $langs->trans("CreditNote").' ';
3806 }
3807 if ($invoice->type == FactureFournisseur::TYPE_DEPOSIT) {
3808 print $langs->trans("Deposit").' ';
3809 }
3810 print $invoice->getNomUrl(0);
3811 print ' :</td>';
3812 print '<td class="right">'.price($obj->amount_ttc).'</td>';
3813 print '<td class="right">';
3814 print '<a href="'.$_SERVER["PHP_SELF"].'?facid='.$object->id.'&action=unlinkdiscount&discountid='.$obj->rowid.'">';
3815 print img_picto($langs->transnoentitiesnoconv("RemoveDiscount"), 'unlink');
3816 print '</a>';
3817 print '</td></tr>';
3818 $i++;
3819 if ($invoice->type == FactureFournisseur::TYPE_CREDIT_NOTE) {
3820 $creditnoteamount += $obj->amount_ttc;
3821 }
3822 if ($invoice->type == FactureFournisseur::TYPE_DEPOSIT) {
3823 $depositamount += $obj->amount_ttc;
3824 }
3825 }
3826 } else {
3827 dol_print_error($db);
3828 }
3829
3830 // Paye partiellement 'escompte'
3831 if (($object->status == FactureFournisseur::STATUS_CLOSED || $object->status == FactureFournisseur::STATUS_ABANDONED) && $object->close_code == 'discount_vat') {
3832 print '<tr><td colspan="'.$nbcols.'" class="right nowrap">';
3833 print '<span class="opacitymedium">';
3834 print $form->textwithpicto($langs->trans("Discount"), $langs->trans("HelpEscompte"), - 1);
3835 print '</span>';
3836 print '</td><td class="right">'.price($object->total_ttc - $creditnoteamount - $depositamount - $totalpaid).'</td><td>&nbsp;</td></tr>';
3837 $resteapayeraffiche = 0;
3838 $cssforamountpaymentcomplete = 'amountpaymentneutral';
3839 }
3840 // Paye partiellement ou Abandon 'badsupplier'
3841 if (($object->status == FactureFournisseur::STATUS_CLOSED || $object->status == FactureFournisseur::STATUS_ABANDONED) && $object->close_code == 'badsupplier') {
3842 print '<tr><td colspan="'.$nbcols.'" class="right nowrap">';
3843 print '<span class="opacitymedium">';
3844 print $form->textwithpicto($langs->trans("Abandoned"), $langs->trans("HelpAbandonBadCustomer"), - 1);
3845 print '</span>';
3846 print '</td><td class="right">'.price($object->total_ttc - $creditnoteamount - $depositamount - $totalpaid).'</td><td>&nbsp;</td></tr>';
3847 // $resteapayeraffiche=0;
3848 $cssforamountpaymentcomplete = 'amountpaymentneutral';
3849 }
3850 // Paye partiellement ou Abandon 'product_returned'
3851 if (($object->status == FactureFournisseur::STATUS_CLOSED || $object->status == FactureFournisseur::STATUS_ABANDONED) && $object->close_code == 'product_returned') {
3852 print '<tr><td colspan="'.$nbcols.'" class="right nowrap">';
3853 print '<span class="opacitymedium">';
3854 print $form->textwithpicto($langs->trans("ProductReturned"), $langs->trans("HelpAbandonProductReturned"), - 1);
3855 print '</span>';
3856 print '</td><td class="right">'.price($object->total_ttc - $creditnoteamount - $depositamount - $totalpaid).'</td><td>&nbsp;</td></tr>';
3857 $resteapayeraffiche = 0;
3858 $cssforamountpaymentcomplete = 'amountpaymentneutral';
3859 }
3860 // Paye partiellement ou Abandon 'abandon'
3861 if (($object->status == FactureFournisseur::STATUS_CLOSED || $object->status == FactureFournisseur::STATUS_ABANDONED) && $object->close_code == 'abandon') {
3862 print '<tr><td colspan="'.$nbcols.'" class="right nowrap">';
3863 $text = $langs->trans("HelpAbandonOther");
3864 if ($object->close_note) {
3865 $text .= '<br><br><b>'.$langs->trans("Reason").'</b>:'.$object->close_note;
3866 }
3867 print '<span class="opacitymedium">';
3868 // @phan-suppress-next-line PhanPluginSuspiciousParamPosition
3869 print $form->textwithpicto($langs->trans("Abandoned"), $text, - 1);
3870 print '</span>';
3871 print '</td><td class="right">'.price($object->total_ttc - $creditnoteamount - $depositamount - $totalpaid).'</td><td>&nbsp;</td></tr>';
3872 $resteapayeraffiche = 0;
3873 $cssforamountpaymentcomplete = 'amountpaymentneutral';
3874 }
3875
3876 // Billed
3877 print '<tr><td colspan="'.$nbcols.'" class="right">';
3878 print '<span class="opacitymedium">';
3879 print $langs->trans("Billed");
3880 print '</span>';
3881 print '</td><td class="right">'.price($object->total_ttc).'</td><td>&nbsp;</td></tr>';
3882
3883 // Remainder to pay
3884 print '<tr><td colspan="'.$nbcols.'" class="right">';
3885 print '<span class="opacitymedium">';
3886 print $langs->trans('RemainderToPay');
3887 if ($resteapayeraffiche < 0) {
3888 print ' ('.$langs->trans('NegativeIfExcessPaid').')';
3889 }
3890 print '</span>';
3891 print '</td>';
3892 print '<td class="right'.($resteapayeraffiche ? ' amountremaintopay' : (' '.$cssforamountpaymentcomplete)).'">'.price($resteapayeraffiche).'</td><td>&nbsp;</td></tr>';
3893
3894 // Remainder to pay Multicurrency
3895 if (isModEnabled('multicurrency') && $object->multicurrency_code != $conf->currency || $object->multicurrency_tx != 1) {
3896 print '<tr><td colspan="'.$nbcols.'" class="right">';
3897 print '<span class="opacitymedium">';
3898 print $langs->trans('RemainderToPayMulticurrency');
3899 if ($resteapayeraffiche < 0) {
3900 print ' ('.$langs->trans('NegativeIfExcessPaid').')';
3901 }
3902 print '</span>';
3903 print '</td>';
3904 print '<td class="right'.($resteapayeraffiche ? ' amountremaintopay' : (' '.$cssforamountpaymentcomplete)).'">'.(!empty($object->multicurrency_code) ? $object->multicurrency_code : $conf->currency).' '.price(price2num($multicurrency_resteapayer, 'MT')).'</td><td>&nbsp;</td></tr>';
3905 }
3906 } else { // Credit note
3907 $cssforamountpaymentcomplete = 'amountpaymentneutral';
3908
3909 // Total already paid back
3910 print '<tr><td colspan="'.$nbcols.'" class="right">';
3911 print $langs->trans('AlreadyPaidBack');
3912 print ' :</td><td class="right">'.price($sign * $totalpaid).'</td><td>&nbsp;</td></tr>';
3913
3914 // Billed
3915 print '<tr><td colspan="'.$nbcols.'" class="right">'.$langs->trans("Billed").' :</td><td class="right">'.price($sign * $object->total_ttc).'</td><td>&nbsp;</td></tr>';
3916
3917 // Remainder to pay back
3918 print '<tr><td colspan="'.$nbcols.'" class="right">';
3919 print '<span class="opacitymedium">';
3920 print $langs->trans('RemainderToPayBack');
3921 if ($resteapayeraffiche > 0) {
3922 print ' ('.$langs->trans('NegativeIfExcessRefunded').')';
3923 }
3924 print '</td>';
3925 print '</span>';
3926 print '<td class="right'.($resteapayeraffiche ? ' amountremaintopay' : (' '.$cssforamountpaymentcomplete)).'">'.price($sign * $resteapayeraffiche).'</td><td>&nbsp;</td></tr>';
3927
3928 // Remainder to pay back Multicurrency
3929 if (isModEnabled('multicurrency') && $object->multicurrency_code != $conf->currency || $object->multicurrency_tx != 1) {
3930 print '<tr><td colspan="'.$nbcols.'" class="right">';
3931 print '<span class="opacitymedium">';
3932 print $langs->trans('RemainderToPayBackMulticurrency');
3933 if ($resteapayeraffiche > 0) {
3934 print ' ('.$langs->trans('NegativeIfExcessRefunded').')';
3935 }
3936 print '</span>';
3937 print '</td>';
3938 print '<td class="right'.($resteapayeraffiche ? ' amountremaintopay' : (' '.$cssforamountpaymentcomplete)).'">'.(!empty($object->multicurrency_code) ? $object->multicurrency_code : $conf->currency).' '.price(price2num($sign * $object->multicurrency_tx * $resteapayeraffiche, 'MT')).'</td><td>&nbsp;</td></tr>';
3939 }
3940
3941 // Sold credit note
3942 // print '<tr><td colspan="'.$nbcols.'" class="right">'.$langs->trans('TotalTTC').' :</td>';
3943 // print '<td class="right" style="border: 1px solid;" bgcolor="#f0f0f0"><b>'.price($sign *
3944 // $object->total_ttc).'</b></td><td>&nbsp;</td></tr>';
3945 }
3946
3947 print '</table>';
3948 print '</div>';
3949
3950 print '</div>';
3951 print '</div>';
3952
3953 print '<div class="clearboth"></div><br>';
3954
3955 if (getDolGlobalString('MAIN_DISABLE_CONTACTS_TAB')) {
3956 $blocname = 'contacts';
3957 $title = $langs->trans('ContactsAddresses');
3958 include DOL_DOCUMENT_ROOT.'/core/tpl/bloc_showhide.tpl.php';
3959 }
3960
3961 if (getDolGlobalString('MAIN_DISABLE_NOTES_TAB')) {
3962 $colwidth = 20;
3963 $blocname = 'notes';
3964 $title = $langs->trans('Notes');
3965 include DOL_DOCUMENT_ROOT.'/core/tpl/bloc_showhide.tpl.php';
3966 }
3967
3968
3969 /*
3970 * Lines
3971 */
3972 print '<form name="addproduct" id="addproduct" action="'.$_SERVER["PHP_SELF"].'?id='.$object->id.'" method="POST">';
3973 print '<input type="hidden" name="token" value="'.newToken().'">';
3974 print '<input type="hidden" name="action" value="'.(($action != 'editline') ? 'addline' : 'updateline').'">';
3975 print '<input type="hidden" name="mode" value="">';
3976 print '<input type="hidden" name="page_y" value="">';
3977 print '<input type="hidden" name="id" value="'.$object->id.'">';
3978 print '<input type="hidden" name="socid" value="'.$societe->id.'">';
3979 print '<input type="hidden" name="backtopage" value="'.$backtopage.'">';
3980
3981 if (!empty($conf->use_javascript_ajax) && $object->status == FactureFournisseur::STATUS_DRAFT) {
3982 include DOL_DOCUMENT_ROOT.'/core/tpl/ajaxrow.tpl.php';
3983 }
3984
3985 print '<div class="div-table-responsive-no-min">';
3986 print '<table id="tablelines" class="noborder noshadow centpercent">';
3987
3988 global $forceall, $senderissupplier, $dateSelector, $inputalsopricewithtax;
3989 $forceall = 1;
3990 $dateSelector = 0;
3991 $inputalsopricewithtax = 1;
3992 $senderissupplier = 2; // $senderissupplier=2 is same than 1 but disable test on minimum qty and disable autofill qty with minimum.
3993 //if (!empty($conf->global->SUPPLIER_INVOICE_WITH_NOPRICEDEFINED)) $senderissupplier=2;
3994 if (getDolGlobalString('SUPPLIER_INVOICE_WITH_PREDEFINED_PRICES_ONLY')) {
3995 $senderissupplier = 1;
3996 }
3997
3998 // Show object lines (result may vary according to hidden option MAIN_NO_INPUT_PRICE_WITH_TAX)
3999 if (!empty($object->lines)) {
4000 $object->printObjectLines($action, $societe, $mysoc, $lineid, 1);
4001 }
4002
4003 $num = count($object->lines);
4004
4005 // Form to add new line
4006 if ($object->status == FactureFournisseur::STATUS_DRAFT && $usercancreate) {
4007 if ($action != 'editline') {
4008 // Add free products/services
4009
4010 $parameters = array();
4011 $reshook = $hookmanager->executeHooks('formAddObjectLine', $parameters, $object, $action); // Note that $action and $object may have been modified by hook
4012 if ($reshook < 0) {
4013 setEventMessages($hookmanager->error, $hookmanager->errors, 'errors');
4014 }
4015 if (empty($reshook)) {
4016 $object->formAddObjectLine(1, $societe, $mysoc);
4017 }
4018 }
4019 }
4020
4021 print '</table>';
4022 print '</div>';
4023 print '</form>';
4024 }
4025
4026 print dol_get_fiche_end();
4027
4028
4029 if ($action != 'presend') {
4030 /*
4031 * Buttons actions
4032 */
4033
4034 print '<div class="tabsAction">';
4035
4036 $parameters = array();
4037 $reshook = $hookmanager->executeHooks('addMoreActionsButtons', $parameters, $object, $action); // Note that $action and $object may have been
4038 // modified by hook
4039 if (empty($reshook)) {
4040 // Modify a validated invoice with no payments
4041 if ($object->status == FactureFournisseur::STATUS_VALIDATED && $action != 'confirm_edit' && $object->getSommePaiement() == 0 && $usercancreate) {
4042 // We check if lines of invoice are not already transferred into accountancy
4043 $ventilExportCompta = $object->getVentilExportCompta(); // Should be 0 since the sum of payments are zero. But we keep the protection.
4044
4045 if ($ventilExportCompta == 0) {
4046 print '<a class="butAction'.($conf->use_javascript_ajax ? ' reposition' : '').'" href="'.$_SERVER['PHP_SELF'].'?id='.$object->id.'&action=edit&token='.newToken().'">'.$langs->trans('Modify').'</a>';
4047 } else {
4048 print '<span class="butActionRefused classfortooltip" title="'.$langs->trans("DisabledBecauseDispatchedInBookkeeping").'">'.$langs->trans('Modify').'</span>';
4049 }
4050 }
4051
4052 $discount = new DiscountAbsolute($db);
4053 $result = $discount->fetch(0, 0, $object->id);
4054
4055 // Reopen a standard paid invoice
4057 || ($object->type == FactureFournisseur::TYPE_CREDIT_NOTE && empty($discount->id))
4058 || ($object->type == FactureFournisseur::TYPE_DEPOSIT && empty($discount->id)))
4059 && ($object->status == FactureFournisseur::STATUS_CLOSED || $object->status == FactureFournisseur::STATUS_ABANDONED)) { // A paid invoice (partially or completely)
4060 if (!$objectidnext && $object->close_code != 'replaced' && $usercancreate) { // Not replaced by another invoice
4061 print '<a class="butAction'.($conf->use_javascript_ajax ? ' reposition' : '').'" href="'.$_SERVER['PHP_SELF'].'?id='.$object->id.'&action=reopen&token='.newToken().'">'.$langs->trans('ReOpen').'</a>';
4062 } else {
4063 if ($usercancreate) {
4064 print '<span class="butActionRefused classfortooltip" title="'.$langs->trans("DisabledBecauseReplacedInvoice").'">'.$langs->trans('ReOpen').'</span>';
4065 } elseif (!getDolGlobalString('MAIN_BUTTON_HIDE_UNAUTHORIZED')) {
4066 print '<span class="butActionRefused classfortooltip">'.$langs->trans('ReOpen').'</span>';
4067 }
4068 }
4069 }
4070
4071 // Validate
4072 if ($action != 'confirm_edit' && $object->status == FactureFournisseur::STATUS_DRAFT) {
4073 if (count($object->lines)) {
4074 if ($usercanvalidate) {
4075 print '<a class="butAction" href="'.$_SERVER["PHP_SELF"].'?id='.$object->id.'&action=valid&token='.newToken().'"';
4076 print '>'.$langs->trans('Validate').'</a>';
4077 } else {
4078 print '<a class="butActionRefused classfortooltip" href="#" title="'.dol_escape_htmltag($langs->trans("NotAllowed")).'"';
4079 print '>'.$langs->trans('Validate').'</a>';
4080 }
4081 }
4082 }
4083
4084 // Send by mail
4085 if (empty($user->socid)) {
4087 if ($usercansend) {
4088 print '<a class="butAction" href="'.$_SERVER['PHP_SELF'].'?id='.$object->id.'&action=presend&mode=init#formmailbeforetitle">'.$langs->trans('SendMail').'</a>';
4089 } else {
4090 print '<span class="butActionRefused classfortooltip">'.$langs->trans('SendMail').'</span>';
4091 }
4092 }
4093 }
4094
4095 // Create payment
4097 print '<a class="butAction'.($conf->use_javascript_ajax ? ' reposition' : '').'" href="'.DOL_URL_ROOT.'/fourn/facture/paiement.php?facid='.$object->id.'&amp;action=create'.($object->fk_account > 0 ? '&amp;accountid='.$object->fk_account : '').'">'.$langs->trans('DoPayment').'</a>'; // must use facid because id is for payment id not invoice
4098 }
4099
4100 // Reverse back money or convert to reduction
4102 // For credit note only
4103 if ($object->type == FactureFournisseur::TYPE_CREDIT_NOTE && $object->status == 1 && $object->paid == 0) {
4104 if ($resteapayer == 0) {
4105 print '<span class="butActionRefused classfortooltip" title="'.$langs->trans("DisabledBecauseRemainderToPayIsZero").'">'.$langs->trans('DoPaymentBack').'</span>';
4106 } else {
4107 print '<a class="butAction" href="'.DOL_URL_ROOT.'/fourn/facture/paiement.php?facid='.$object->id.'&amp;action=create&amp;accountid='.$object->fk_account.'">'.$langs->trans('DoPaymentBack').'</a>';
4108 }
4109 }
4110
4111 // For standard invoice with excess paid
4112 if ($object->type == FactureFournisseur::TYPE_STANDARD && empty($object->paid) && ($object->total_ttc - $totalpaid - $totalcreditnotes - $totaldeposits) < 0 && $usercancreate && empty($discount->id)) {
4113 print '<a class="butAction'.($conf->use_javascript_ajax ? ' reposition' : '').'" href="'.$_SERVER["PHP_SELF"].'?facid='.$object->id.'&action=converttoreduc&token='.newToken().'">'.$langs->trans('ConvertExcessPaidToReduc').'</a>';
4114 }
4115 // For credit note
4116 if ($object->type == FactureFournisseur::TYPE_CREDIT_NOTE && $object->status == 1 && $object->paid == 0 && $usercancreate
4117 && (getDolGlobalString('SUPPLIER_INVOICE_ALLOW_REUSE_OF_CREDIT_WHEN_PARTIALLY_REFUNDED') || $object->getSommePaiement() == 0)
4118 ) {
4119 print '<a class="butAction'.($conf->use_javascript_ajax ? ' reposition' : '').'" href="'.$_SERVER["PHP_SELF"].'?facid='.$object->id.'&action=converttoreduc&token='.newToken().'" title="'.dol_escape_htmltag($langs->trans("ConfirmConvertToReducSupplier2")).'">'.$langs->trans('ConvertToReduc').'</a>';
4120 }
4121 // For deposit invoice
4122 if ($object->type == FactureFournisseur::TYPE_DEPOSIT && $usercancreate && $object->status > 0 && empty($discount->id)) {
4123 print '<a class="butAction'.($conf->use_javascript_ajax ? ' reposition' : '').'" href="'.$_SERVER["PHP_SELF"].'?facid='.$object->id.'&action=converttoreduc&token='.newToken().'">'.$langs->trans('ConvertToReduc').'</a>';
4124 }
4125 }
4126
4127 // Classify paid
4128 if ($object->status == FactureFournisseur::STATUS_VALIDATED && $object->paid == 0 && (
4129 ($object->type != FactureFournisseur::TYPE_CREDIT_NOTE && $object->type != FactureFournisseur::TYPE_DEPOSIT && ($resteapayer <= 0 || (getDolGlobalString('SUPPLIER_INVOICE_CAN_SET_PAID_EVEN_IF_PARTIALLY_PAID') && $object->total_ttc == $resteapayer))) ||
4130 ($object->type == FactureFournisseur::TYPE_CREDIT_NOTE && $resteapayer >= 0) ||
4131 ($object->type == FactureFournisseur::TYPE_DEPOSIT && $object->total_ttc > 0 && ($resteapayer == 0 || (getDolGlobalString('SUPPLIER_INVOICE_CAN_SET_PAID_EVEN_IF_PARTIALLY_PAID') && $object->total_ttc == $resteapayer)))
4132 )
4133 ) {
4134 print '<a class="butAction'.($conf->use_javascript_ajax ? ' reposition' : '').'" href="'.$_SERVER["PHP_SELF"].'?id='.$object->id.'&action=paid&token='.newToken().'">'.$langs->trans('ClassifyPaid').'</a>';
4135 }
4136
4137 // Classify 'closed not completely paid' (possible if validated and not yet filed paid)
4138 if ($object->status == FactureFournisseur::STATUS_VALIDATED && $object->paid == 0 && $resteapayer > 0 && (!getDolGlobalString('SUPPLIER_INVOICE_CAN_SET_PAID_EVEN_IF_PARTIALLY_PAID') || $object->total_ttc != $resteapayer)) {
4139 if ($totalpaid > 0 || $totalcreditnotes > 0) {
4140 // If one payment or one credit note was linked to this invoice
4141 print '<a class="butAction'.($conf->use_javascript_ajax ? ' reposition' : '').'" href="'.$_SERVER['PHP_SELF'].'?id='.$object->id.'&action=paid&token='.newToken().'">'.$langs->trans('ClassifyPaidPartially').'</a>';
4142 } else {
4143 if (!getDolGlobalString('INVOICE_CAN_NEVER_BE_CANCELED')) {
4144 print '<a class="butAction'.($conf->use_javascript_ajax ? ' reposition' : '').'" href="'.$_SERVER['PHP_SELF'].'?id='.$object->id.'&action=canceled">'.$langs->trans('ClassifyCanceled').'</a>';
4145 }
4146 }
4147 }
4148
4149 // Create event
4150 /*if (isModEnabled('agenda') && getDolGlobalString('MAIN_ADD_EVENT_ON_ELEMENT_CARD')) // Add hidden condition because this is not a "workflow" action so should appears somewhere else on page.
4151 {
4152 print '<div class="inline-block divButAction"><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></div>';
4153 }*/
4154
4155 // Create a credit note
4156 if (($object->type == FactureFournisseur::TYPE_STANDARD || $object->type == FactureFournisseur::TYPE_DEPOSIT) && $object->status > 0 && $usercancreate) {
4157 if (!$objectidnext) {
4158 print '<a class="butAction" href="'.$_SERVER['PHP_SELF'].'?socid='.$object->socid.'&amp;fac_avoir='.$object->id.'&amp;action=create&amp;type=2'.($object->fk_project > 0 ? '&amp;projectid='.$object->fk_project : '').'">'.$langs->trans("CreateCreditNote").'</a>';
4159 }
4160 }
4161
4162 // Clone
4163 if ($action != 'edit' && $usercancreate) {
4164 print '<a class="butAction" href="'.$_SERVER["PHP_SELF"].'?id='.$object->id.'&action=clone&socid='.$object->socid.'&token='.newToken().'">'.$langs->trans('ToClone').'</a>';
4165 }
4166
4167 // Clone as predefined / Create template
4168 if (($object->type == FactureFournisseur::TYPE_STANDARD || $object->type == FactureFournisseur::TYPE_DEPOSIT) && $object->status == 0 && $usercancreate) {
4169 if (!$objectidnext && count($object->lines) > 0) {
4170 print '<a class="butAction" href="'.DOL_URL_ROOT.'/fourn/facture/card-rec.php?facid='.$object->id.'&action=create">'.$langs->trans("ChangeIntoRepeatableInvoice").'</a>';
4171 }
4172 }
4173
4174 // Delete
4175 $isErasable = $object->is_erasable();
4176 if ($action != 'confirm_edit' && ($usercandelete || ($usercancreate && $isErasable == 1))) { // isErasable = 1 means draft with temporary ref (draft can always be deleted with no need of permissions)
4177 $enableDelete = false;
4178 $htmltooltip = '';
4179 $params = (empty($conf->use_javascript_ajax) ? array() : array('attr' => array('class' => 'reposition')));
4180 //var_dump($isErasable); var_dump($params);
4181 if ($isErasable == -4) {
4182 $htmltooltip = $langs->trans("DisabledBecausePayments");
4183 } elseif ($isErasable == -3) { // Should never happen with supplier invoice
4184 $htmltooltip = $langs->trans("DisabledBecauseNotLastSituationInvoice");
4185 } elseif ($isErasable == -2) { // Should never happen with supplier invoice
4186 $htmltooltip = $langs->trans("DisabledBecauseNotLastInvoice");
4187 } elseif ($isErasable == -1) {
4188 $htmltooltip = $langs->trans("DisabledBecauseDispatchedInBookkeeping");
4189 } elseif ($isErasable <= 0) { // Any other cases
4190 $htmltooltip = $langs->trans("DisabledBecauseNotErasable");
4191 } else {
4192 $enableDelete = true;
4193 $htmltooltip = '';
4194 }
4195 print dolGetButtonAction($htmltooltip, $langs->trans("Delete"), 'delete', $_SERVER["PHP_SELF"].'?id='.$object->id.'&action=delete&token='.newToken(), $object->id, $enableDelete, $params);
4196 }
4197 print '</div>';
4198
4199 if ($action != 'confirm_edit') {
4200 print '<div class="fichecenter"><div class="fichehalfleft">';
4201
4202 /*
4203 * Generated documents
4204 */
4205 $ref = dol_sanitizeFileName($object->ref);
4206 $subdir = get_exdir($object->id, 2, 0, 0, $object, 'invoice_supplier').$ref;
4207 $filedir = $conf->fournisseur->facture->dir_output.'/'.$subdir;
4208 $urlsource = $_SERVER['PHP_SELF'].'?id='.$object->id;
4209 $genallowed = $usercanread;
4210 $delallowed = $usercancreate;
4211 $modelpdf = (!empty($object->model_pdf) ? $object->model_pdf : (!getDolGlobalString('INVOICE_SUPPLIER_ADDON_PDF') ? '' : $conf->global->INVOICE_SUPPLIER_ADDON_PDF));
4212
4213 print $formfile->showdocuments('facture_fournisseur', $subdir, $filedir, $urlsource, $genallowed, $delallowed, $modelpdf, 1, 0, 0, 40, 0, '', '', '', $societe->default_lang);
4214 $somethingshown = $formfile->numoffiles;
4215
4216 // Show links to link elements
4217 $linktoelem = $form->showLinkToObjectBlock($object, array(), array('invoice_supplier'));
4218 $somethingshown = $form->showLinkedObjectBlock($object, $linktoelem);
4219
4220 print '</div><div class="fichehalfright">';
4221
4222 // List of actions on element
4223 include_once DOL_DOCUMENT_ROOT.'/core/class/html.formactions.class.php';
4224 $formactions = new FormActions($db);
4225 $somethingshown = $formactions->showactions($object, 'invoice_supplier', $socid, 1, 'listaction'.($genallowed ? 'largetitle' : ''));
4226
4227 print '</div></div>';
4228 }
4229 }
4230 }
4231
4232 // Select mail models is same action as presend
4233 if (GETPOST('modelselected')) {
4234 $action = 'presend';
4235 }
4236
4237 // Presend form
4238 $modelmail = 'invoice_supplier_send';
4239 $defaulttopic = 'SendBillRef';
4240 $diroutput = $conf->fournisseur->facture->dir_output;
4241 $autocopy = 'MAIN_MAIL_AUTOCOPY_SUPPLIER_INVOICE_TO';
4242 $trackid = 'sinv'.$object->id;
4243
4244 include DOL_DOCUMENT_ROOT.'/core/tpl/card_presend.tpl.php';
4245 }
4246}
4247
4248
4249// End of page
4250llxFooter();
4251$db->close();
if( $user->socid > 0) if(! $user->hasRight('accounting', 'chartofaccount')) $object
Definition card.php:58
if(!defined('NOREQUIRESOC')) if(!defined( 'NOREQUIRETRAN')) if(!defined('NOTOKENRENEWAL')) if(!defined( 'NOREQUIREMENU')) if(!defined('NOREQUIREHTML')) if(!defined( 'NOREQUIREAJAX')) llxHeader()
Empty header.
Definition wrapper.php:55
llxFooter()
Empty footer.
Definition wrapper.php:69
Class to manage bank accounts.
Class to manage accounting journals.
const TYPE_SITUATION
Situation invoice.
Class to manage absolute discounts.
Class to manage a WYSIWYG editor.
Class to manage warehouses.
Class to manage standard extra fields.
Class to manage suppliers invoices.
const TYPE_DEPOSIT
Deposit invoice.
const TYPE_CREDIT_NOTE
Credit note invoice.
const TYPE_REPLACEMENT
Replacement invoice.
const STATUS_VALIDATED
Validated (need to be paid)
const TYPE_STANDARD
Standard invoice.
const STATUS_ABANDONED
Classified abandoned and no payment done.
const STATUS_CLOSED
Classified paid.
Class to manage invoice templates.
Class to manage building of HTML components.
Class to offer components to list and upload files.
Class to manage generation of HTML components Only common components must be here.
Class with static methods for building HTML components related to products Only components common to ...
Class to manage building of HTML components.
static getIdAndTxFromCode($dbs, $code, $date_document='')
Get id and rate of currency from code.
Class to manage payments for supplier invoices.
Class ProductCombination Used to represent the relation between a product and one of its variants.
Class to manage predefined suppliers products.
Class to manage products or services.
Class to manage projects.
Class to manage third parties objects (customers, suppliers, prospects...)
Class to manage translations.
isInEEC($object)
Return if a country of an object is inside the EEC (European Economic Community)
dol_get_last_hour($date, $gm='tzserver')
Return GMT time for last hour of a given GMT date (it replaces hours, min and second part to 23:59:59...
Definition date.lib.php:641
dol_time_plus_duree($time, $duration_value, $duration_unit, $ruleforendofmonth=0)
Add a delay to a date.
Definition date.lib.php:125
print $script_file $mode $langs defaultlang(is_numeric($duration_value) ? " delay=". $duration_value :"").(is_numeric($duration_value2) ? " after cd cd cd description as description
Only used if Module[ID]Desc translation string is not found.
facturefourn_prepare_head(FactureFournisseur $object)
Prepare array with list of tabs.
Definition fourn.lib.php:36
dol_mktime($hour, $minute, $second, $month, $day, $year, $gm='auto', $check=1)
Return a timestamp date built from detailed information (by default a local PHP server timestamp) Rep...
load_fiche_titre($title, $morehtmlright='', $picto='generic', $pictoisfullpath=0, $id='', $morecssontable='', $morehtmlcenter='')
Load a title with picto.
img_warning($titlealt='default', $moreatt='', $morecss='pictowarning')
Show warning logo.
img_delete($titlealt='default', $other='class="pictodelete"', $morecss='')
Show delete logo.
img_picto($titlealt, $picto, $moreatt='', $pictoisfullpath=0, $srconly=0, $notitle=0, $alt='', $morecss='', $marginleftonlyshort=2)
Show picto whatever it's its name (generic function)
GETPOSTINT($paramname, $method=0)
Return the value of a $_GET or $_POST supervariable, converted into integer.
dol_get_fiche_head($links=array(), $active='', $title='', $notab=0, $picto='', $pictoisfullpath=0, $morehtmlright='', $morecss='', $limittoshow=0, $moretabssuffix='', $dragdropfile=0)
Show tabs of a record.
price2num($amount, $rounding='', $option=0)
Function that return a number with universal decimal format (decimal separator is '.
dol_get_fiche_end($notab=0)
Return tab footer of a card.
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.
dol_now($mode='auto')
Return date for now.
getDolGlobalInt($key, $default=0)
Return a Dolibarr global constant int value.
dol_print_date($time, $format='', $tzoutput='auto', $outputlangs=null, $encodetooutput=false)
Output date in a string format according to outputlangs (or langs if not defined).
newToken()
Return the value of token currently saved into session with name 'newtoken'.
dol_clone($object, $native=0)
Create a clone of instance of object (new instance with same value for each properties) With native =...
dolGetButtonAction($label, $text='', $actionType='default', $url='', $id='', $userRight=1, $params=array())
Function dolGetButtonAction.
get_default_npr(Societe $thirdparty_seller, Societe $thirdparty_buyer, $idprod=0, $idprodfournprice=0)
Function that returns whether VAT must be recoverable collected VAT (e.g.: VAT NPR in France)
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...
dol_htmloutput_events($disabledoutputofmessages=0)
Print formatted messages to output (Used to show messages on html output).
GETPOST($paramname, $check='alphanohtml', $method=0, $filter=null, $options=null, $noreplace=0)
Return value of a param into GET or POST supervariable.
setEventMessages($mesg, $mesgs, $style='mesgs', $messagekey='', $noduplicate=0)
Set event messages in dol_events session object.
dol_sanitizeFileName($str, $newstr='_', $unaccent=1)
Clean a string to use it as a file name.
dol_print_error($db=null, $error='', $errors=null)
Displays error message system with all the information to facilitate the diagnosis and the escalation...
getDolGlobalString($key, $default='')
Return dolibarr global constant string value.
info_admin($text, $infoonimgalt=0, $nodiv=0, $admin='1', $morecss='hideonsmartphone', $textfordropdown='', $picto='')
Show information in HTML for admin users or standard users.
img_edit($titlealt='default', $float=0, $other='')
Show logo edit/modify fiche.
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...
get_localtax($vatrate, $local, $thirdparty_buyer=null, $thirdparty_seller=null, $vatnpr=0)
Return localtax rate for a particular vat, when selling a product with vat $vatrate,...
get_exdir($num, $level, $alpha, $withoutslash, $object, $modulepart='')
Return a path to have a the directory according to object where files are stored.
getEntity($element, $shared=1, $currentobject=null)
Get list of entity id to use.
dol_escape_htmltag($stringtoescape, $keepb=0, $keepn=0, $noescapetags='', $escapeonlyhtmltags=0, $cleanalsojavascript=0)
Returns text escaped for inclusion in HTML alt or title or value tags, or into values of HTML input f...
restrictedArea(User $user, $features, $object=0, $tableandshare='', $feature2='', $dbt_keyfield='fk_soc', $dbt_select='rowid', $isdraft=0, $mode=0)
Check permissions of a user to show a page and an object.