dolibarr 19.0.4
card-rec.php
Go to the documentation of this file.
1<?php
2/* Copyright (C) 2002-2003 Rodolphe Quiedeville <rodolphe@quiedeville.org>
3 * Copyright (C) 2004-2023 Laurent Destailleur <eldy@users.sourceforge.net>
4 * Copyright (C) 2005-2012 Regis Houssin <regis.houssin@inodbox.com>
5 * Copyright (C) 2013 Florian Henry <florian.henry@open-concept.pro>
6 * Copyright (C) 2013-2023 Juanjo Menent <jmenent@2byte.es>
7 * Copyright (C) 2015 Jean-François Ferry <jfefe@aternatik.fr>
8 * Copyright (C) 2012 Cedric Salvador <csalvador@gpcsolutions.fr>
9 * Copyright (C) 2015 Alexandre Spangaro <aspangaro@open-dsi.fr>
10 * Copyright (C) 2016 Meziane Sof <virtualsof@yahoo.fr>
11 * Copyright (C) 2017-2018 Frédéric France <frederic.france@netlogic.fr>
12 * Copyright (C) 2023 Nick Fragoulis
13 *
14 * This program is free software; you can redistribute it and/or modify
15 * it under the terms of the GNU General Public License as published by
16 * the Free Software Foundation; either version 3 of the License, or
17 * (at your option) any later version.
18 *
19 * This program is distributed in the hope that it will be useful,
20 * but WITHOUT ANY WARRANTY; without even the implied warranty of
21 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
22 * GNU General Public License for more details.
23 *
24 * You should have received a copy of the GNU General Public License
25 * along with this program. If not, see <https://www.gnu.org/licenses/>.
26 */
27
34// Load Dolibarr environment
35require '../../main.inc.php';
36require_once DOL_DOCUMENT_ROOT.'/compta/facture/class/facture-rec.class.php';
37require_once DOL_DOCUMENT_ROOT.'/product/class/product.class.php';
38require_once DOL_DOCUMENT_ROOT.'/core/class/html.formother.class.php';
39if (isModEnabled('project')) {
40 include_once DOL_DOCUMENT_ROOT.'/projet/class/project.class.php';
41 //include_once DOL_DOCUMENT_ROOT . '/core/class/html.formprojet.class.php';
42}
43require_once DOL_DOCUMENT_ROOT.'/core/class/html.formprojet.class.php';
44require_once DOL_DOCUMENT_ROOT.'/core/class/doleditor.class.php';
45require_once DOL_DOCUMENT_ROOT.'/core/lib/invoice.lib.php';
46require_once DOL_DOCUMENT_ROOT.'/core/class/extrafields.class.php';
47
48// Load translation files required by the page
49$langs->loadLangs(array('bills', 'companies', 'compta', 'admin', 'other', 'products', 'banks'));
50
51$action = GETPOST('action', 'alpha');
52$massaction = GETPOST('massaction', 'alpha');
53$show_files = GETPOST('show_files', 'int');
54$confirm = GETPOST('confirm', 'alpha');
55$cancel = GETPOST('cancel', 'alpha');
56$toselect = GETPOST('toselect', 'array');
57$contextpage = GETPOST('contextpage', 'aZ') ? GETPOST('contextpage', 'aZ') : 'invoicetemplatelist'; // To manage different context of search
58
59// Security check
60$id = (GETPOST('facid', 'int') ? GETPOST('facid', 'int') : GETPOST('id', 'int'));
61$lineid = GETPOST('lineid', 'int');
62$ref = GETPOST('ref', 'alpha');
63if ($user->socid) {
64 $socid = $user->socid;
65}
66$objecttype = 'facture_rec';
67if ($action == "create" || $action == "add") {
68 $objecttype = '';
69}
70$projectid = GETPOST('projectid', 'int');
71
72$year_date_when = GETPOST('year_date_when');
73$month_date_when = GETPOST('month_date_when');
74$selectedLines = GETPOST('toselect', 'array');
75
76$limit = GETPOST('limit', 'int') ? GETPOST('limit', 'int') : $conf->liste_limit;
77$sortfield = GETPOST('sortfield', 'aZ09comma');
78$sortorder = GETPOST('sortorder', 'aZ09comma');
79$page = GETPOSTISSET('pageplusone') ? (GETPOST('pageplusone') - 1) : GETPOST("page", 'int');
80if (empty($page) || $page == -1) {
81 $page = 0;
82} // If $page is not defined, or '' or -1
83$offset = $limit * $page;
84if (!$sortorder) {
85 $sortorder = 'DESC';
86}
87if (!$sortfield) {
88 $sortfield = 'f.titre';
89}
90$pageprev = $page - 1;
91$pagenext = $page + 1;
92
93$object = new FactureRec($db);
94if (($id > 0 || $ref) && $action != 'create' && $action != 'add') {
95 $ret = $object->fetch($id, $ref);
96 if ($ret < 0) {
97 dol_print_error($db, $object->error, $object->errors);
98 exit;
99 } elseif (! $ret) {
100 setEventMessages($langs->trans("ErrorRecordNotFound"), null, 'errors');
101 }
102}
103
104// Initialize technical object to manage hooks of page. Note that conf->hooks_modules contains array of hook context
105$hookmanager->initHooks(array('invoicereccard', 'globalcard'));
106$extrafields = new ExtraFields($db);
107
108// fetch optionals attributes and labels
109$extrafields->fetch_name_optionals_label($object->table_element);
110
111$search_array_options = $extrafields->getOptionalsFromPost($object->table_element, '', 'search_');
112
113$permissionnote = $user->hasRight('facture', 'creer'); // Used by the include of actions_setnotes.inc.php
114$permissiondellink = $user->hasRight('facture', 'creer'); // Used by the include of actions_dellink.inc.php
115$permissiontoedit = $user->hasRight('facture', 'creer'); // Used by the include of actions_lineupdonw.inc.php
116
117$usercanread = $user->hasRight('facture', 'lire');
118$usercancreate = $user->hasRight('facture', 'creer');
119$usercanissuepayment = $user->hasRight('facture', 'paiement');
120$usercandelete = $user->hasRight('facture', 'supprimer');
121$usercanvalidate = ((!getDolGlobalString('MAIN_USE_ADVANCED_PERMS') && $usercancreate) || (getDolGlobalString('MAIN_USE_ADVANCED_PERMS') && !empty($user->rights->facture->invoice_advance->validate)));
122$usercansend = (!getDolGlobalString('MAIN_USE_ADVANCED_PERMS') || $user->rights->facture->invoice_advance->send);
123$usercanreopen = (!getDolGlobalString('MAIN_USE_ADVANCED_PERMS') || $user->rights->facture->invoice_advance->reopen);
124$usercanunvalidate = ((!getDolGlobalString('MAIN_USE_ADVANCED_PERMS') && !empty($usercancreate)) || (getDolGlobalString('MAIN_USE_ADVANCED_PERMS') && !empty($user->rights->facture->invoice_advance->unvalidate)));
125
126$usercanproductignorepricemin = ((getDolGlobalString('MAIN_USE_ADVANCED_PERMS') && empty($user->rights->produit->ignore_price_min_advance)) || !getDolGlobalString('MAIN_USE_ADVANCED_PERMS'));
127$usercancreatemargin = $user->hasRight("margins", "creer");
128$usercanreadallmargin = $user->hasRight("margins", "liretous");
129$usercancreatewithdrarequest = $user->hasRight("prelevement", "bons", "creer");
130
131$now = dol_now();
132
133$error = 0;
134
135$result = restrictedArea($user, 'facture', $object->id, $objecttype);
136
137
138/*
139 * Actions
140 */
141
142if (GETPOST('cancel', 'alpha')) {
143 $action = 'list';
144 $massaction = '';
145}
146if (!GETPOST('confirmmassaction', 'alpha') && $massaction != 'presend' && $massaction != 'confirm_presend') {
147 $massaction = '';
148}
149
150$parameters = array();
151$reshook = $hookmanager->executeHooks('doActions', $parameters, $object, $action); // Note that $action and $object may have been modified by some hooks
152if ($reshook < 0) {
153 setEventMessages($hookmanager->error, $hookmanager->errors, 'errors');
154}
155
156if (empty($reshook)) {
157 if (GETPOST('cancel', 'alpha')) {
158 $action = '';
159 }
160
161 // Selection of new fields
162 include DOL_DOCUMENT_ROOT.'/core/actions_changeselectedfields.inc.php';
163
164 // Set note
165 include DOL_DOCUMENT_ROOT.'/core/actions_setnotes.inc.php'; // Must be include, not include_once
166
167 include DOL_DOCUMENT_ROOT.'/core/actions_dellink.inc.php'; // Must be include, not include_once
168
169 include DOL_DOCUMENT_ROOT.'/core/actions_lineupdown.inc.php'; // Must be include, not include_once
170
171 // Mass actions
172 /*$objectclass='MyObject';
173 $objectlabel='MyObject';
174 $permissiontoread = $user->rights->mymodule->read;
175 $permissiontodelete = $user->rights->mymodule->delete;
176 $uploaddir = $conf->mymodule->dir_output;
177 include DOL_DOCUMENT_ROOT.'/core/actions_massactions.inc.php';*/
178
179 // Create predefined invoice
180 if ($action == 'add') {
181 if (!GETPOST('title', 'alphanohtml')) {
182 setEventMessages($langs->transnoentities("ErrorFieldRequired", $langs->trans("Title")), null, 'errors');
183 $action = "create";
184 $error++;
185 }
186
187 $frequency = GETPOST('frequency', 'int');
188 $reyear = GETPOST('reyear', 'int');
189 $remonth = GETPOST('remonth', 'int');
190 $reday = GETPOST('reday', 'int');
191 $rehour = GETPOST('rehour', 'int');
192 $remin = GETPOST('remin', 'int');
193 $nb_gen_max = GETPOST('nb_gen_max', 'int');
194 //if (empty($nb_gen_max)) $nb_gen_max =0;
195
196 if (GETPOST('frequency', 'int')) {
197 if (empty($reyear) || empty($remonth) || empty($reday)) {
198 setEventMessages($langs->transnoentities("ErrorFieldRequired", $langs->trans("Date")), null, 'errors');
199 $action = "create";
200 $error++;
201 }
202 /*if ($nb_gen_max === '') {
203 setEventMessages($langs->transnoentities("ErrorFieldRequired", $langs->trans("MaxPeriodNumber")), null, 'errors');
204 $action = "create";
205 $error++;
206 }*/
207 }
208
209 if (!$error) {
210 $object->subtype = GETPOST('subtype');
211 $object->title = GETPOST('title', 'alphanohtml');
212 $object->note_private = GETPOST('note_private', 'restricthtml');
213 $object->note_public = GETPOST('note_public', 'restricthtml');
214 $object->model_pdf = GETPOST('modelpdf', 'alphanohtml');
215 $object->usenewprice = GETPOST('usenewprice', 'alphanohtml');
216
217 $object->mode_reglement_id = GETPOST('mode_reglement_id', 'int');
218 $object->cond_reglement_id = GETPOST('cond_reglement_id', 'int');
219
220 $object->frequency = $frequency;
221 $object->unit_frequency = GETPOST('unit_frequency', 'alpha');
222 $object->nb_gen_max = $nb_gen_max;
223 $object->auto_validate = GETPOST('auto_validate', 'int');
224 $object->generate_pdf = GETPOST('generate_pdf', 'int');
225 $object->fk_project = $projectid;
226
227 $date_next_execution = dol_mktime($rehour, $remin, 0, $remonth, $reday, $reyear);
228 $object->date_when = $date_next_execution;
229
230 $ret = $extrafields->setOptionalsFromPost(null, $object);
231 if ($ret < 0) {
232 $error++;
233 }
234
235 // Get first contract linked to invoice used to generate template (facid is id of source invoice)
236 if (GETPOST('facid', 'int') > 0) {
237 $srcObject = new Facture($db);
238 $srcObject->fetch(GETPOST('facid', 'int'));
239
240 $srcObject->fetchObjectLinked();
241
242 if (!empty($srcObject->linkedObjectsIds['contrat'])) {
243 $contractidid = reset($srcObject->linkedObjectsIds['contrat']);
244
245 $object->origin = 'contrat';
246 $object->origin_id = $contractidid;
247 $object->linked_objects[$object->origin] = $object->origin_id;
248 }
249 }
250
251 $db->begin();
252
253 $oldinvoice = new Facture($db);
254 $oldinvoice->fetch(GETPOST('facid', 'int'));
255
256 $onlylines = GETPOST('toselect', 'array');
257
258 $result = $object->create($user, $oldinvoice->id, 0, $onlylines);
259 if ($result > 0) {
260 $result = $oldinvoice->delete($user, 1);
261 if ($result < 0) {
262 $error++;
263 setEventMessages($oldinvoice->error, $oldinvoice->errors, 'errors');
264 $action = "create";
265 }
266 } else {
267 $error++;
268 setEventMessages($object->error, $object->errors, 'errors');
269 $action = "create";
270 }
271
272 if (!$error) {
273 $db->commit();
274
275 header("Location: ".$_SERVER['PHP_SELF'].'?facid='.$object->id);
276 exit;
277 } else {
278 $db->rollback();
279
280 $action = "create";
281 }
282 }
283 }
284
285 // Delete
286 if ($action == 'confirm_delete' && $confirm == 'yes' && $user->hasRight('facture', 'supprimer')) {
287 $object->delete($user);
288
289 header("Location: ".DOL_URL_ROOT.'/compta/facture/invoicetemplate_list.php');
290 exit;
291 }
292
293
294 // Update field
295 if ($action == 'setconditions' && $user->hasRight('facture', 'creer')) {
296 // Set condition
297 $object->context['actionmsg'] = $langs->trans("FieldXModified", $langs->transnoentitiesnoconv("PaymentTerm"));
298 $result = $object->setPaymentTerms(GETPOST('cond_reglement_id', 'int'));
299 } elseif ($action == 'setmode' && $user->hasRight('facture', 'creer')) {
300 // Set mode
301 $object->context['actionmsg'] = $langs->trans("FieldXModified", $langs->transnoentitiesnoconv("PaymentMode"));
302 $result = $object->setPaymentMethods(GETPOST('mode_reglement_id', 'int'));
303 } elseif ($action == 'classin' && $user->hasRight('facture', 'creer')) {
304 // Set project
305 $object->context['actionmsg'] = $langs->trans("FieldXModified", $langs->transnoentitiesnoconv("Project"));
306 $object->setProject(GETPOST('projectid', 'int'));
307 } elseif ($action == 'setref' && $user->hasRight('facture', 'creer')) {
308 // Set bank account
309 $object->context['actionmsg'] = $langs->trans("FieldXModifiedFromYToZ", $langs->transnoentitiesnoconv("Title"), $object->title, $ref);
310 $result = $object->setValueFrom('titre', $ref, '', null, 'text', '', $user, 'BILLREC_MODIFY');
311 if ($result > 0) {
312 $object->title = $ref;
313 $object->ref = $object->title;
314 } else {
315 $error++;
316 if ($object->error == 'DB_ERROR_RECORD_ALREADY_EXISTS') {
317 $langs->load("errors");
318 setEventMessages($langs->trans('ErrorRefAlreadyExists', $ref), null, 'errors');
319 } else {
320 setEventMessages($object->error, $object->errors, 'errors');
321 }
322 }
323 } elseif ($action == 'setbankaccount' && $user->hasRight('facture', 'creer')) {
324 // Set bank account
325 $object->context['actionmsg'] = $langs->trans("FieldXModified", $langs->transnoentitiesnoconv("Bank"));
326 $result = $object->setBankAccount(GETPOST('fk_account', 'int'));
327 } elseif ($action == 'setfrequency' && $user->hasRight('facture', 'creer')) {
328 // Set frequency and unit frequency
329 $object->context['actionmsg'] = $langs->trans("FieldXModified", $langs->transnoentitiesnoconv("Frequency"));
330 $object->setFrequencyAndUnit(GETPOST('frequency', 'int'), GETPOST('unit_frequency', 'alpha'));
331 } elseif ($action == 'setdate_when' && $user->hasRight('facture', 'creer')) {
332 // Set next date of execution
333 $date = dol_mktime(GETPOST('date_whenhour'), GETPOST('date_whenmin'), 0, GETPOST('date_whenmonth'), GETPOST('date_whenday'), GETPOST('date_whenyear'));
334 if (!empty($date)) {
335 $object->setNextDate($date);
336 }
337 } elseif ($action == 'setnb_gen_max' && $user->hasRight('facture', 'creer')) {
338 // Set max period
339 $object->setMaxPeriod(GETPOST('nb_gen_max', 'int'));
340 } elseif ($action == 'setauto_validate' && $user->hasRight('facture', 'creer')) {
341 // Set auto validate
342 $object->setAutoValidate(GETPOST('auto_validate', 'int'));
343 } elseif ($action == 'setgenerate_pdf' && $user->hasRight('facture', 'creer')) {
344 // Set generate pdf
345 $object->setGeneratepdf(GETPOST('generate_pdf', 'int'));
346 } elseif ($action == 'setmodelpdf' && $user->hasRight('facture', 'creer')) {
347 // Set model pdf
348 $object->setModelpdf(GETPOST('modelpdf', 'alpha'));
349 } elseif ($action == 'disable' && $user->hasRight('facture', 'creer')) {
350 // Set status disabled
351 $db->begin();
352
353 $object->context['actionmsg'] = $langs->trans("RecordDisabled");
354
355 $res = $object->setValueFrom('suspended', 1, '', null, 'text', '', $user, 'BILLREC_MODIFY');
356 if ($res <= 0) {
357 $error++;
358 }
359
360 if (!$error) {
361 $db->commit();
362 } else {
363 $db->rollback();
364 setEventMessages($object->error, $object->errors, 'errors');
365 }
366 } elseif ($action == 'enable' && $user->hasRight('facture', 'creer')) {
367 // Set status enabled
368 $db->begin();
369
370 $object->context['actionmsg'] = $langs->trans("RecordEnabled");
371
372 $res = $object->setValueFrom('suspended', 0, '', null, 'text', '', $user, 'BILLREC_MODIFY');
373 if ($res <= 0) {
374 $error++;
375 }
376
377 if (!$error) {
378 $db->commit();
379 } else {
380 $db->rollback();
381 setEventMessages($object->error, $object->errors, 'errors');
382 }
383 } elseif ($action == 'setmulticurrencycode' && $usercancreate) {
384 // Multicurrency Code
385 $result = $object->setMulticurrencyCode(GETPOST('multicurrency_code', 'alpha'));
386 } elseif ($action == 'setmulticurrencyrate' && $usercancreate) {
387 // Multicurrency rate
388 $result = $object->setMulticurrencyRate(price2num(GETPOST('multicurrency_tx')), GETPOST('calculation_mode', 'int'));
389 }
390
391 // Delete line
392 if ($action == 'confirm_deleteline' && $confirm == 'yes' && $user->hasRight('facture', 'creer')) {
393 $object->fetch($id);
394 $object->fetch_thirdparty();
395
396 $db->begin();
397
398 $line = new FactureLigneRec($db);
399
400 // For triggers
401 $line->id = $lineid;
402
403 if ($line->delete($user) > 0) {
404 $result = $object->update_price(1);
405
406 if ($result > 0) {
407 $db->commit();
408 $object->fetch($object->id); // Reload lines
409 } else {
410 $db->rollback();
411 setEventMessages($db->lasterror(), null, 'errors');
412 }
413 } else {
414 $db->rollback();
415 setEventMessages($line->error, $line->errors, 'errors');
416 }
417 } elseif ($action == 'update_extras') {
418 $object->oldcopy = dol_clone($object, 2);
419
420 // Fill array 'array_options' with data from update form
421 $ret = $extrafields->setOptionalsFromPost(null, $object, GETPOST('attribute', 'restricthtml'));
422 if ($ret < 0) {
423 $error++;
424 }
425
426 if (!$error) {
427 $result = $object->insertExtraFields('BILLREC_MODIFY');
428 if ($result < 0) {
429 setEventMessages($object->error, $object->errors, 'errors');
430 $error++;
431 }
432 }
433 }
434
435 // Add a new line
436 if ($action == 'addline' && $user->hasRight('facture', 'creer')) {
437 $langs->load('errors');
438 $error = 0;
439
440 // Set if we used free entry or predefined product
441 $predef = '';
442 $product_desc = (GETPOSTISSET('dp_desc') ? GETPOST('dp_desc', 'restricthtml') : '');
443 $price_ht = price2num(GETPOST('price_ht'), 'MU', 2);
444 $price_ht_devise = price2num(GETPOST('multicurrency_price_ht'), 'CU', 2);
445 $prod_entry_mode = GETPOST('prod_entry_mode', 'alpha');
446 if ($prod_entry_mode == 'free') {
447 $idprod = 0;
448 } else {
449 $idprod = GETPOST('idprod', 'int');
450
451 if (getDolGlobalString('MAIN_DISABLE_FREE_LINES') && $idprod <= 0) {
452 setEventMessages($langs->trans("ErrorFieldRequired", $langs->transnoentitiesnoconv("ProductOrService")), null, 'errors');
453 $error++;
454 }
455 }
456
457 $tva_tx = (GETPOST('tva_tx', 'alpha') ? GETPOST('tva_tx', 'alpha') : 0);
458
459 $qty = price2num(GETPOST('qty'.$predef, 'alpha'), 'MS', 2);
460 $remise_percent = price2num(GETPOST('remise_percent'.$predef), '', 2);
461 if (empty($remise_percent)) {
462 $remise_percent = 0;
463 }
464
465 // Extrafields
466 $extralabelsline = $extrafields->fetch_name_optionals_label($object->table_element_line);
467 $array_options = $extrafields->getOptionalsFromPost($object->table_element_line, $predef);
468 // Unset extrafield
469 if (is_array($extralabelsline)) {
470 // Get extra fields
471 foreach ($extralabelsline as $key => $value) {
472 unset($_POST["options_".$key.$predef]);
473 }
474 }
475
476 if ((empty($idprod) || $idprod < 0) && ($price_ht < 0) && ($qty < 0)) {
477 setEventMessages($langs->trans('ErrorBothFieldCantBeNegative', $langs->transnoentitiesnoconv('UnitPriceHT'), $langs->transnoentitiesnoconv('Qty')), null, 'errors');
478 $error++;
479 }
480 if ($prod_entry_mode == 'free' && (empty($idprod) || $idprod < 0) && GETPOST('type') < 0) {
481 setEventMessages($langs->trans('ErrorFieldRequired', $langs->transnoentitiesnoconv('Type')), null, 'errors');
482 $error++;
483 }
484 if ($prod_entry_mode == 'free' && (empty($idprod) || $idprod < 0) && (!($price_ht >= 0) || $price_ht == '')) { // Unit price can be 0 but not ''
485 setEventMessages($langs->trans("ErrorFieldRequired", $langs->transnoentitiesnoconv("UnitPriceHT")), null, 'errors');
486 $error++;
487 }
488 if ($qty == '') {
489 setEventMessages($langs->trans('ErrorFieldRequired', $langs->transnoentitiesnoconv('Qty')), null, 'errors');
490 $error++;
491 }
492 if ($prod_entry_mode == 'free' && (empty($idprod) || $idprod < 0) && empty($product_desc)) {
493 setEventMessages($langs->trans('ErrorFieldRequired', $langs->transnoentitiesnoconv('Description')), null, 'errors');
494 $error++;
495 }
496 if ($qty < 0) {
497 $langs->load("errors");
498 setEventMessages($langs->trans('ErrorQtyForCustomerInvoiceCantBeNegative'), null, 'errors');
499 $error++;
500 }
501
502 if (!$error && ($qty >= 0) && (!empty($product_desc) || (!empty($idprod) && $idprod > 0))) {
503 $ret = $object->fetch($id);
504 if ($ret < 0) {
505 dol_print_error($db, $object->error);
506 exit();
507 }
508 $ret = $object->fetch_thirdparty();
509
510 // Clean parameters
511 $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'));
512 $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'));
513 $price_base_type = (GETPOST('price_base_type', 'alpha') ? GETPOST('price_base_type', 'alpha') : 'HT');
514 $tva_npr = "";
515
516 // Define special_code for special lines
517 $special_code = 0;
518 // if (!GETPOST('qty')) $special_code=3; // Options should not exists on invoices
519
520 // Ecrase $pu par celui du produit
521 // Ecrase $desc par celui du produit
522 // Ecrase $base_price_type par celui du produit
523 // Replaces $fk_unit with the product's
524 if (!empty($idprod) && $idprod > 0) {
525 $prod = new Product($db);
526 $prod->fetch($idprod);
527
528 $label = ((GETPOST('product_label') && GETPOST('product_label') != $prod->label) ? GETPOST('product_label') : '');
529
530 // Update if prices fields are defined
531 //$tva_tx = get_default_tva($mysoc, $object->thirdparty, $prod->id);
532 //$tva_npr = get_default_npr($mysoc, $object->thirdparty, $prod->id);
533 //if (empty($tva_tx)) {
534 // $tva_npr = 0;
535 //}
536
537 // Search the correct price into loaded array product_price_by_qty using id of array retrieved into POST['pqp'].
538 $pqp = (GETPOST('pbq', 'int') ? GETPOST('pbq', 'int') : 0);
539
540 $datapriceofproduct = $prod->getSellPrice($mysoc, $object->thirdparty, $pqp);
541
542 $pu_ht = $datapriceofproduct['pu_ht'];
543 $pu_ttc = $datapriceofproduct['pu_ttc'];
544 $price_min = $datapriceofproduct['price_min'];
545 $price_base_type = empty($datapriceofproduct['price_base_type']) ? 'HT' : $datapriceofproduct['price_base_type'];
546 //$tva_tx = $datapriceofproduct['tva_tx'];
547 //$tva_npr = $datapriceofproduct['tva_npr'];
548
549 $tmpvat = (float) price2num(preg_replace('/\s*\‍(.*\‍)/', '', $tva_tx));
550 $tmpprodvat = price2num(preg_replace('/\s*\‍(.*\‍)/', '', $prod->tva_tx));
551
552 // if price ht was forced (ie: from gui when calculated by margin rate and cost price). TODO Why this ?
553 if (!empty($price_ht)) {
554 $pu_ht = price2num($price_ht, 'MU');
555 $pu_ttc = price2num($pu_ht * (1 + ($tmpvat / 100)), 'MU');
556 } elseif ($tmpvat != $tmpprodvat) {
557 // On reevalue prix selon taux tva car taux tva transaction peut etre different
558 // de ceux du produit par defaut (par exemple si pays different entre vendeur et acheteur).
559 if ($price_base_type != 'HT') {
560 $pu_ht = price2num($pu_ttc / (1 + ($tmpvat / 100)), 'MU');
561 } else {
562 $pu_ttc = price2num($pu_ht * (1 + ($tmpvat / 100)), 'MU');
563 }
564 }
565
566 $desc = '';
567
568 // Define output language
569 if (getDolGlobalInt('MAIN_MULTILANGS') && getDolGlobalString('PRODUIT_TEXTS_IN_THIRDPARTY_LANGUAGE')) {
570 $outputlangs = $langs;
571 $newlang = '';
572 if (empty($newlang) && GETPOST('lang_id', 'aZ09')) {
573 $newlang = GETPOST('lang_id', 'aZ09');
574 }
575 if (empty($newlang)) {
576 $newlang = $object->thirdparty->default_lang;
577 }
578 if (!empty($newlang)) {
579 $outputlangs = new Translate("", $conf);
580 $outputlangs->setDefaultLang($newlang);
581 }
582
583 $desc = (!empty($prod->multilangs [$outputlangs->defaultlang] ["description"])) ? $prod->multilangs [$outputlangs->defaultlang] ["description"] : $prod->description;
584 } else {
585 $desc = $prod->description;
586 }
587
588 $desc = dol_concatdesc($desc, $product_desc);
589
590 // Add custom code and origin country into description
591 if (!getDolGlobalString('MAIN_PRODUCT_DISABLE_CUSTOMCOUNTRYCODE') && (!empty($prod->customcode) || !empty($prod->country_code))) {
592 $tmptxt = '(';
593 // Define output language
594 if (getDolGlobalInt('MAIN_MULTILANGS') && getDolGlobalString('PRODUIT_TEXTS_IN_THIRDPARTY_LANGUAGE')) {
595 $outputlangs = $langs;
596 $newlang = '';
597 if (empty($newlang) && GETPOST('lang_id', 'alpha')) {
598 $newlang = GETPOST('lang_id', 'alpha');
599 }
600 if (empty($newlang)) {
601 $newlang = $object->thirdparty->default_lang;
602 }
603 if (!empty($newlang)) {
604 $outputlangs = new Translate("", $conf);
605 $outputlangs->setDefaultLang($newlang);
606 $outputlangs->load('products');
607 }
608 if (!empty($prod->customcode)) {
609 $tmptxt .= $outputlangs->transnoentitiesnoconv("CustomCode").': '.$prod->customcode;
610 }
611 if (!empty($prod->customcode) && !empty($prod->country_code)) {
612 $tmptxt .= ' - ';
613 }
614 if (!empty($prod->country_code)) {
615 $tmptxt .= $outputlangs->transnoentitiesnoconv("CountryOrigin").': '.getCountry($prod->country_code, 0, $db, $outputlangs, 0);
616 }
617 } else {
618 if (!empty($prod->customcode)) {
619 $tmptxt .= $langs->transnoentitiesnoconv("CustomCode").': '.$prod->customcode;
620 }
621 if (!empty($prod->customcode) && !empty($prod->country_code)) {
622 $tmptxt .= ' - ';
623 }
624 if (!empty($prod->country_code)) {
625 $tmptxt .= $langs->transnoentitiesnoconv("CountryOrigin").': '.getCountry($prod->country_code, 0, $db, $langs, 0);
626 }
627 }
628 $tmptxt .= ')';
629 $desc = dol_concatdesc($desc, $tmptxt);
630 }
631
632 $type = $prod->type;
633 $fk_unit = $prod->fk_unit;
634 } else {
635 $pu_ht = price2num($price_ht, 'MU');
636 $pu_ttc = price2num(GETPOST('price_ttc'), 'MU');
637 $tva_npr = (preg_match('/\*/', $tva_tx) ? 1 : 0);
638 $tva_tx = str_replace('*', '', $tva_tx);
639 if (empty($tva_tx)) {
640 $tva_npr = 0;
641 }
642 $label = (GETPOST('product_label') ? GETPOST('product_label') : '');
643 $desc = $product_desc;
644 $type = GETPOST('type');
645 $fk_unit = GETPOST('units', 'alpha');
646 }
647
648 $date_start_fill = GETPOST('date_start_fill', 'int');
649 $date_end_fill = GETPOST('date_end_fill', 'int');
650
651 // Margin
652 $fournprice = price2num(GETPOST('fournprice'.$predef) ? GETPOST('fournprice'.$predef) : '');
653 $buyingprice = price2num(GETPOST('buying_price'.$predef) != '' ? GETPOST('buying_price'.$predef) : ''); // If buying_price is '0', we must keep this value
654
655 // Local Taxes
656 $localtax1_tx = get_localtax($tva_tx, 1, $object->thirdparty, $mysoc, $tva_npr);
657 $localtax2_tx = get_localtax($tva_tx, 2, $object->thirdparty, $mysoc, $tva_npr);
658
659 $info_bits = 0;
660 if ($tva_npr) {
661 $info_bits |= 0x01;
662 }
663
664 $fk_parent_line = GETPOST('fk_parent_line', 'int');
665
666 if ($usercanproductignorepricemin && (!empty($price_min) && (price2num($pu_ht) * (1 - price2num($remise_percent) / 100) < price2num($price_min)))) {
667 $mesg = $langs->trans("CantBeLessThanMinPrice", price(price2num($price_min, 'MU'), 0, $langs, 0, 0, - 1, $conf->currency));
668 setEventMessages($mesg, null, 'errors');
669 } else {
670 // Insert line
671 $result = $object->addline($desc, $pu_ht, $qty, $tva_tx, $localtax1_tx, $localtax2_tx, $idprod, $remise_percent, $price_base_type, $info_bits, '', $pu_ttc, $type, -1, $special_code, $label, $fk_unit, 0, $date_start_fill, $date_end_fill, $fournprice, $buyingprice, $fk_parent_line);
672
673 if ($result > 0) {
674 // Define output language and generate document
675 /*if (empty($conf->global->MAIN_DISABLE_PDF_AUTOUPDATE))
676 {
677 // Define output language
678 $outputlangs = $langs;
679 $newlang = '';
680 if (getDolGlobalInt('MAIN_MULTILANGS') && empty($newlang) && GETPOST('lang_id','aZ09')) $newlang = GETPOST('lang_id','aZ09');
681 if (getDolGlobalInt('MAIN_MULTILANGS') && empty($newlang)) $newlang = $object->thirdparty->default_lang;
682 if (!empty($newlang)) {
683 $outputlangs = new Translate("", $conf);
684 $outputlangs->setDefaultLang($newlang);
685 }
686 $model=$object->model_pdf;
687 $ret = $object->fetch($id); // Reload to get new records
688
689 $result = $object->generateDocument($model, $outputlangs, $hidedetails, $hidedesc, $hideref);
690 if ($result < 0) setEventMessages($object->error, $object->errors, 'errors');
691 }*/
692 $object->fetch($object->id); // Reload lines
693
694 unset($_POST['prod_entry_mode']);
695
696 unset($_POST['qty']);
697 unset($_POST['type']);
698 unset($_POST['remise_percent']);
699 unset($_POST['price_ht']);
700 unset($_POST['multicurrency_price_ht']);
701 unset($_POST['price_ttc']);
702 unset($_POST['tva_tx']);
703 unset($_POST['product_ref']);
704 unset($_POST['product_label']);
705 unset($_POST['product_desc']);
706 unset($_POST['fournprice']);
707 unset($_POST['buying_price']);
708 unset($_POST['np_marginRate']);
709 unset($_POST['np_markRate']);
710 unset($_POST['dp_desc']);
711 unset($_POST['idprod']);
712 unset($_POST['units']);
713
714 unset($_POST['date_starthour']);
715 unset($_POST['date_startmin']);
716 unset($_POST['date_startsec']);
717 unset($_POST['date_startday']);
718 unset($_POST['date_startmonth']);
719 unset($_POST['date_startyear']);
720 unset($_POST['date_endhour']);
721 unset($_POST['date_endmin']);
722 unset($_POST['date_endsec']);
723 unset($_POST['date_endday']);
724 unset($_POST['date_endmonth']);
725 unset($_POST['date_endyear']);
726
727 unset($_POST['date_start_fill']);
728 unset($_POST['date_end_fill']);
729
730 unset($_POST['situations']);
731 unset($_POST['progress']);
732 } else {
733 setEventMessages($object->error, $object->errors, 'errors');
734 }
735
736 $action = '';
737 }
738 }
739 } elseif ($action == 'updateline' && $usercancreate && !GETPOST('cancel', 'alpha')) {
740 if (!$object->fetch($id) > 0) {
741 dol_print_error($db);
742 }
743 $object->fetch_thirdparty();
744
745 // Clean parameters
746 $date_start = '';
747 $date_end = '';
748 //$date_start = dol_mktime(GETPOST('date_starthour'), GETPOST('date_startmin'), GETPOST('date_startsec'), GETPOST('date_startmonth'), GETPOST('date_startday'), GETPOST('date_startyear'));
749 //$date_end = dol_mktime(GETPOST('date_endhour'), GETPOST('date_endmin'), GETPOST('date_endsec'), GETPOST('date_endmonth'), GETPOST('date_endday'), GETPOST('date_endyear'));
750 $description = dol_htmlcleanlastbr(GETPOST('product_desc', 'restricthtml') ? GETPOST('product_desc', 'restricthtml') : GETPOST('desc', 'restricthtml'));
751 $pu_ht = price2num(GETPOST('price_ht'), '', 2);
752 $vat_rate = (GETPOST('tva_tx') ? GETPOST('tva_tx') : 0);
753 $qty = GETPOST('qty');
754 $pu_ht_devise = price2num(GETPOST('multicurrency_subprice'), '', 2);
755
756 // Define info_bits
757 $info_bits = 0;
758 if (preg_match('/\*/', $vat_rate)) {
759 $info_bits |= 0x01;
760 }
761
762 // Define vat_rate
763 $vat_rate = str_replace('*', '', $vat_rate);
764 $localtax1_rate = get_localtax($vat_rate, 1, $object->thirdparty);
765 $localtax2_rate = get_localtax($vat_rate, 2, $object->thirdparty);
766
767 // Add buying price
768 $fournprice = price2num(GETPOST('fournprice') ? GETPOST('fournprice') : '');
769 $buyingprice = price2num(GETPOST('buying_price') != '' ? GETPOST('buying_price') : ''); // If buying_price is '0', we muste keep this value
770
771 // Extrafields
772 $extralabelsline = $extrafields->fetch_name_optionals_label($object->table_element_line);
773 $array_options = $extrafields->getOptionalsFromPost($object->table_element_line);
774
775 $objectline = new FactureLigneRec($db);
776 if ($objectline->fetch(GETPOST('lineid', 'int'))) {
777 $objectline->array_options = $array_options;
778 $result = $objectline->insertExtraFields();
779 if ($result < 0) {
780 setEventMessages($langs->trans('Error').$result, null, 'errors');
781 }
782 }
783
784 $position = ($objectline->rang >= 0 ? $objectline->rang : 0);
785
786 // Unset extrafield
787 if (is_array($extralabelsline)) {
788 // Get extra fields
789 foreach ($extralabelsline as $key => $value) {
790 unset($_POST["options_".$key]);
791 }
792 }
793
794 // Define special_code for special lines
795 $special_code = GETPOST('special_code', 'int');
796 if ($special_code == 3) {
797 $special_code = 0; // Options should not exists on invoices
798 }
799
800 /*$line = new FactureLigne($db);
801 $line->fetch(GETPOST('lineid', 'int'));
802 $percent = $line->get_prev_progress($object->id);
803
804 if (GETPOST('progress') < $percent)
805 {
806 $mesg = '<div class="warning">' . $langs->trans("CantBeLessThanMinPercent") . '</div>';
807 setEventMessages($mesg, null, 'warnings');
808 $error++;
809 $result = -1;
810 }*/
811
812 $remise_percent = price2num(GETPOST('remise_percent'), '', 2);
813 if (empty($remise_percent)) {
814 $remise_percent = 0;
815 }
816
817 // Check minimum price
818 $productid = GETPOST('productid', 'int');
819 if (!empty($productid)) {
820 $product = new Product($db);
821 $product->fetch($productid);
822
823 $type = $product->type;
824
825 $price_min = $product->price_min;
826 if (getDolGlobalString('PRODUIT_MULTIPRICES') && !empty($object->thirdparty->price_level)) {
827 $price_min = $product->multiprices_min[$object->thirdparty->price_level];
828 }
829
830 $label = ((GETPOST('update_label') && GETPOST('product_label')) ? GETPOST('product_label') : '');
831
832 $typeinvoice = Facture::TYPE_STANDARD;
833
834 // Check price is not lower than minimum (check is done only for standard or replacement invoices)
835 if (((getDolGlobalString('MAIN_USE_ADVANCED_PERMS') && !$user->hasRight('produit', 'ignore_price_min_advance')) || !getDolGlobalString('MAIN_USE_ADVANCED_PERMS')) && (($typeinvoice == Facture::TYPE_STANDARD || $typeinvoice == Facture::TYPE_REPLACEMENT) && $price_min && ((float) price2num($pu_ht) * (1 - (float) $remise_percent / 100) < (float) price2num($price_min)))) {
836 setEventMessages($langs->trans("CantBeLessThanMinPrice", price(price2num($price_min, 'MU'), 0, $langs, 0, 0, - 1, $conf->currency)), null, 'errors');
837 $error++;
838 }
839 } else {
840 $type = GETPOST('type', 'int');
841 $label = (GETPOST('product_label') ? GETPOST('product_label') : '');
842
843 // Check parameters
844 if (GETPOST('type', 'int') < 0) {
845 setEventMessages($langs->trans("ErrorFieldRequired", $langs->transnoentitiesnoconv("Type")), null, 'errors');
846 $error++;
847 }
848 }
849 if ($qty < 0) {
850 $langs->load("errors");
851 setEventMessages($langs->trans('ErrorQtyForCustomerInvoiceCantBeNegative'), null, 'errors');
852 $error++;
853 }
854
855 $date_start_fill = GETPOST('date_start_fill', 'int');
856 $date_end_fill = GETPOST('date_end_fill', 'int');
857 $fk_parent_line = GETPOST('fk_parent_line', 'int');
858
859 // Update line
860 if (!$error) {
861 $result = $object->updateline(
862 GETPOST('lineid', 'int'),
863 $description,
864 $pu_ht,
865 $qty,
866 $vat_rate,
867 $localtax1_rate,
868 $localtax1_rate,
869 GETPOST('productid', 'int'),
870 $remise_percent,
871 'HT',
872 $info_bits,
873 0,
874 0,
875 $type,
876 $position,
877 $special_code,
878 $label,
879 GETPOST('units'),
880 $pu_ht_devise,
881 0,
882 $date_start_fill,
883 $date_end_fill,
884 $fournprice,
885 $buyingprice,
886 $fk_parent_line
887 );
888
889 if ($result >= 0) {
890 /*if (empty($conf->global->MAIN_DISABLE_PDF_AUTOUPDATE)) {
891 // Define output language
892 $outputlangs = $langs;
893 $newlang = '';
894 if (getDolGlobalInt('MAIN_MULTILANGS') && empty($newlang) && GETPOST('lang_id','aZ09'))
895 $newlang = GETPOST('lang_id','aZ09');
896 if (getDolGlobalInt('MAIN_MULTILANGS') && empty($newlang))
897 $newlang = $object->thirdparty->default_lang;
898 if (!empty($newlang)) {
899 $outputlangs = new Translate("", $conf);
900 $outputlangs->setDefaultLang($newlang);
901 }
902
903 $ret = $object->fetch($id); // Reload to get new records
904 $object->generateDocument($object->model_pdf, $outputlangs, $hidedetails, $hidedesc, $hideref);
905 }*/
906
907 $object->fetch($object->id); // Reload lines
908
909 unset($_POST['qty']);
910 unset($_POST['type']);
911 unset($_POST['productid']);
912 unset($_POST['remise_percent']);
913 unset($_POST['price_ht']);
914 unset($_POST['multicurrency_price_ht']);
915 unset($_POST['price_ttc']);
916 unset($_POST['tva_tx']);
917 unset($_POST['product_ref']);
918 unset($_POST['product_label']);
919 unset($_POST['product_desc']);
920 unset($_POST['fournprice']);
921 unset($_POST['buying_price']);
922 unset($_POST['np_marginRate']);
923 unset($_POST['np_markRate']);
924
925 unset($_POST['dp_desc']);
926 unset($_POST['idprod']);
927 unset($_POST['units']);
928
929 unset($_POST['date_starthour']);
930 unset($_POST['date_startmin']);
931 unset($_POST['date_startsec']);
932 unset($_POST['date_startday']);
933 unset($_POST['date_startmonth']);
934 unset($_POST['date_startyear']);
935 unset($_POST['date_endhour']);
936 unset($_POST['date_endmin']);
937 unset($_POST['date_endsec']);
938 unset($_POST['date_endday']);
939 unset($_POST['date_endmonth']);
940 unset($_POST['date_endyear']);
941
942 unset($_POST['situations']);
943 unset($_POST['progress']);
944 } else {
945 setEventMessages($object->error, $object->errors, 'errors');
946 }
947 }
948 }
949}
950
951
952/*
953 * View
954 */
955
956$title = $object->ref." - ".$langs->trans('Card');
957$help_url = '';
958
959llxHeader('', $title, $help_url);
960
961$form = new Form($db);
962$formother = new FormOther($db);
963if (isModEnabled('project')) {
964 $formproject = new FormProjets($db);
965}
966$companystatic = new Societe($db);
967$invoicerectmp = new FactureRec($db);
968
969$now = dol_now();
970$nowlasthour = dol_get_last_hour($now);
971
972
973/*
974 * Create mode
975 */
976if ($action == 'create') {
977 print load_fiche_titre($langs->trans("CreateRepeatableInvoice"), '', 'bill');
978
979 $object = new Facture($db); // Source invoice
980 $product_static = new Product($db);
981
982 if ($object->fetch($id, $ref) > 0) {
983 $result = $object->getLinesArray();
984
985 print '<form action="'.$_SERVER["PHP_SELF"].'" method="POST">';
986 print '<input type="hidden" name="token" value="'.newToken().'">';
987 print '<input type="hidden" name="action" value="add">';
988 print '<input type="hidden" name="facid" value="'.$object->id.'">';
989
990 print dol_get_fiche_head(null, '', '', 0);
991
992 $rowspan = 4;
993 if (isModEnabled('project')) {
994 $rowspan++;
995 }
996 if ($object->fk_account > 0) {
997 $rowspan++;
998 }
999
1000 print '<table class="border centpercent">';
1001
1002 $object->fetch_thirdparty();
1003
1004 // Title
1005 print '<tr><td class="titlefieldcreate fieldrequired">'.$langs->trans("Title").'</td><td>';
1006 print '<input class="flat quatrevingtpercent" type="text" name="title" value="'.dol_escape_htmltag(GETPOST("title", 'alphanohtml')).'" autofocus>';
1007 print '</td></tr>';
1008
1009 // Third party
1010 print '<tr><td class="titlefieldcreate">'.$langs->trans("Customer").'</td><td>'.$object->thirdparty->getNomUrl(1, 'customer').'</td>';
1011 print '</tr>';
1012
1013 // Invoice subtype
1014 if (getDolGlobalInt('INVOICE_SUBTYPE_ENABLED')) {
1015 print "<tr><td>".$langs->trans("InvoiceSubtype")."</td><td>";
1016 print $form->getSelectInvoiceSubtype(GETPOSTISSET('subtype') ? GETPOST('subtype') : $object->subtype, 'subtype', 0, 0, '');
1017 print "</td></tr>";
1018 }
1019
1020 $note_public = GETPOSTISSET('note_public') ? GETPOST('note_public', 'restricthtml') : $object->note_public;
1021 $note_private = GETPOSTISSET('note_private') ? GETPOST('note_private', 'restricthtml') : $object->note_private;
1022
1023 // Help of substitution key
1024 $substitutionarray = getCommonSubstitutionArray($langs, 2, null, $object);
1025
1026 $substitutionarray['__INVOICE_PREVIOUS_MONTH__'] = $langs->trans("PreviousMonthOfInvoice").' ('.$langs->trans("Example").': '.dol_print_date(dol_time_plus_duree($object->date, -1, 'm'), '%m').')';
1027 $substitutionarray['__INVOICE_MONTH__'] = $langs->trans("MonthOfInvoice").' ('.$langs->trans("Example").': '.dol_print_date($object->date, '%m').')';
1028 $substitutionarray['__INVOICE_NEXT_MONTH__'] = $langs->trans("NextMonthOfInvoice").' ('.$langs->trans("Example").': '.dol_print_date(dol_time_plus_duree($object->date, 1, 'm'), '%m').')';
1029 $substitutionarray['__INVOICE_PREVIOUS_MONTH_TEXT__'] = $langs->trans("TextPreviousMonthOfInvoice").' ('.$langs->trans("Example").': '.dol_print_date(dol_time_plus_duree($object->date, -1, 'm'), '%B').')';
1030 $substitutionarray['__INVOICE_MONTH_TEXT__'] = $langs->trans("TextMonthOfInvoice").' ('.$langs->trans("Example").': '.dol_print_date($object->date, '%B').')';
1031 $substitutionarray['__INVOICE_NEXT_MONTH_TEXT__'] = $langs->trans("TextNextMonthOfInvoice").' ('.$langs->trans("Example").': '.dol_print_date(dol_time_plus_duree($object->date, 1, 'm'), '%B').')';
1032 $substitutionarray['__INVOICE_PREVIOUS_YEAR__'] = $langs->trans("PreviousYearOfInvoice").' ('.$langs->trans("Example").': '.dol_print_date(dol_time_plus_duree($object->date, -1, 'y'), '%Y').')';
1033 $substitutionarray['__INVOICE_YEAR__'] = $langs->trans("YearOfInvoice").' ('.$langs->trans("Example").': '.dol_print_date($object->date, '%Y').')';
1034 $substitutionarray['__INVOICE_NEXT_YEAR__'] = $langs->trans("NextYearOfInvoice").' ('.$langs->trans("Example").': '.dol_print_date(dol_time_plus_duree($object->date, 1, 'y'), '%Y').')';
1035 // Only on template invoices
1036 $substitutionarray['__INVOICE_DATE_NEXT_INVOICE_BEFORE_GEN__'] = $langs->trans("DateNextInvoiceBeforeGen").' ('.$langs->trans("Example").': '.dol_print_date(dol_time_plus_duree($object->date, 1, 'm'), 'dayhour').')';
1037 $substitutionarray['__INVOICE_DATE_NEXT_INVOICE_AFTER_GEN__'] = $langs->trans("DateNextInvoiceAfterGen").' ('.$langs->trans("Example").': '.dol_print_date(dol_time_plus_duree($object->date, 2, 'm'), 'dayhour').')';
1038 $substitutionarray['__INVOICE_COUNTER_CURRENT__'] = $langs->trans("Count");
1039 $substitutionarray['__INVOICE_COUNTER_MAX__'] = $langs->trans("MaxPeriodNumber");
1040
1041 $htmltext = '<i>'.$langs->trans("FollowingConstantsWillBeSubstituted").':<br>';
1042 foreach ($substitutionarray as $key => $val) {
1043 $htmltext .= $key.' = '.$langs->trans($val).'<br>';
1044 }
1045 $htmltext .= '</i>';
1046
1047 // Author
1048 print "<tr><td>".$langs->trans("Author")."</td><td>".$user->getFullName($langs)."</td></tr>";
1049
1050 // Payment term
1051 print "<tr><td>".$langs->trans("PaymentConditions")."</td><td>";
1052 print $form->getSelectConditionsPaiements(GETPOSTISSET('cond_reglement_id') ? GETPOST('cond_reglement_id', 'int') : $object->cond_reglement_id, 'cond_reglement_id', -1, 0, 0, '');
1053 //$form->form_conditions_reglement($_SERVER['PHP_SELF'].'?id='.$object->id, $object->cond_reglement_id, 'cond_reglement_id');
1054 print "</td></tr>";
1055
1056 // Payment mode
1057 print "<tr><td>".$langs->trans("PaymentMode")."</td><td>";
1058 print img_picto('', 'payment', 'class="pictofixedwidth"');
1059 print $form->select_types_paiements(GETPOSTISSET('mode_reglement_id') ? GETPOST('mode_reglement_id', 'int') : $object->mode_reglement_id, 'mode_reglement_id', '', 0, 1, 0, 0, 1, '', 1);
1060 //$form->form_modes_reglement($_SERVER['PHP_SELF'].'?id='.$object->id, $object->mode_reglement_id, 'mode_reglement_id', '', 1);
1061 print "</td></tr>";
1062
1063 // Bank account
1064 if ($object->fk_account > 0) {
1065 print "<tr><td>".$langs->trans('BankAccount')."</td><td>";
1066 $form->formSelectAccount($_SERVER['PHP_SELF'].'?id='.$object->id, $object->fk_account, 'none');
1067 print "</td></tr>";
1068 }
1069
1070 //extrafields
1071 $draft = new Facture($db);
1072 $draft->fetch(GETPOST('facid', 'int'));
1073
1074 $extralabels = new ExtraFields($db);
1075 $extralabels = $extrafields->fetch_name_optionals_label($draft->table_element);
1076 if ($draft->fetch_optionals() > 0) {
1077 $object->array_options = array_merge($object->array_options, $draft->array_options);
1078 }
1079
1080 print $object->showOptionals($extrafields, 'create', $parameters);
1081
1082 // Project
1083 if (isModEnabled('project') && is_object($object->thirdparty) && $object->thirdparty->id > 0) {
1084 $projectid = GETPOST('projectid') ? GETPOST('projectid') : $object->fk_project;
1085 $langs->load('projects');
1086 print '<tr><td>'.$langs->trans('Project').'</td><td>';
1087 print img_picto('', 'project', 'class="pictofixedwidth"');
1088 $numprojet = $formproject->select_projects($object->thirdparty->id, $projectid, 'projectid', 0, 0, 1, 0, 0, 0, 0, '', 0, 0, '');
1089 print ' &nbsp; <a href="'.DOL_URL_ROOT.'/projet/card.php?socid='.$object->thirdparty->id.'&action=create&status=1&backtopage='.urlencode($_SERVER["PHP_SELF"].'?action=create&socid='.$object->thirdparty->id.(!empty($id) ? '&id='.$id : '')).'">'.img_object($langs->trans("AddProject"), 'add').'</a>';
1090 print '</td></tr>';
1091 }
1092
1093 // Model pdf
1094 print "<tr><td>".$langs->trans('Model')."</td><td>";
1095 include_once DOL_DOCUMENT_ROOT.'/core/modules/facture/modules_facture.php';
1097 print img_picto('', 'generic', 'class="pictofixedwidth"');
1098 print $form->selectarray('modelpdf', $list, $conf->global->FACTURE_ADDON_PDF);
1099 print "</td></tr>";
1100
1101 // Public note
1102 print '<tr>';
1103 print '<td class="tdtop">';
1104 print $form->textwithpicto($langs->trans('NotePublic'), $htmltext, 1, 'help', '', 0, 2, 'notepublic');
1105 print '</td>';
1106 print '<td>';
1107 $doleditor = new DolEditor('note_public', $note_public, '', 80, 'dolibarr_notes', 'In', 0, false, !getDolGlobalString('FCKEDITOR_ENABLE_NOTE_PUBLIC') ? 0 : 1, ROWS_3, '90%');
1108 print $doleditor->Create(1);
1109
1110 // Private note
1111 if (empty($user->socid)) {
1112 print '<tr>';
1113 print '<td class="tdtop">';
1114 print $form->textwithpicto($langs->trans('NotePrivate'), $htmltext, 1, 'help', '', 0, 2, 'noteprivate');
1115 print '</td>';
1116 print '<td>';
1117 $doleditor = new DolEditor('note_private', $note_private, '', 80, 'dolibarr_notes', 'In', 0, false, !getDolGlobalString('FCKEDITOR_ENABLE_NOTE_PRIVATE') ? 0 : 1, ROWS_3, '90%');
1118 print $doleditor->Create(1);
1119 // print '<textarea name="note_private" wrap="soft" cols="70" rows="'.ROWS_3.'">'.$note_private.'.</textarea>
1120 print '</td></tr>';
1121 }
1122
1123 print "</table>";
1124
1125 print dol_get_fiche_end();
1126
1127 // Autogeneration
1128 $title = $langs->trans("Recurrence");
1129 print load_fiche_titre(img_picto('', 'recurring', 'class="pictofixedwidth"').$title, '', '');
1130
1131 print '<span class="opacitymedium">'.$langs->trans("ToCreateARecurringInvoiceGeneAuto", $langs->transnoentitiesnoconv('Module2300Name')).'</span><br><br>';
1132
1133 print dol_get_fiche_head(null, '', '', 0);
1134
1135 print '<table class="border centpercent">';
1136
1137 // Frequency + unit
1138 print '<tr><td class="titlefieldcreate">'.$form->textwithpicto($langs->trans("Frequency"), $langs->transnoentitiesnoconv('toolTipFrequency'))."</td><td>";
1139 print "<input type='text' name='frequency' value='".GETPOST('frequency', 'int')."' size='4' />&nbsp;";
1140 print $form->selectarray('unit_frequency', array('d'=>$langs->trans('Day'), 'm'=>$langs->trans('Month'), 'y'=>$langs->trans('Year')), (GETPOST('unit_frequency') ? GETPOST('unit_frequency') : 'm'));
1141 print "</td></tr>";
1142
1143 // Date next run
1144 print "<tr><td>".$langs->trans('NextDateToExecution')."</td><td>";
1145 $date_next_execution = isset($date_next_execution) ? $date_next_execution : (GETPOST('remonth') ? dol_mktime(12, 0, 0, GETPOST('remonth'), GETPOST('reday'), GETPOST('reyear')) : -1);
1146 print $form->selectDate($date_next_execution, '', 1, 1, '', "add", 1, 1);
1147 print "</td></tr>";
1148
1149 // Number max of generation
1150 print "<tr><td>".$langs->trans("MaxPeriodNumber")."</td><td>";
1151 print '<input type="text" name="nb_gen_max" value="'.GETPOST('nb_gen_max').'" size="5" />';
1152 print "</td></tr>";
1153
1154 // Auto validate the invoice
1155 print "<tr><td>".$langs->trans("StatusOfAutoGeneratedInvoices")."</td><td>";
1156 $select = array('0'=>$langs->trans('BillStatusDraft'), '1'=>$langs->trans('BillStatusValidated'));
1157 print $form->selectarray('auto_validate', $select, GETPOST('auto_validate'));
1158 print "</td></tr>";
1159
1160 // Auto generate document
1161 if (getDolGlobalString('INVOICE_REC_CAN_DISABLE_DOCUMENT_FILE_GENERATION')) {
1162 print "<tr><td>".$langs->trans("StatusOfGeneratedDocuments")."</td><td>";
1163 $select = array('0'=>$langs->trans('DoNotGenerateDoc'), '1'=>$langs->trans('AutoGenerateDoc'));
1164 print $form->selectarray('generate_pdf', $select, GETPOST('generate_pdf'));
1165 print "</td></tr>";
1166 } else {
1167 print '<input type="hidden" name="generate_pdf" value="1">';
1168 }
1169
1170 print "</table>";
1171
1172 print dol_get_fiche_end();
1173
1174
1175 $title = $langs->trans("ProductsAndServices");
1176 if (!isModEnabled('service')) {
1177 $title = $langs->trans("Products");
1178 } elseif (!isModEnabled('product')) {
1179 $title = $langs->trans("Services");
1180 }
1181
1182 print load_fiche_titre($title, '', '');
1183
1184 /*
1185 * Invoice lines
1186 */
1187 print '<div class="div-table-responsive-no-min">';
1188 print '<table id="tablelines" class="noborder noshadow centpercent">';
1189
1190 // Show object lines
1191 if (!empty($object->lines)) {
1192 $object->printOriginLinesList('', $selectedLines);
1193 }
1194
1195 print "</table>\n";
1196 print '<div>';
1197
1198 print '</td></tr>';
1199
1200 if (!empty($flag_price_may_change)) {
1201 print '<tr><td colspan="3" class="left">';
1202 print '<select name="usenewprice" class="flat">';
1203 print '<option value="0">'.$langs->trans("AlwaysUseFixedPrice").'</option>';
1204 print '<option value="1" disabled>'.$langs->trans("AlwaysUseNewPrice").'</option>';
1205 print '</select>';
1206 print '</td></tr>';
1207 }
1208 print "</table>\n";
1209
1210 print $form->buttonsSaveCancel("Create");
1211
1212 print "</form>\n";
1213 } else {
1214 dol_print_error('', "Error, no invoice ".$object->id);
1215 }
1216} else {
1217 /*
1218 * View mode
1219 */
1220 if ($object->id > 0) {
1221 $object->fetch_thirdparty();
1222
1223 $formconfirm = '';
1224 // Confirmation of deletion of product line
1225 if ($action == 'ask_deleteline') {
1226 $formconfirm = $form->formconfirm($_SERVER["PHP_SELF"].'?id='.$object->id.'&lineid='.$lineid, $langs->trans('DeleteProductLine'), $langs->trans('ConfirmDeleteProductLine'), 'confirm_deleteline', '', 'no', 1);
1227 }
1228 // Confirm delete of repeatable invoice
1229 if ($action == 'delete') {
1230 $formconfirm = $form->formconfirm($_SERVER["PHP_SELF"].'?id='.$object->id, $langs->trans('DeleteRepeatableInvoice'), $langs->trans('ConfirmDeleteRepeatableInvoice'), 'confirm_delete', '', 'no', 1);
1231 }
1232
1233 // Call Hook formConfirm
1234 $parameters = array('formConfirm' => $formconfirm, 'lineid' => $lineid);
1235 $reshook = $hookmanager->executeHooks('formConfirm', $parameters, $object, $action); // Note that $action and $object may have been modified by hook
1236 if (empty($reshook)) {
1237 $formconfirm .= $hookmanager->resPrint;
1238 } elseif ($reshook > 0) {
1239 $formconfirm = $hookmanager->resPrint;
1240 }
1241
1242 print $formconfirm;
1243
1244 $author = new User($db);
1245 $author->fetch($object->user_author);
1246
1247 $head = invoice_rec_prepare_head($object);
1248
1249 print dol_get_fiche_head($head, 'card', $langs->trans("RepeatableInvoice"), -1, 'bill'); // Add a div
1250
1251 // Recurring invoice content
1252
1253 $linkback = '<a href="'.DOL_URL_ROOT.'/compta/facture/invoicetemplate_list.php?restore_lastsearch_values=1'.(!empty($socid) ? '&socid='.$socid : '').'">'.$langs->trans("BackToList").'</a>';
1254
1255 $morehtmlref = '';
1256 if ($action != 'editref') {
1257 $morehtmlref .= $form->editfieldkey($object->ref, 'ref', $object->ref, $object, $user->hasRight('facture', 'creer'), '', '', 0, 2);
1258 } else {
1259 $morehtmlref .= $form->editfieldval('', 'ref', $object->ref, $object, $user->hasRight('facture', 'creer'), 'string');
1260 }
1261
1262 $morehtmlref .= '<div class="refidno">';
1263 // Ref customer
1264 //$morehtmlref.=$form->editfieldkey("RefCustomer", 'ref_client', $object->ref_client, $object, $user->hasRight('facture', 'creer'), 'string', '', 0, 1);
1265 //$morehtmlref.=$form->editfieldval("RefCustomer", 'ref_client', $object->ref_client, $object, $user->hasRight('facture', 'creer'), 'string', '', null, null, '', 1);
1266 // Thirdparty
1267 $morehtmlref .= $object->thirdparty->getNomUrl(1, 'customer');
1268 // Project
1269 if (isModEnabled('project')) {
1270 $langs->load("projects");
1271 $morehtmlref .= '<br>';
1272 if ($user->hasRight('facture', 'creer')) {
1273 $morehtmlref .= img_picto($langs->trans("Project"), 'project', 'class="pictofixedwidth"');
1274 if ($action != 'classify') {
1275 $morehtmlref .= '<a class="editfielda" href="'.$_SERVER['PHP_SELF'].'?action=classify&token='.newToken().'&id='.$object->id.'">'.img_edit($langs->transnoentitiesnoconv('SetProject')).'</a> ';
1276 }
1277 $morehtmlref .= $form->form_project($_SERVER['PHP_SELF'].'?id='.$object->id, $object->socid, $object->fk_project, ($action == 'classify' ? 'projectid' : 'none'), 0, 0, 0, 1, '', 'maxwidth300');
1278 } else {
1279 if (!empty($object->fk_project)) {
1280 $proj = new Project($db);
1281 $proj->fetch($object->fk_project);
1282 $morehtmlref .= ' : '.$proj->getNomUrl(1);
1283 if ($proj->title) {
1284 $morehtmlref .= ' - '.$proj->title;
1285 }
1286 } else {
1287 $morehtmlref .= '';
1288 }
1289 }
1290 }
1291 $morehtmlref .= '</div>';
1292
1293 $morehtmlright = '';
1294
1295 dol_banner_tab($object, 'ref', $linkback, 1, 'title', 'none', $morehtmlref, '', 0, '', $morehtmlright);
1296
1297 print '<div class="fichecenter">';
1298 print '<div class="fichehalfleft">';
1299 print '<div class="underbanner clearboth"></div>';
1300
1301 print '<table class="border centpercent tableforfield">';
1302
1303 // Invoice subtype
1304 if (getDolGlobalInt('INVOICE_SUBTYPE_ENABLED')) {
1305 print "<tr><td>".$langs->trans("InvoiceSubtype")."</td><td>";
1306 if ($object->subtype > 0) {
1307 print $object->getSubtypeLabel('facture_rec');
1308 }
1309 print "</td></tr>";
1310 }
1311
1312 // Author
1313 print '<tr><td class="titlefield">'.$langs->trans("Author").'</td><td>';
1314 print $author->getNomUrl(-1);
1315 print "</td></tr>";
1316
1317 // Amount (excl. tax)
1318 print '<tr><td>'.$langs->trans("AmountHT").'</td>';
1319 print '<td>'.price($object->total_ht, '', $langs, 1, -1, -1, $conf->currency).'</td>';
1320 print '</tr>';
1321
1322 // Amount tax
1323 print '<tr><td>'.$langs->trans("AmountVAT").'</td><td>'.price($object->total_tva, '', $langs, 1, -1, -1, $conf->currency).'</td>';
1324 print '</tr>';
1325
1326 // Amount Local Taxes
1327 if (($mysoc->localtax1_assuj == "1" && $mysoc->useLocalTax(1)) || $object->total_localtax1 != 0) { // Localtax1
1328 print '<tr><td>'.$langs->transcountry("AmountLT1", $mysoc->country_code).'</td>';
1329 print '<td class="nowrap">'.price($object->total_localtax1, 1, '', 1, - 1, - 1, $conf->currency).'</td></tr>';
1330 }
1331 if (($mysoc->localtax2_assuj == "1" && $mysoc->useLocalTax(2)) || $object->total_localtax2 != 0) { // Localtax2
1332 print '<tr><td>'.$langs->transcountry("AmountLT2", $mysoc->country_code).'</td>';
1333 print '<td class=nowrap">'.price($object->total_localtax2, 1, '', 1, - 1, - 1, $conf->currency).'</td></tr>';
1334 }
1335
1336 print '<tr><td>'.$langs->trans("AmountTTC").'</td><td colspan="3">'.price($object->total_ttc, '', $langs, 1, -1, -1, $conf->currency).'</td>';
1337 print '</tr>';
1338
1339
1340 // Payment term
1341 print '<tr><td>';
1342 print '<table class="nobordernopadding centpercent"><tr><td>';
1343 print $langs->trans('PaymentConditionsShort');
1344 print '</td>';
1345 if ($action != 'editconditions' && $user->hasRight('facture', 'creer')) {
1346 print '<td class="right"><a class="editfielda" href="'.$_SERVER["PHP_SELF"].'?action=editconditions&token='.newToken().'&facid='.$object->id.'">'.img_edit($langs->trans('SetConditions'), 1).'</a></td>';
1347 }
1348 print '</tr></table>';
1349 print '</td><td>';
1350 if ($action == 'editconditions') {
1351 $form->form_conditions_reglement($_SERVER['PHP_SELF'].'?facid='.$object->id, $object->cond_reglement_id, 'cond_reglement_id');
1352 } else {
1353 $form->form_conditions_reglement($_SERVER['PHP_SELF'].'?facid='.$object->id, $object->cond_reglement_id, 'none');
1354 }
1355 print '</td></tr>';
1356
1357 // Payment mode
1358 print '<tr><td>';
1359 print '<table class="nobordernopadding" width="100%"><tr><td>';
1360 print $langs->trans('PaymentMode');
1361 print '</td>';
1362 if ($action != 'editmode' && $user->hasRight('facture', 'creer')) {
1363 print '<td class="right"><a class="editfielda" href="'.$_SERVER["PHP_SELF"].'?action=editmode&token='.newToken().'&facid='.$object->id.'">'.img_edit($langs->trans('SetMode'), 1).'</a></td>';
1364 }
1365 print '</tr></table>';
1366 print '</td><td>';
1367 if ($action == 'editmode') {
1368 $form->form_modes_reglement($_SERVER['PHP_SELF'].'?facid='.$object->id, $object->mode_reglement_id, 'mode_reglement_id', 'CRDT', 1, 1);
1369 } else {
1370 $form->form_modes_reglement($_SERVER['PHP_SELF'].'?facid='.$object->id, $object->mode_reglement_id, 'none');
1371 }
1372 print '</td></tr>';
1373
1374 // Multicurrency
1375 if (isModEnabled('multicurrency')) {
1376 // Multicurrency code
1377 print '<tr>';
1378 print '<td>';
1379 print '<table class="nobordernopadding" width="100%"><tr><td>';
1380 print $form->editfieldkey('Currency', 'multicurrency_code', '', $object, 0);
1381 print '</td>';
1382 if ($usercancreate && $action != 'editmulticurrencycode' && $object->suspended == $object::STATUS_SUSPENDED) {
1383 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>';
1384 }
1385 print '</tr></table>';
1386 print '</td><td>';
1387 $htmlname = (($usercancreate && $action == 'editmulticurrencycode') ? 'multicurrency_code' : 'none');
1388 $form->form_multicurrency_code($_SERVER['PHP_SELF'].'?id='.$object->id, $object->multicurrency_code, $htmlname);
1389 print '</td></tr>';
1390
1391 // Multicurrency rate
1392 if ($object->multicurrency_code != $conf->currency || $object->multicurrency_tx != 1) {
1393 print '<tr>';
1394 print '<td>';
1395 print '<table class="nobordernopadding" width="100%"><tr><td>';
1396 print $form->editfieldkey('CurrencyRate', 'multicurrency_tx', '', $object, 0);
1397 print '</td>';
1398 if ($usercancreate && $action != 'editmulticurrencyrate' && $object->suspended == $object::STATUS_SUSPENDED && $object->multicurrency_code && $object->multicurrency_code != $conf->currency) {
1399 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>';
1400 }
1401 print '</tr></table>';
1402 print '</td><td>';
1403 if ($action == 'editmulticurrencyrate' || $action == 'actualizemulticurrencyrate') {
1404 if ($action == 'actualizemulticurrencyrate') {
1405 list($object->fk_multicurrency, $object->multicurrency_tx) = MultiCurrency::getIdAndTxFromCode($object->db, $object->multicurrency_code);
1406 }
1407 $form->form_multicurrency_rate($_SERVER['PHP_SELF'].'?id='.$object->id, $object->multicurrency_tx, ($usercancreate ? 'multicurrency_tx' : 'none'), $object->multicurrency_code);
1408 } else {
1409 $form->form_multicurrency_rate($_SERVER['PHP_SELF'].'?id='.$object->id, $object->multicurrency_tx, 'none', $object->multicurrency_code);
1410 if ($object->statut == $object::STATUS_DRAFT && $object->multicurrency_code && $object->multicurrency_code != $conf->currency) {
1411 print '<div class="inline-block"> &nbsp; &nbsp; &nbsp; &nbsp; ';
1412 print '<a href="'.$_SERVER["PHP_SELF"].'?id='.$object->id.'&action=actualizemulticurrencyrate">'.$langs->trans("ActualizeCurrency").'</a>';
1413 print '</div>';
1414 }
1415 }
1416 print '</td></tr>';
1417 }
1418 }
1419
1420 // Help of substitution key
1421 $dateexample = dol_now();
1422 if (!empty($object->frequency) && !empty($object->date_when)) {
1423 $dateexample = $object->date_when;
1424 }
1425
1426 // Help of substitution key
1427 $substitutionarray = getCommonSubstitutionArray($langs, 2, null, $object);
1428
1429 $substitutionarray['__INVOICE_PREVIOUS_MONTH__'] = $langs->trans("PreviousMonthOfInvoice").' ('.$langs->trans("Example").': '.dol_print_date(dol_time_plus_duree($dateexample, -1, 'm'), '%m').')';
1430 $substitutionarray['__INVOICE_MONTH__'] = $langs->trans("MonthOfInvoice").' ('.$langs->trans("Example").': '.dol_print_date($dateexample, '%m').')';
1431 $substitutionarray['__INVOICE_NEXT_MONTH__'] = $langs->trans("NextMonthOfInvoice").' ('.$langs->trans("Example").': '.dol_print_date(dol_time_plus_duree($dateexample, 1, 'm'), '%m').')';
1432 $substitutionarray['__INVOICE_PREVIOUS_MONTH_TEXT__'] = $langs->trans("TextPreviousMonthOfInvoice").' ('.$langs->trans("Example").': '.dol_print_date(dol_time_plus_duree($dateexample, -1, 'm'), '%B').')';
1433 $substitutionarray['__INVOICE_MONTH_TEXT__'] = $langs->trans("TextMonthOfInvoice").' ('.$langs->trans("Example").': '.dol_print_date($dateexample, '%B').')';
1434 $substitutionarray['__INVOICE_NEXT_MONTH_TEXT__'] = $langs->trans("TextNextMonthOfInvoice").' ('.$langs->trans("Example").': '.dol_print_date(dol_time_plus_duree($dateexample, 1, 'm'), '%B').')';
1435 $substitutionarray['__INVOICE_PREVIOUS_YEAR__'] = $langs->trans("PreviousYearOfInvoice").' ('.$langs->trans("Example").': '.dol_print_date(dol_time_plus_duree($dateexample, -1, 'y'), '%Y').')';
1436 $substitutionarray['__INVOICE_YEAR__'] = $langs->trans("YearOfInvoice").' ('.$langs->trans("Example").': '.dol_print_date($dateexample, '%Y').')';
1437 $substitutionarray['__INVOICE_NEXT_YEAR__'] = $langs->trans("NextYearOfInvoice").' ('.$langs->trans("Example").': '.dol_print_date(dol_time_plus_duree($dateexample, 1, 'y'), '%Y').')';
1438 // Only on template invoices
1439 $substitutionarray['__INVOICE_DATE_NEXT_INVOICE_BEFORE_GEN__'] = $langs->trans("DateNextInvoiceBeforeGen").' ('.$langs->trans("Example").': '.dol_print_date(($object->date_when ? $object->date_when : dol_now()), 'dayhour').')';
1440 $substitutionarray['__INVOICE_DATE_NEXT_INVOICE_AFTER_GEN__'] = $langs->trans("DateNextInvoiceAfterGen").' ('.$langs->trans("Example").': '.dol_print_date(dol_time_plus_duree(($object->date_when ? $object->date_when : dol_now()), $object->frequency, $object->unit_frequency), 'dayhour').')';
1441 $substitutionarray['__INVOICE_COUNTER_CURRENT__'] = $object->nb_gen_done;
1442 $substitutionarray['__INVOICE_COUNTER_MAX__'] = $object->nb_gen_max;
1443
1444 $htmltext = '<i>'.$langs->trans("FollowingConstantsWillBeSubstituted").':<br>';
1445 foreach ($substitutionarray as $key => $val) {
1446 $htmltext .= $key.' = '.$langs->trans($val).'<br>';
1447 }
1448 $htmltext .= '</i>';
1449
1450 // Bank Account
1451 print '<tr><td class="nowrap">';
1452 print '<table width="100%" class="nobordernopadding"><tr><td class="nowrap">';
1453 print $langs->trans('BankAccount');
1454 print '<td>';
1455 if (($action != 'editbankaccount') && $user->hasRight('facture', 'creer') && $object->statut == FactureRec::STATUS_DRAFT) {
1456 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>';
1457 }
1458 print '</tr></table>';
1459 print '</td><td>';
1460 if ($action == 'editbankaccount') {
1461 $form->formSelectAccount($_SERVER['PHP_SELF'].'?id='.$object->id, $object->fk_account, 'fk_account', 1);
1462 } else {
1463 $form->formSelectAccount($_SERVER['PHP_SELF'].'?id='.$object->id, $object->fk_account, 'none');
1464 }
1465 print "</td>";
1466 print '</tr>';
1467
1468 // Extrafields
1469 include DOL_DOCUMENT_ROOT.'/core/tpl/extrafields_view.tpl.php';
1470
1471
1472 // Note public
1473 print '<tr><td>';
1474 print $form->editfieldkey($form->textwithpicto($langs->trans('NotePublic'), $htmltext, 1, 'help', '', 0, 2, 'notepublic'), 'note_public', $object->note_public, $object, $user->hasRight('facture', 'creer'));
1475 print '</td><td class="wordbreak">';
1476 print $form->editfieldval($langs->trans("NotePublic"), 'note_public', $object->note_public, $object, $user->hasRight('facture', 'creer'), 'textarea:'.ROWS_4.':90%', '', null, null, '', 1);
1477 print '</td>';
1478 print '</tr>';
1479
1480 // Note private
1481 print '<tr><td>';
1482 print $form->editfieldkey($form->textwithpicto($langs->trans("NotePrivate"), $htmltext, 1, 'help', '', 0, 2, 'noteprivate'), 'note_private', $object->note_private, $object, $user->hasRight('facture', 'creer'));
1483 print '</td><td class="wordbreak">';
1484 print $form->editfieldval($langs->trans("NotePrivate"), 'note_private', $object->note_private, $object, $user->hasRight('facture', 'creer'), 'textarea:'.ROWS_4.':90%', '', null, null, '', 1);
1485 print '</td>';
1486 print '</tr>';
1487
1488 // Model pdf
1489 print '<tr><td class="nowrap">';
1490 print '<table width="100%" class="nobordernopadding"><tr><td class="nowrap">';
1491 print $langs->trans('Model');
1492 print '<td>';
1493 if (($action != 'editmodelpdf') && $user->hasRight('facture', 'creer') && $object->statut == FactureRec::STATUS_DRAFT) {
1494 print '<td class="right"><a class="editfielda" href="'.$_SERVER["PHP_SELF"].'?action=editmodelpdf&token='.newToken().'&id='.$object->id.'">'.img_edit($langs->trans('SetModel'), 1).'</a></td>';
1495 }
1496 print '</tr></table>';
1497 print '</td><td>';
1498 if ($action == 'editmodelpdf') {
1499 include_once DOL_DOCUMENT_ROOT.'/core/modules/facture/modules_facture.php';
1500 $list = array();
1501 $models = ModelePDFFactures::liste_modeles($db);
1502 foreach ($models as $k => $model) {
1503 $list[] = str_replace(':', '|', $k).':'.$model;
1504 }
1505 $select = 'select;'.implode(',', $list);
1506 print $form->editfieldval($langs->trans("Model"), 'modelpdf', $object->model_pdf, $object, $user->hasRight('facture', 'creer'), $select);
1507 } else {
1508 print $object->model_pdf;
1509 }
1510 print "</td>";
1511 print '</tr>';
1512
1513 // Other attributes
1514 $cols = 2;
1515
1516
1517 print '</table>';
1518
1519 print '</div>';
1520 print '<div class="fichehalfright">';
1521 print '<div class="underbanner clearboth"></div>';
1522
1523
1524 /*
1525 * Recurrence
1526 */
1527 $title = $langs->trans("Recurrence");
1528
1529 print '<table class="border centpercent tableforfield">';
1530
1531 print '<tr><td colspan="2">'.img_picto('', 'recurring', 'class="pictofixedwidth"').$title.'</td></tr>';
1532
1533 // if "frequency" is empty or = 0, the reccurence is disabled
1534 print '<tr><td style="width: 50%">';
1535 print '<table class="nobordernopadding" width="100%"><tr><td>';
1536 print $langs->trans('Frequency');
1537 print '</td>';
1538 if ($action != 'editfrequency' && $user->hasRight('facture', 'creer')) {
1539 print '<td class="right"><a class="editfielda" href="'.$_SERVER["PHP_SELF"].'?action=editfrequency&token='.newToken().'&facid='.$object->id.'">'.img_edit($langs->trans('Edit'), 1).'</a></td>';
1540 }
1541 print '</tr></table>';
1542 print '</td><td>';
1543 if ($action == 'editfrequency') {
1544 print '<form method="post" action="'.$_SERVER["PHP_SELF"].'?facid='.$object->id.'">';
1545 print '<input type="hidden" name="action" value="setfrequency">';
1546 print '<input type="hidden" name="token" value="'.newToken().'">';
1547 print '<table class="nobordernopadding">';
1548 print '<tr><td>';
1549 print "<input type='text' name='frequency' value='".$object->frequency."' size='5' />&nbsp;";
1550 print $form->selectarray('unit_frequency', array('d'=>$langs->trans('Day'), 'm'=>$langs->trans('Month'), 'y'=>$langs->trans('Year')), ($object->unit_frequency ? $object->unit_frequency : 'm'));
1551 print '</td>';
1552 print '<td class="left"><input type="submit" class="button button-edit smallpaddingimp" value="'.$langs->trans("Modify").'"></td>';
1553 print '</tr></table></form>';
1554 } else {
1555 if ($object->frequency > 0) {
1556 print $langs->trans('FrequencyPer_'.$object->unit_frequency, $object->frequency);
1557 } else {
1558 print '<span class="opacitymedium">'.$langs->trans("NotARecurringInvoiceTemplate").'</span>';
1559 }
1560 }
1561 print '</td></tr>';
1562
1563 // Date when (next invoice generation)
1564 print '<tr><td>';
1565 if ($action == 'date_when' || $object->frequency > 0) {
1566 print $form->editfieldkey($langs->trans("NextDateToExecution"), 'date_when', $object->date_when, $object, $user->hasRight('facture', 'creer'), 'day');
1567 } else {
1568 print $langs->trans("NextDateToExecution");
1569 }
1570 print '</td><td>';
1571 if ($action == 'date_when' || $object->frequency > 0) {
1572 print $form->editfieldval($langs->trans("NextDateToExecution"), 'date_when', $object->date_when, $object, $user->hasRight('facture', 'creer'), 'day', $object->date_when, null, '', '', 0, 'strikeIfMaxNbGenReached');
1573 }
1574 //var_dump(dol_print_date($object->date_when+60, 'dayhour').' - '.dol_print_date($now, 'dayhour'));
1575 if (!$object->isMaxNbGenReached()) {
1576 if (!$object->suspended && $action != 'editdate_when' && $object->frequency > 0 && $object->date_when && $object->date_when < $now) {
1577 print img_warning($langs->trans("Late"));
1578 }
1579 } else {
1580 print img_info($langs->trans("MaxNumberOfGenerationReached"));
1581 }
1582 print '</td>';
1583 print '</tr>';
1584
1585 // Max period / Rest period
1586 print '<tr><td>';
1587 if ($action == 'nb_gen_max' || $object->frequency > 0) {
1588 print $form->editfieldkey($langs->trans("MaxPeriodNumber"), 'nb_gen_max', $object->nb_gen_max, $object, $user->hasRight('facture', 'creer'));
1589 } else {
1590 print $langs->trans("MaxPeriodNumber");
1591 }
1592 print '</td><td>';
1593 if ($action == 'nb_gen_max' || $object->frequency > 0) {
1594 print $form->editfieldval($langs->trans("MaxPeriodNumber"), 'nb_gen_max', $object->nb_gen_max ? $object->nb_gen_max : '', $object, $user->hasRight('facture', 'creer'));
1595 } else {
1596 print '';
1597 }
1598 print '</td>';
1599 print '</tr>';
1600
1601 // Status of auto generated invoices
1602 print '<tr><td>';
1603 if ($action == 'auto_validate' || $object->frequency > 0) {
1604 print $form->editfieldkey($langs->trans("StatusOfAutoGeneratedInvoices"), 'auto_validate', $object->auto_validate, $object, $user->hasRight('facture', 'creer'));
1605 } else {
1606 print $langs->trans("StatusOfAutoGeneratedInvoices");
1607 }
1608 print '</td><td>';
1609 $select = 'select;0:'.$langs->trans('BillStatusDraft').',1:'.$langs->trans('BillStatusValidated');
1610 if ($action == 'auto_validate' || $object->frequency > 0) {
1611 print $form->editfieldval($langs->trans("StatusOfAutoGeneratedInvoices"), 'auto_validate', $object->auto_validate, $object, $user->hasRight('facture', 'creer'), $select);
1612 }
1613 print '</td>';
1614 // Auto generate documents
1615 if (getDolGlobalString('INVOICE_REC_CAN_DISABLE_DOCUMENT_FILE_GENERATION')) {
1616 print '<tr>';
1617 print '<td>';
1618 if ($action == 'generate_pdf' || $object->frequency > 0) {
1619 print $form->editfieldkey($langs->trans("StatusOfGeneratedDocuments"), 'generate_pdf', $object->generate_pdf, $object, $user->hasRight('facture', 'creer'));
1620 } else {
1621 print $langs->trans("StatusOfGeneratedDocuments");
1622 }
1623 print '</td>';
1624 print '<td>';
1625 $select = 'select;0:'.$langs->trans('DoNotGenerateDoc').',1:'.$langs->trans('AutogenerateDoc');
1626 if ($action == 'generate_pdf' || $object->frequency > 0) {
1627 print $form->editfieldval($langs->trans("StatusOfGeneratedDocuments"), 'generate_pdf', $object->generate_pdf, $object, $user->hasRight('facture', 'creer'), $select);
1628 }
1629 print '</td>';
1630 print '</tr>';
1631 } else {
1632 print '<input type="hidden" name="generate_pdf" value="1">';
1633 }
1634
1635 print '</table>';
1636
1637 // Frequencry/Recurring section
1638 if ($object->frequency > 0) {
1639 print '<br>';
1640
1641 if (!isModEnabled('cron')) {
1642 print info_admin($langs->trans("EnableAndSetupModuleCron", $langs->transnoentitiesnoconv("Module2300Name")));
1643 }
1644
1645 print '<div class="underbanner clearboth"></div>';
1646 print '<table class="border centpercent tableforfield">';
1647
1648 // Nb of generation already done
1649 print '<tr><td style="width: 50%">'.$langs->trans("NbOfGenerationDone").'</td>';
1650 print '<td>';
1651 print $object->nb_gen_done ? $object->nb_gen_done : '0';
1652 print '</td>';
1653 print '</tr>';
1654
1655 // Date last
1656 print '<tr><td>';
1657 print $langs->trans("DateLastGeneration");
1658 print '</td><td>';
1659 print dol_print_date($object->date_last_gen, 'dayhour');
1660 print '</td>';
1661 print '</tr>';
1662
1663 print '</table>';
1664
1665 print '<br>';
1666 }
1667
1668 print '</div>';
1669 print '</div>';
1670
1671 print '<div class="clearboth"></div><br>';
1672
1673
1674 // Lines
1675 print '<form name="addproduct" id="addproduct" action="'.$_SERVER["PHP_SELF"].'?id='.$object->id.(($action != 'editline') ? '#add' : '#line_'.GETPOST('lineid', 'int')).'" method="POST">';
1676 print '<input type="hidden" name="token" value="' . newToken().'">';
1677 print '<input type="hidden" name="action" value="' . (($action != 'editline') ? 'addline' : 'updateline').'">';
1678 print '<input type="hidden" name="mode" value="">';
1679 print '<input type="hidden" name="id" value="' . $object->id.'">';
1680 print '<input type="hidden" name="page_y" value="">';
1681
1682 if (!empty($conf->use_javascript_ajax) && $object->statut == 0) {
1683 include DOL_DOCUMENT_ROOT.'/core/tpl/ajaxrow.tpl.php';
1684 }
1685
1686 print '<div class="div-table-responsive-no-min">';
1687 print '<table id="tablelines" class="noborder noshadow centpercent">';
1688 // Show object lines
1689 if (!empty($object->lines)) {
1690 $canchangeproduct = 1;
1691 $object->printObjectLines($action, $mysoc, $object->thirdparty, $lineid, 0); // No date selector for template invoice
1692 }
1693
1694 // Form to add new line
1695 if ($object->statut == $object::STATUS_DRAFT && $user->hasRight('facture', 'creer') && $action != 'valid' && $action != 'editline') {
1696 if ($action != 'editline') {
1697 // Add free products/services
1698
1699 $parameters = array();
1700 $reshook = $hookmanager->executeHooks('formAddObjectLine', $parameters, $object, $action); // Note that $action and $object may have been modified by hook
1701 if ($reshook < 0) {
1702 setEventMessages($hookmanager->error, $hookmanager->errors, 'errors');
1703 }
1704 if (empty($reshook)) {
1705 $object->formAddObjectLine(0, $mysoc, $object->thirdparty);
1706 } // No date selector for template invoice
1707 }
1708 }
1709
1710 print "</table>\n";
1711 print '</div>';
1712
1713 print "</form>\n";
1714
1715 print dol_get_fiche_end();
1716
1717
1718 /*
1719 * Action bar
1720 */
1721 print '<div class="tabsAction">';
1722
1723 $parameters = array();
1724 $reshook = $hookmanager->executeHooks('addMoreActionsButtons', $parameters, $object, $action); // Note that $action and $object may have been modified by hook
1725 if (empty($reshook)) {
1726 $params = array(
1727 'attr' => array(
1728 'class' => 'classfortooltip',
1729 ),
1730 );
1731 if (empty($object->suspended)) {
1732 if ($user->hasRight('facture', 'creer')) {
1733 if (!empty($object->frequency) && $object->nb_gen_max > 0 && ($object->nb_gen_done >= $object->nb_gen_max)) {
1734 print '<div class="inline-block divButAction"><a class="butActionRefused classfortooltip" href="#" title="' . dol_escape_htmltag($langs->trans("MaxGenerationReached")) . '">' . $langs->trans("CreateBill") . '</a></div>';
1735 } else {
1736 if (empty($object->frequency) || $object->date_when <= $nowlasthour) {
1737 print '<div class="inline-block divButAction"><a class="butAction" href="' . DOL_URL_ROOT . '/compta/facture/card.php?action=create&socid=' . $object->thirdparty->id . '&fac_rec=' . $object->id . '">' . $langs->trans("CreateBill") . '</a></div>';
1738 } else {
1739 print '<div class="inline-block divButAction"><a class="butActionRefused classfortooltip" href="#" title="' . dol_escape_htmltag($langs->trans("DateIsNotEnough")) . '">' . $langs->trans("CreateBill") . '</a></div>';
1740 }
1741 }
1742 } else {
1743 print '<div class="inline-block divButAction"><a class="butActionRefused classfortooltip" href="#">' . $langs->trans("CreateBill") . '</a></div>';
1744 }
1745 }
1746
1747 if ($user->hasRight('facture', 'creer')) {
1748 if (empty($object->suspended)) {
1749 print '<div class="inline-block divButAction"><a class="butActionDelete" href="'.$_SERVER["PHP_SELF"].'?action=disable&id='.$object->id.'&token='.newToken().'">'.$langs->trans("Disable").'</a></div>';
1750 } else {
1751 print '<div class="inline-block divButAction"><a class="butAction" href="'.$_SERVER["PHP_SELF"].'?action=enable&id='.$object->id.'&token='.newToken().'">'.$langs->trans("Enable").'</a></div>';
1752 }
1753 }
1754
1755 // Delete
1756 print dolGetButtonAction($langs->trans("Delete"), '', 'delete', $_SERVER["PHP_SELF"] . '?id=' . $object->id . '&action=delete&token=' . newToken(), 'delete', $user->hasRight('facture', 'supprimer'));
1757 }
1758 print '</div>';
1759
1760
1761
1762 print '<div class="fichecenter"><div class="fichehalfleft">';
1763 print '<a name="builddoc"></a>'; // ancre
1764
1765
1766 // Show links to link elements
1767 $linktoelem = $form->showLinkToObjectBlock($object, null, array('invoice'));
1768
1769 $somethingshown = $form->showLinkedObjectBlock($object, $linktoelem);
1770
1771
1772 print '</div>';
1773 print '<div class="fichehalfright">';
1774
1775 $MAXEVENT = 10;
1776
1777 //$morehtmlcenter = dolGetButtonTitle($langs->trans('SeeAll'), '', 'fa fa-bars imgforviewmode', dol_buildpath('/mymodule/myobject_agenda.php', 1).'?id='.$object->id);
1778 $morehtmlcenter = '';
1779
1780 // List of actions on element
1781 include_once DOL_DOCUMENT_ROOT.'/core/class/html.formactions.class.php';
1782 $formactions = new FormActions($db);
1783 $morehtmlcenter = '';
1784 $somethingshown = $formactions->showactions($object, $object->element, (is_object($object->thirdparty) ? $object->thirdparty->id : 0), 1, '', $MAXEVENT, '', $morehtmlcenter);
1785
1786 print '</div>';
1787 print '</div>';
1788 }
1789}
1790
1791// End of page
1792llxFooter();
1793$db->close();
if(preg_match('/set_([a-z0-9_\-]+)/i', $action, $reg)) if(preg_match('/del_([a-z0-9_\-]+)/i', $action, $reg)) if($action=='set') elseif( $action=='specimen') elseif($action=='setmodel') elseif( $action=='del') elseif($action=='setdoc') $formactions
View.
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
const STATUS_DRAFT
Draft status.
Class to manage a WYSIWYG editor.
Class to manage standard extra fields.
Class to manage invoices.
const TYPE_REPLACEMENT
Replacement invoice.
const TYPE_STANDARD
Standard invoice.
Class to manage invoice lines of templates.
Class to manage invoice templates.
Class to manage building of HTML components.
Class to manage generation of HTML components Only common components must be here.
Classe permettant la generation de composants html autre Only common components are here.
Class to manage building of HTML components.
static liste_modeles($db, $maxfilenamelength=0)
Return list of active generation modules.
static getIdAndTxFromCode($dbs, $code, $date_document='')
Get id and rate of currency from code.
Class to manage products or services.
Class to manage projects.
Class to manage third parties objects (customers, suppliers, prospects...)
Class to manage translations.
Class to manage Dolibarr users.
getCountry($searchkey, $withcode='', $dbtouse=0, $outputlangs='', $entconv=1, $searchlabel='')
Return country label, code or id from an id, code or label.
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:640
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.
dol_banner_tab($object, $paramid, $morehtml='', $shownav=1, $fieldid='rowid', $fieldref='ref', $morehtmlref='', $moreparam='', $nodbprefix=0, $morehtmlleft='', $morehtmlstatus='', $onlybanner=0, $morehtmlright='')
Show tab footer of a card.
dol_mktime($hour, $minute, $second, $month, $day, $year, $gm='auto', $check=1)
Return a timestamp date built from detailed informations (by default a local PHP server timestamp) Re...
load_fiche_titre($titre, $morehtmlright='', $picto='generic', $pictoisfullpath=0, $id='', $morecssontable='', $morehtmlcenter='')
Load a title with picto.
img_warning($titlealt='default', $moreatt='', $morecss='pictowarning')
Show warning logo.
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_print_error($db='', $error='', $errors=null)
Displays error message system with all the information to facilitate the diagnosis and the escalation...
img_object($titlealt, $picto, $moreatt='', $pictoisfullpath=false, $srconly=0, $notitle=0)
Show a picto called object_picto (generic function)
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_print_date($time, $format='', $tzoutput='auto', $outputlangs='', $encodetooutput=false)
Output date in a string format according to outputlangs (or langs if not defined).
dol_now($mode='auto')
Return date for now.
getDolGlobalInt($key, $default=0)
Return a Dolibarr global constant int value.
img_picto($titlealt, $picto, $moreatt='', $pictoisfullpath=false, $srconly=0, $notitle=0, $alt='', $morecss='', $marginleftonlyshort=2)
Show picto whatever it's its name (generic function)
dol_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.
dol_htmlcleanlastbr($stringtodecode)
This function remove all ending and br at end.
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...
GETPOST($paramname, $check='alphanohtml', $method=0, $filter=null, $options=null, $noreplace=0)
Return value of a param into GET or POST supervariable.
info_admin($text, $infoonimgalt=0, $nodiv=0, $admin='1', $morecss='hideonsmartphone', $textfordropdown='')
Show information for admin users or standard users.
setEventMessages($mesg, $mesgs, $style='mesgs', $messagekey='', $noduplicate=0)
Set event messages in dol_events session object.
get_localtax($vatrate, $local, $thirdparty_buyer="", $thirdparty_seller="", $vatnpr=0)
Return localtax rate for a particular vat, when selling a product with vat $vatrate,...
getCommonSubstitutionArray($outputlangs, $onlykey=0, $exclude=null, $object=null, $include=null)
Return array of possible common substitutions.
getDolGlobalString($key, $default='')
Return dolibarr global constant string value.
img_edit($titlealt='default', $float=0, $other='')
Show logo editer/modifier fiche.
img_info($titlealt='default')
Show info logo.
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...
invoice_rec_prepare_head($object)
Return array head with list of tabs to view object informations.
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.