dolibarr 21.0.0-alpha
price.php
Go to the documentation of this file.
1<?php
2/* Copyright (C) 2001-2007 Rodolphe Quiedeville <rodolphe@quiedeville.org>
3 * Copyright (C) 2004-2015 Laurent Destailleur <eldy@users.sourceforge.net>
4 * Copyright (C) 2005 Eric Seigne <eric.seigne@ryxeo.com>
5 * Copyright (C) 2005-2013 Regis Houssin <regis.houssin@inodbox.com>
6 * Copyright (C) 2006 Andre Cianfarani <acianfa@free.fr>
7 * Copyright (C) 2015 Marcos García <marcosgdf@gmail.com>
8 * Copyright (C) 2023 Alexandre Spangaro <aspangaro@open-dsi.fr>
9 * Copyright (C) 2024 Frédéric France <frederic.france@free.fr>
10 * Copyright (C) 2024 Mélina Joum <melina.joum@altairis.fr>
11 *
12 * This program is free software; you can redistribute it and/or modify
13 * it under the terms of the GNU General Public License as published by
14 * the Free Software Foundation; either version 3 of the License, or
15 * (at your option) any later version.
16 *
17 * This program is distributed in the hope that it will be useful,
18 * but WITHOUT ANY WARRANTY; without even the implied warranty of
19 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
20 * GNU General Public License for more details.
21 *
22 * You should have received a copy of the GNU General Public License
23 * along with this program. If not, see <https://www.gnu.org/licenses/>.
24 */
25
33// Load Dolibarr environment
34require '../main.inc.php';
35require_once DOL_DOCUMENT_ROOT.'/core/lib/product.lib.php';
36require_once DOL_DOCUMENT_ROOT.'/product/class/product.class.php';
37require_once DOL_DOCUMENT_ROOT.'/core/lib/company.lib.php';
38require_once DOL_DOCUMENT_ROOT.'/societe/class/societe.class.php';
39
40if (getDolGlobalString('PRODUIT_CUSTOMER_PRICES') || getDolGlobalString('PRODUIT_CUSTOMER_PRICES_AND_MULTIPRICES')) {
41 require_once DOL_DOCUMENT_ROOT.'/product/class/productcustomerprice.class.php';
42
43 $prodcustprice = new ProductCustomerPrice($db);
44}
45
46
47// Load translation files required by the page
48$langs->loadLangs(array("products", "companies", "bills"));
49
50
51// Get parameters
52$action = GETPOST('action', 'aZ09');
53$search_prod = GETPOST('search_prod', 'alpha');
54$cancel = GETPOST('cancel', 'alpha');
55$search_label = GETPOST('search_label', 'alpha');
56$search_price = GETPOST('search_price');
57$search_price_ttc = GETPOST('search_price_ttc');
58
59// Security check
60$socid = GETPOSTINT('socid') ? GETPOSTINT('socid') : GETPOSTINT('id');
61if ($user->socid) {
62 $socid = $user->socid;
63}
64
65// Initialize a technical object to manage hooks of page. Note that conf->hooks_modules contains an array of hook context
66$hookmanager->initHooks(array('thirdpartycustomerprice', 'globalcard'));
67
68$result = restrictedArea($user, 'societe', $socid, '&societe');
69
70// Initialize objects
71$object = new Societe($db);
72
73$error = 0;
74
75
76/*
77 * Actions
78 */
79
80$parameters = array('id' => $socid);
81$reshook = $hookmanager->executeHooks('doActions', $parameters, $object, $action); // Note that $action and $object may have been modified by some hooks
82if ($reshook < 0) {
83 setEventMessages($hookmanager->error, $hookmanager->errors, 'errors');
84}
85
86if (empty($reshook)) {
87 if (GETPOST('button_removefilter_x', 'alpha') || GETPOST('button_removefilter.x', 'alpha') || GETPOST('button_removefilter', 'alpha')) { // Both test are required to be compatible with all browsers
88 $search_prod = $search_label = $search_price = $search_price_ttc = '';
89 }
90
91 if ($action == 'add_customer_price_confirm' && !$cancel && ($user->hasRight('produit', 'creer') || $user->hasRight('service', 'creer'))) {
92 if (!(GETPOSTINT('prodid') > 0)) {
93 $error++;
94 setEventMessages($langs->trans("ErrorFieldRequired", $langs->trans("Product")), null, 'errors');
95 $action = 'add_customer_price';
96 }
97
98 if (!$error) {
99 $update_child_soc = GETPOST('updatechildprice');
100
101 // add price by customer
102 $prodcustprice->fk_soc = $socid;
103 $prodcustprice->ref_customer = GETPOST('ref_customer', 'alpha');
104 $prodcustprice->fk_product = GETPOSTINT('prodid');
105 $prodcustprice->price = price2num(GETPOST("price"), 'MU');
106 $prodcustprice->price_min = price2num(GETPOST("price_min"), 'MU');
107 $prodcustprice->price_base_type = GETPOST("price_base_type", 'alpha');
108
109 $tva_tx_txt = GETPOST('tva_tx', 'alpha'); // tva_tx can be '8.5' or '8.5*' or '8.5 (XXX)' or '8.5* (XXX)'
110
111 // We must define tva_tx, npr and local taxes
112 $vatratecode = '';
113 $tva_tx = preg_replace('/[^0-9\.].*$/', '', $tva_tx_txt); // keep remove all after the numbers and dot
114 $npr = preg_match('/\*/', $tva_tx_txt) ? 1 : 0;
115 $localtax1 = 0;
116 $localtax2 = 0;
117 $localtax1_type = '0';
118 $localtax2_type = '0';
119 // If value contains the unique code of vat line (new recommended method), we use it to find npr and local taxes
120 if (preg_match('/\‍((.*)\‍)/', $tva_tx_txt, $reg)) {
121 // We look into database using code (we can't use get_localtax() because it depends on buyer that is not known). Same in update price.
122 $vatratecode = $reg[1];
123 // Get record from code
124 $sql = "SELECT t.rowid, t.code, t.recuperableonly, t.localtax1, t.localtax2, t.localtax1_type, t.localtax2_type";
125 $sql .= " FROM ".MAIN_DB_PREFIX."c_tva as t, ".MAIN_DB_PREFIX."c_country as c";
126 $sql .= " WHERE t.fk_pays = c.rowid AND c.code = '".$db->escape($mysoc->country_code)."'";
127 $sql .= " AND t.taux = ".((float) $tva_tx)." AND t.active = 1";
128 $sql .= " AND t.code = '".$db->escape($vatratecode)."'";
129 $sql .= " AND t.entity IN (".getEntity('c_tva').")";
130 $resql = $db->query($sql);
131 if ($resql) {
132 $obj = $db->fetch_object($resql);
133 $npr = $obj->recuperableonly;
134 $localtax1 = $obj->localtax1;
135 $localtax2 = $obj->localtax2;
136 $localtax1_type = $obj->localtax1_type;
137 $localtax2_type = $obj->localtax2_type;
138 }
139 }
140
141 $prodcustprice->default_vat_code = $vatratecode;
142 $prodcustprice->tva_tx = $tva_tx;
143 $prodcustprice->recuperableonly = $npr;
144 $prodcustprice->localtax1_tx = $localtax1;
145 $prodcustprice->localtax2_tx = $localtax2;
146 $prodcustprice->localtax1_type = $localtax1_type;
147 $prodcustprice->localtax2_type = $localtax2_type;
148
149 $result = $prodcustprice->create($user, 0, $update_child_soc);
150 if ($result > 0) {
151 $extrafields->fetch_name_optionals_label("product_customer_price");
152 $extralabels = !empty($extrafields->attributes["product_customer_price"]['label']) ? $extrafields->attributes["product_customer_price"]['label'] : '';
153 $extrafield_values = $extrafields->getOptionalsFromPost("product_customer_price");
154 if (!empty($extralabels) && is_array($extralabels)) {
155 $productcustomerprice = new ProductCustomerPrice($db);
156 $res = $productcustomerprice->fetch($prodcustprice->id);
157 if ($res > 0) {
158 foreach ($extrafield_values as $key => $value) {
159 $productcustomerprice->array_options[$key] = $value;
160 }
161 $result2 = $productcustomerprice->insertExtraFields();
162 if ($result2 < 0) {
163 $prodcustprice->error = $productcustomerprice->error;
164 $prodcustprice->errors = $productcustomerprice->errors;
165 $error++;
166 }
167 }
168 }
169 }
170
171 if ($result < 0) {
172 setEventMessages($prodcustprice->error, $prodcustprice->errors, 'errors');
173 } else {
174 setEventMessages($langs->trans("Save"), null, 'mesgs');
175 }
176
177 $action = '';
178 }
179 }
180
181 if ($action == 'delete_customer_price' && ($user->hasRight('produit', 'creer') || $user->hasRight('service', 'creer'))) {
182 // Delete price by customer
183 $prodcustprice->id = GETPOSTINT('lineid');
184 $result = $prodcustprice->delete($user);
185
186 if ($result < 0) {
187 setEventMessages($prodcustprice->error, $prodcustprice->errors, 'mesgs');
188 } else {
189 setEventMessages($langs->trans('RecordDeleted'), null, 'errors');
190 }
191 $action = '';
192 }
193
194 if ($action == 'update_customer_price_confirm' && !$cancel && ($user->hasRight('produit', 'creer') || $user->hasRight('service', 'creer'))) {
195 $prodcustprice->fetch(GETPOSTINT('lineid'));
196
197 $update_child_soc = GETPOST('updatechildprice');
198
199 // update price by customer
200 $prodcustprice->ref_customer = GETPOST('ref_customer', 'alpha');
201 $prodcustprice->price = price2num(GETPOST("price"), 'MU');
202 $prodcustprice->price_min = price2num(GETPOST("price_min"), 'MU');
203 $prodcustprice->price_base_type = GETPOST("price_base_type", 'alpha');
204 $prodcustprice->tva_tx = str_replace('*', '', GETPOST("tva_tx"));
205 $prodcustprice->recuperableonly = (preg_match('/\*/', GETPOST("tva_tx")) ? 1 : 0);
206
207 $result = $prodcustprice->update($user, 0, $update_child_soc);
208 if ($result > 0) {
209 $extrafields->fetch_name_optionals_label("product_customer_price");
210 $extralabels = !empty($extrafields->attributes["product_customer_price"]['label']) ? $extrafields->attributes["product_customer_price"]['label'] : '';
211 $extrafield_values = $extrafields->getOptionalsFromPost("product_customer_price");
212 if (!empty($extralabels) && is_array($extralabels)) {
213 $productcustomerprice = new ProductCustomerPrice($db);
214 $res = $productcustomerprice->fetch($prodcustprice->id);
215 if ($res > 0) {
216 foreach ($extrafield_values as $key => $value) {
217 $productcustomerprice->array_options[$key] = $value;
218 }
219 $result2 = $productcustomerprice->insertExtraFields();
220 if ($result2 < 0) {
221 $prodcustprice->error = $productcustomerprice->error;
222 $prodcustprice->errors = $productcustomerprice->errors;
223 $error++;
224 }
225 }
226 }
227 }
228 if ($result < 0) {
229 setEventMessages($prodcustprice->error, $prodcustprice->errors, 'errors');
230 } else {
231 setEventMessages($langs->trans("Save"), null, 'mesgs');
232 }
233
234 $action = '';
235 }
236}
237
238
239/*
240 * View
241 */
242
243$form = new Form($db);
244
245$object = new Societe($db);
246
247$result = $object->fetch($socid);
248llxHeader("", $langs->trans("ThirdParty").'-'.$langs->trans('PriceByCustomer'));
249
250$head = societe_prepare_head($object);
251
252print dol_get_fiche_head($head, 'price', $langs->trans("ThirdParty"), -1, 'company');
253
254$linkback = '<a href="'.DOL_URL_ROOT.'/societe/list.php?restore_lastsearch_values=1">'.$langs->trans("BackToList").'</a>';
255
256dol_banner_tab($object, 'socid', $linkback, ($user->socid ? 0 : 1), 'rowid', 'nom');
257
258print '<div class="fichecenter">';
259
260print '<div class="underbanner clearboth"></div>';
261print '<table class="border centpercent tableforfield">';
262
263// Type Prospect/Customer/Supplier
264print '<tr><td class="titlefield">'.$langs->trans('NatureOfThirdParty').'</td><td>';
265print $object->getTypeUrl(1);
266print '</td></tr>';
267
268if (getDolGlobalString('SOCIETE_USEPREFIX')) { // Old not used prefix field
269 print '<tr><td class="titlefield">'.$langs->trans('Prefix').'</td><td colspan="3">'.$object->prefix_comm.'</td></tr>';
270}
271
272if ($object->client) {
273 print '<tr><td class="titlefield">';
274 print $langs->trans('CustomerCode').'</td><td colspan="3">';
275 print $object->code_client;
276 $tmpcheck = $object->check_codeclient();
277 if ($tmpcheck != 0 && $tmpcheck != -5) {
278 print ' <span class="error">('.$langs->trans("WrongCustomerCode").')</span>';
279 }
280 print '</td></tr>';
281}
282
283if ($object->fournisseur) {
284 print '<tr><td class="titlefield">';
285 print $langs->trans('SupplierCode').'</td><td colspan="3">';
286 print $object->code_fournisseur;
287 $tmpcheck = $object->check_codefournisseur();
288 if ($tmpcheck != 0 && $tmpcheck != -5) {
289 print ' <span class="error">('.$langs->trans("WrongSupplierCode").')</span>';
290 }
291 print '</td></tr>';
292}
293
294print '</table>';
295
296print '</div>';
297
298print dol_get_fiche_end();
299
300
301
302if (getDolGlobalString('PRODUIT_CUSTOMER_PRICES') || getDolGlobalString('PRODUIT_CUSTOMER_PRICES_AND_MULTIPRICES')) {
303 $prodcustprice = new ProductCustomerPrice($db);
304
305 $sortfield = GETPOST('sortfield', 'aZ09comma');
306 $sortorder = GETPOST('sortorder', 'aZ09comma');
307 $limit = GETPOSTINT('limit') ? GETPOSTINT('limit') : $conf->liste_limit;
308 $page = GETPOSTISSET('pageplusone') ? (GETPOSTINT('pageplusone') - 1) : GETPOSTINT("page");
309 if (empty($page) || $page == -1) {
310 $page = 0;
311 } // If $page is not defined, or '' or -1
312 $offset = $limit * $page;
313 $pageprev = $page - 1;
314 $pagenext = $page + 1;
315 if (!$sortorder) {
316 $sortorder = "ASC";
317 }
318 if (!$sortfield) {
319 $sortfield = "soc.nom";
320 }
321
322 // Build filter to display only concerned lines
323 $filter = array(
324 't.fk_soc' => $object->id
325 );
326
327 if (!empty($search_prod)) {
328 $filter ['prod.ref'] = $search_prod;
329 }
330
331 if (!empty($search_label)) {
332 $filter ['prod.label'] = $search_label;
333 }
334
335 if (!empty($search_price)) {
336 $filter ['t.price'] = $search_price;
337 }
338
339 if (!empty($search_price_ttc)) {
340 $filter ['t.price_ttc'] = $search_price_ttc;
341 }
342
343 if ($action == 'add_customer_price') {
344 // Create mode
345
346 print '<br>';
347 print '<!-- Price by customer -->'."\n";
348
349 print load_fiche_titre($langs->trans('PriceByCustomer'));
350
351 print '<form action="'.$_SERVER["PHP_SELF"].'?socid='.$object->id.'" method="POST">';
352 print '<input type="hidden" name="token" value="'.newToken().'">';
353 print '<input type="hidden" name="action" value="add_customer_price_confirm">';
354 print '<input type="hidden" name="sortfield" value="'.$sortfield.'">';
355 print '<input type="hidden" name="sortorder" value="'.$sortorder.'">';
356 print '<input type="hidden" name="socid" value="'.$object->id.'">';
357 print '<table class="border centpercent">';
358 print '<tr>';
359 print '<td>'.$langs->trans('Product').'</td>';
360 print '<td>';
361 $form->select_produits('', 'prodid', '', 0);
362 print '</td>';
363 print '</tr>';
364
365 // Ref. Customer
366 print '<tr><td>'.$langs->trans('RefCustomer').'</td>';
367 print '<td><input name="ref_customer" size="12"></td></tr>';
368
369 // VAT
370 print '<tr><td>'.$langs->trans("VATRate").'</td><td>';
371 print $form->load_tva("tva_tx", GETPOST("tva_tx", "alpha"), $mysoc, '', $object->id, 0, '', false, 1);
372 print '</td></tr>';
373
374 // Price base
375 print '<tr><td width="15%">';
376 print $langs->trans('PriceBase');
377 print '</td>';
378 print '<td>';
379 print $form->selectPriceBaseType(GETPOST("price_base_type", "aZ09"), "price_base_type");
380 print '</td>';
381 print '</tr>';
382
383 // Price
384 print '<tr><td width="20%">';
385 $text = $langs->trans('SellingPrice');
386 print $form->textwithpicto($text, $langs->trans("PrecisionUnitIsLimitedToXDecimals", getDolGlobalString('MAIN_MAX_DECIMALS_UNIT')), 1, 1);
387 print '</td><td>';
388 print '<input name="price" size="10" value="'.GETPOSTINT('price').'">';
389 print '</td></tr>';
390
391 // Price minimum
392 print '<tr><td>';
393 $text = $langs->trans('MinPrice');
394 print $form->textwithpicto($text, $langs->trans("PrecisionUnitIsLimitedToXDecimals", getDolGlobalString('MAIN_MAX_DECIMALS_UNIT')), 1, 1);
395 print '<td><input name="price_min" size="10" value="'.GETPOSTINT('price_min').'">';
396 print '</td></tr>';
397
398 // Update all child soc
399 print '<tr><td width="15%">';
400 print $langs->trans('ForceUpdateChildPriceSoc');
401 print '</td>';
402 print '<td>';
403 print '<input type="checkbox" name="updatechildprice" value="1"/>';
404 print '</td>';
405 print '</tr>';
406
407 // Extrafields
408 $extrafields->fetch_name_optionals_label("product_customer_price");
409 $extralabels = !empty($extrafields->attributes["product_customer_price"]['label']) ? $extrafields->attributes["product_customer_price"]['label'] : '';
410 $extrafield_values = $extrafields->getOptionalsFromPost("product_customer_price");
411 if (!empty($extralabels)) {
412 if (empty($prodcustprice->id)) {
413 foreach ($extralabels as $key => $value) {
414 if (!empty($extrafields->attributes["product_customer_price"]['list'][$key]) && ($extrafields->attributes["product_customer_price"]['list'][$key] == 1 || $extrafields->attributes["product_customer_price"]['list'][$key] == 3 || ($action == "add_customer_price" && $extrafields->attributes["product_customer_price"]['list'][$key] == 4))) {
415 if (!empty($extrafields->attributes["product_customer_price"]['langfile'][$key])) {
416 $langs->load($extrafields->attributes["product_customer_price"]['langfile'][$key]);
417 }
418
419 print '<tr><td'.($extrafields->attributes["product_customer_price"]['required'][$key] ? ' class="fieldrequired"' : '').'>';
420 if (!empty($extrafields->attributes["product_customer_price"]['help'][$key])) {
421 print $form->textwithpicto($langs->trans($value), $langs->trans($extrafields->attributes["product_customer_price"]['help'][$key]));
422 } else {
423 print $langs->trans($value);
424 }
425 print '</td><td>'.$extrafields->showInputField($key, GETPOSTISSET('options_'.$key) ? $extrafield_values['options_'.$key] : '', '', '', '', '', 0, 'product_customer_price').'</td></tr>';
426 }
427 }
428 }
429 }
430
431 print '</table>';
432
433 print $form->buttonsSaveCancel();
434
435 print '</form>';
436 } elseif ($action == 'edit_customer_price') {
437 // Edit mode
438
439 print load_fiche_titre($langs->trans('PriceByCustomer'));
440
441 $result = $prodcustprice->fetch(GETPOSTINT('lineid'));
442
443 if ($result <= 0) {
444 setEventMessages($prodcustprice->error, $prodcustprice->errors, 'errors');
445 } else {
446 print '<form action="'.$_SERVER["PHP_SELF"].'?socid='.$object->id.'" method="POST">';
447 print '<input type="hidden" name="token" value="'.newToken().'">';
448 print '<input type="hidden" name="action" value="update_customer_price_confirm">';
449 print '<input type="hidden" name="lineid" value="'.$prodcustprice->id.'">';
450 print '<table class="border centpercent">';
451 print '<tr>';
452 print '<td>'.$langs->trans('Product').'</td>';
453 $staticprod = new Product($db);
454 $staticprod->fetch($prodcustprice->fk_product);
455 print "<td>".$staticprod->getNomUrl(1)."</td>";
456 print '</tr>';
457
458 // Ref. Customer
459 print '<tr><td>'.$langs->trans('RefCustomer').'</td>';
460 print '<td><input name="ref_customer" size="12" value="'.dol_escape_htmltag($prodcustprice->ref_customer).'"></td></tr>';
461
462 // VAT
463 print '<tr><td>'.$langs->trans("VATRate").'</td><td>';
464 print $form->load_tva("tva_tx", $prodcustprice->tva_tx, $mysoc, '', $staticprod->id, $prodcustprice->recuperableonly);
465 print '</td></tr>';
466
467 // Price base
468 print '<tr><td width="15%">';
469 print $langs->trans('PriceBase');
470 print '</td>';
471 print '<td>';
472 print $form->selectPriceBaseType($prodcustprice->price_base_type, "price_base_type");
473 print '</td>';
474 print '</tr>';
475
476 // Price
477 print '<tr><td>';
478 $text = $langs->trans('SellingPrice');
479 print $form->textwithpicto($text, $langs->trans("PrecisionUnitIsLimitedToXDecimals", getDolGlobalString('MAIN_MAX_DECIMALS_UNIT')), 1, 1);
480 print '</td><td>';
481 if ($prodcustprice->price_base_type == 'TTC') {
482 print '<input name="price" size="10" value="'.price($prodcustprice->price_ttc).'">';
483 } else {
484 print '<input name="price" size="10" value="'.price($prodcustprice->price).'">';
485 }
486 print '</td></tr>';
487
488 // Price minimum
489 print '<tr><td>';
490 $text = $langs->trans('MinPrice');
491 print $form->textwithpicto($text, $langs->trans("PrecisionUnitIsLimitedToXDecimals", getDolGlobalString('MAIN_MAX_DECIMALS_UNIT')), 1, 1);
492 print '</td><td>';
493 if ($prodcustprice->price_base_type == 'TTC') {
494 print '<input name="price_min" size="10" value="'.price($prodcustprice->price_min_ttc).'">';
495 } else {
496 print '<input name="price_min" size="10" value="'.price($prodcustprice->price_min).'">';
497 }
498 print '</td></tr>';
499
500 // Update all child soc
501 print '<tr><td>';
502 print $langs->trans('ForceUpdateChildPriceSoc');
503 print '</td>';
504 print '<td>';
505 print '<input type="checkbox" name="updatechildprice" value="1">';
506 print '</td>';
507 print '</tr>';
508
509 // Extrafields
510 $extrafields->fetch_name_optionals_label("product_customer_price");
511 $extralabels = !empty($extrafields->attributes["product_customer_price"]['label']) ? $extrafields->attributes["product_customer_price"]['label'] : '';
512 $extrafield_values = $extrafields->getOptionalsFromPost("product_customer_price");
513 if (!empty($extralabels)) {
514 if (empty($object->id)) {
515 foreach ($extralabels as $key => $value) {
516 if (!empty($extrafields->attributes["product_customer_price"]['list'][$key]) && ($extrafields->attributes["product_customer_price"]['list'][$key] == 1 || $extrafields->attributes["product_customer_price"]['list'][$key] == 3 || ($action == "edit_price" && $extrafields->attributes["product_customer_price"]['list'][$key] == 4))) {
517 if (!empty($extrafields->attributes["product_customer_price"]['langfile'][$key])) {
518 $langs->load($extrafields->attributes["product_customer_price"]['langfile'][$key]);
519 }
520
521 print '<tr><td'.($extrafields->attributes["product_customer_price"]['required'][$key] ? ' class="fieldrequired"' : '').'>';
522 if (!empty($extrafields->attributes["product_customer_price"]['help'][$key])) {
523 print $form->textwithpicto($langs->trans($value), $langs->trans($extrafields->attributes["product_customer_price"]['help'][$key]));
524 } else {
525 print $langs->trans($value);
526 }
527 print '</td><td>'.$extrafields->showInputField($key, GETPOSTISSET('options_'.$key) ? $extrafield_values['options_'.$key] : '', '', '', '', '', 0, 'product_customer_price').'</td></tr>';
528 }
529 }
530 } else {
531 $sql = "SELECT";
532 $sql .= " fk_object";
533 foreach ($extralabels as $key => $value) {
534 $sql .= ", ".$key;
535 }
536 $sql .= " FROM ".MAIN_DB_PREFIX."product_customer_price_extrafields";
537 $sql .= " WHERE fk_object = ".((int) $prodcustprice->id);
538 $resql = $db->query($sql);
539 if ($resql) {
540 $obj = $db->fetch_object($resql);
541 foreach ($extralabels as $key => $value) {
542 if (!empty($extrafields->attributes["product_customer_price"]['list'][$key]) && ($extrafields->attributes["product_customer_price"]['list'][$key] == 1 || $extrafields->attributes["product_customer_price"]['list'][$key] == 3 || ($action == "edit_price" && $extrafields->attributes["product_customer_price"]['list'][$key] == 4))) {
543 if (!empty($extrafields->attributes["product_customer_price"]['langfile'][$key])) {
544 $langs->load($extrafields->attributes["product_customer_price"]['langfile'][$key]);
545 }
546
547 print '<tr><td'.($extrafields->attributes["product_customer_price"]['required'][$key] ? ' class="fieldrequired"' : '').'>';
548 if (!empty($extrafields->attributes["product_customer_price"]['help'][$key])) {
549 print $form->textwithpicto($langs->trans($value), $langs->trans($extrafields->attributes["product_customer_price"]['help'][$key]));
550 } else {
551 print $langs->trans($value);
552 }
553 print '</td><td>'.$extrafields->showInputField($key, GETPOSTISSET('options_'.$key) ? $extrafield_values['options_'.$key] : $obj->{$key}, '', '', '', '', 0, 'product_customer_price');
554
555 print '</td></tr>';
556 }
557 }
558 $db->free($resql);
559 }
560 }
561 }
562
563 print '</table>';
564
565 print $form->buttonsSaveCancel();
566
567 print '</form>';
568 }
569 } elseif ($action == 'showlog_customer_price') {
570 print '<br>';
571 print '<!-- showlog_customer_price -->'."\n";
572
573 $filter = array(
574 't.fk_product' => GETPOSTINT('prodid'),
575 't.fk_soc' => $socid
576 );
577
578 // Count total nb of records
579 $nbtotalofrecords = '';
580 $result = $prodcustprice->fetchAllLog($sortorder, $sortfield, $conf->liste_limit, $offset, $filter);
581 if ($result < 0) {
582 setEventMessages($prodcustprice->error, $prodcustprice->errors, 'errors');
583 } else {
584 if (!getDolGlobalInt('MAIN_DISABLE_FULL_SCANLIST')) {
585 $nbtotalofrecords = $result;
586 }
587 }
588
589 $option = '&socid='.GETPOSTINT('socid').'&prodid='.GETPOSTINT('prodid');
590
591 // @phan-suppress-next-line PhanPluginSuspiciousParamOrder
592 print_barre_liste($langs->trans('PriceByCustomerLog'), $page, $_SERVER ['PHP_SELF'], $option, $sortfield, $sortorder, '', count($prodcustprice->lines), $nbtotalofrecords);
593
594 if (count($prodcustprice->lines) > 0) {
595 print '<form action="'.$_SERVER["PHP_SELF"].'?id='.$object->id.'" method="POST">';
596 print '<input type="hidden" name="token" value="'.newToken().'">';
597 print '<input type="hidden" name="id" value="'.$object->id.'">';
598
599 print '<table class="noborder centpercent">';
600
601 print '<tr class="liste_titre">';
602 print '<td>'.$langs->trans("Product").'</td>';
603 print '<td>'.$langs->trans('RefCustomer').'</td>';
604 print '<td>'.$langs->trans("AppliedPricesFrom").'</td>';
605 print '<td class="center">'.$langs->trans("PriceBase").'</td>';
606 print '<td class="right">'.$langs->trans("VAT").'</td>';
607 print '<td class="right">'.$langs->trans("HT").'</td>';
608 print '<td class="right">'.$langs->trans("TTC").'</td>';
609 print '<td class="right">'.$langs->trans("MinPrice").' '.$langs->trans("HT").'</td>';
610 print '<td class="right">'.$langs->trans("MinPrice").' '.$langs->trans("TTC").'</td>';
611 print '<td class="right">'.$langs->trans("ChangedBy").'</td>';
612 print '<td></td>';
613 print '</tr>';
614
615 foreach ($prodcustprice->lines as $line) {
616 $staticprod = new Product($db);
617 $staticprod->fetch($line->fk_product);
618
619 $userstatic = new User($db);
620 $userstatic->fetch($line->fk_user);
621
622 print '<tr class="oddeven">';
623
624 print "<td>".$staticprod->getNomUrl(1)."</td>";
625 print '<td>'.$line->ref_customer.'</td>';
626 print "<td>".dol_print_date($line->datec, "dayhour")."</td>";
627
628 print '<td class="center">'.$langs->trans($line->price_base_type)."</td>";
629 print '<td class="right">'.vatrate($line->tva_tx, true, $line->recuperableonly)."</td>";
630 print '<td class="right">'.price($line->price)."</td>";
631 print '<td class="right">'.price($line->price_ttc)."</td>";
632 print '<td class="right">'.price($line->price_min).'</td>';
633 print '<td class="right">'.price($line->price_min_ttc).'</td>';
634
635 // User
636 print '<td class="right">';
637 print $userstatic->getNomUrl(-1);
638 print '</td>';
639 print '<td></td>';
640 }
641 print "</table>";
642 } else {
643 print $langs->trans('None');
644 }
645
646 print "\n".'<div class="tabsAction">'."\n";
647 print '<div class="inline-block divButAction"><a class="butAction" href="'.$_SERVER["PHP_SELF"].'?socid='.$object->id.'">'.$langs->trans("Ok").'</a></div>';
648 print "\n</div><br>\n";
649 } else {
650 // View mode
651
652 /*
653 * Action bar
654 */
655 print "\n".'<div class="tabsAction">'."\n";
656
657 if ($user->hasRight('produit', 'creer') || $user->hasRight('service', 'creer')) {
658 print '<div class="inline-block divButAction"><a class="butAction" href="'.$_SERVER["PHP_SELF"].'?action=add_customer_price&token='.newToken().'&socid='.$object->id.'">'.$langs->trans("AddCustomerPrice").'</a></div>';
659 }
660 print "\n</div>\n";
661
662
663 $arrayfields = array();
664 foreach ($prodcustprice->fields as $key => $val) {
665 // If $val['visible']==0, then we never show the field
666 if (!empty($val['visible'])) {
667 $visible = (int) dol_eval((string) $val['visible'], 1, 1, '1');
668 $arrayfields['t.'.$key] = array(
669 'label' => $val['label'],
670 'checked' => (($visible < 0) ? 0 : 1),
671 'enabled' => (abs($visible) != 3 && (bool) dol_eval($val['enabled'], 1)),
672 'position' => $val['position'],
673 'help' => isset($val['help']) ? $val['help'] : ''
674 );
675 }
676 }
677 // fetch optionals attributes and labels
678 $extrafields->fetch_name_optionals_label("product_customer_price");
679 if ($extrafields->attributes["product_customer_price"] && array_key_exists('label', $extrafields->attributes["product_customer_price"])) {
680 $extralabels = $extrafields->attributes["product_customer_price"]['label'];
681
682 if (!empty($extralabels)) {
683 foreach ($extralabels as $key => $value) {
684 // Show field if not hidden
685 if (!empty($extrafields->attributes["product_customer_price"]['list'][$key]) && $extrafields->attributes["product_customer_price"]['list'][$key] != 3) {
686 $extratitle = $langs->trans($value);
687 if (!empty($val['visible'])) {
688 $visible = (int) dol_eval((string) $val['visible'], 1, 1, '1');
689 $arrayfields['ef.' . $key] = array(
690 'label' => $extratitle,
691 'checked' => (($visible < 0) ? 0 : 1),
692 'position' => (int) $extrafields->attributes['product_customer_price']['pos'][$key],
693 'langfile' => $extrafields->attributes["product_customer_price"]['langfile'][$key],
694 'help' => $extrafields->attributes["product_customer_price"]['help'][$key]
695 );
696 }
697 }
698 }
699 }
700 }
701
702 $arrayfields = dol_sort_array($arrayfields, 'position');
703
704 // Count total nb of records
705 $nbtotalofrecords = '';
706 if (!getDolGlobalInt('MAIN_DISABLE_FULL_SCANLIST')) {
707 $nbtotalofrecords = $prodcustprice->fetchAll('', '', 0, 0, $filter);
708 }
709
710 $result = $prodcustprice->fetchAll($sortorder, $sortfield, $conf->liste_limit, $offset, $filter);
711 if ($result < 0) {
712 setEventMessages($prodcustprice->error, $prodcustprice->errors, 'errors');
713 }
714
715 $option = '&search_prod='.$search_prod.'&id='.$object->id.'&label='.$search_label.'&price='.$search_price.'&price_ttc='.$search_price_ttc;
716
717 print '<!-- view specific price for each product -->'."\n";
718
719 // @phan-suppress-next-line PhanPluginSuspiciousParamOrder
720 print_barre_liste($langs->trans('PriceForEachProduct'), $page, $_SERVER['PHP_SELF'], $option, $sortfield, $sortorder, '', count($prodcustprice->lines), $nbtotalofrecords, '');
721
722 print '<form action="'.$_SERVER["PHP_SELF"].'?id='.$object->id.'" method="POST">';
723 print '<input type="hidden" name="token" value="'.newToken().'">';
724 print '<input type="hidden" name="id" value="'.$object->id.'">';
725 if (!empty($sortfield)) {
726 print '<input type="hidden" name="sortfield" value="'.$sortfield.'"/>';
727 }
728 if (!empty($sortorder)) {
729 print '<input type="hidden" name="sortorder" value="'.$sortorder.'"/>';
730 }
731 print '<div class="div-table-responsive-no-min">';
732 print '<table class="noborder centpercent liste">';
733
734 $param = 'socid='.$object->id.'&';
735 if ($search_prod) {
736 $param .= '&search_prod='.urlencode($search_prod);
737 }
738 if ($search_label) {
739 $param .= '&search_label='.urlencode($search_label);
740 }
741 if ($search_price) {
742 $param .= '&search_price='.urlencode($search_price);
743 }
744 if ($search_price) {
745 $param .= '&search_price='.urlencode($search_price);
746 }
747 if ($search_price_ttc) {
748 $param .= '&search_price_ttc='.urlencode($search_price_ttc);
749 }
750
751 print '<tr class="liste_titre">';
752 foreach ($prodcustprice->fields as $key => $val) {
753 if (!empty($arrayfields['t.'.$key]['checked'])) {
754 print getTitleFieldOfList($arrayfields['t.'.$key]['label'], 0, $_SERVER['PHP_SELF'], $key, '', $param, '', $sortfield, $sortorder)."\n";
755 }
756 }
757 foreach ($extralabels as $key => $val) {
758 if (!empty($arrayfields['ef.'.$key]['checked'])) {
759 print getTitleFieldOfList($arrayfields['ef.'.$key]['label'], 0, $_SERVER['PHP_SELF'], $key, '', $param, '', $sortfield, $sortorder)."\n";
760 }
761 }
762 print '<td></td>';
763 print '</tr>';
764
765 if (count($prodcustprice->lines) > 0 || $search_prod) {
766 print '<tr class="liste_titre">';
767 print '<td class="liste_titre"><input type="text" class="flat width75" name="search_prod" value="'.$search_prod.'"></td>';
768 print '<td class="liste_titre" ><input type="text" class="flat width75" name="search_label" value="'.$search_label.'"></td>';
769 print '<td class="liste_titre"></td>';
770 print '<td class="liste_titre"></td>';
771 print '<td class="liste_titre"></td>';
772 print '<td class="liste_titre"></td>';
773 print '<td class="liste_titre left"><input type="text" class="flat width75" name="search_price" value="'.$search_price.'"></td>';
774 print '<td class="liste_titre left"><input type="text" class="flat width75" name="search_price_ttc" value="'.$search_price_ttc.'"></td>';
775 print '<td class="liste_titre"></td>';
776 print '<td class="liste_titre"></td>';
777 print '<td class="liste_titre"></td>';
778 print '<td class="liste_titre"></td>';
779 if (!empty($extralabels)) {
780 foreach ($extralabels as $key) {
781 print '<td class="right"></td>';
782 }
783 }
784 // Print the search button
785 print '<td class="liste_titre maxwidthsearch">';
786 $searchpicto = $form->showFilterAndCheckAddButtons(0);
787 print $searchpicto;
788 print '</td>';
789 print '</tr>';
790 }
791
792 if (count($prodcustprice->lines) > 0) {
793 foreach ($prodcustprice->lines as $line) {
794 $staticprod = new Product($db);
795 $staticprod->fetch($line->fk_product);
796
797 $userstatic = new User($db);
798 $userstatic->fetch($line->fk_user);
799
800 print '<tr class="oddeven">';
801
802 print '<td class="left">'.$staticprod->getNomUrl(1)."</td>";
803 print '<td class="left">'.$staticprod->label."</td>";
804 print '<td class="left">'.$line->ref_customer.'</td>';
805 print '<td class="left">'.dol_print_date($line->datec, "dayhour")."</td>";
806 print '<td class="left">'.$langs->trans($line->price_base_type)."</td>";
807 print '<td class="left">'.vatrate($line->tva_tx.($line->default_vat_code ? ' ('.$line->default_vat_code.')' : ''), true, $line->recuperableonly)."</td>";
808 print '<td class="left">'.price($line->price)."</td>";
809 print '<td class="left">'.price($line->price_ttc)."</td>";
810 print '<td class="left">'.price($line->price_min).'</td>';
811 print '<td class="left">'.price($line->price_min_ttc).'</td>';
812 print '<td class="left">'.$line->price_label.'</td>';
813 // User
814 print '<td class="left">';
815 print $userstatic->getNomUrl(-1);
816 print '</td>';
817 // Extrafields
818 $extrafields->fetch_name_optionals_label("product_customer_price");
819 $extralabels = $extrafields->attributes["product_customer_price"]['label'];
820 if (!empty($extralabels)) {
821 $sql = "SELECT";
822 $sql .= " fk_object";
823 foreach ($extralabels as $key => $value) {
824 $sql .= ", ".$key;
825 }
826 $sql .= " FROM ".MAIN_DB_PREFIX."product_customer_price_extrafields";
827 $sql .= " WHERE fk_object = ".((int) $line->id);
828 $resql = $db->query($sql);
829 if ($resql) {
830 if ($db->num_rows($resql) != 1) {
831 foreach ($extralabels as $key => $value) {
832 if (!empty($extrafields->attributes["product_customer_price"]['list'][$key]) && $extrafields->attributes["product_customer_price"]['list'][$key] != 3) {
833 print "<td></td>";
834 }
835 }
836 } else {
837 $obj = $db->fetch_object($resql);
838 foreach ($extralabels as $key => $value) {
839 if (!empty($extrafields->attributes["product_customer_price"]['list'][$key]) && $extrafields->attributes["product_customer_price"]['list'][$key] != 3) {
840 print '<td align="right">'.$extrafields->showOutputField($key, $obj->{$key}, '', 'product_customer_price')."</td>";
841 }
842 }
843 }
844 $db->free($resql);
845 }
846 }
847 // Action
848 if ($user->hasRight('produit', 'creer') || $user->hasRight('service', 'creer')) {
849 print '<td class="right nowraponall">';
850 print '<a class="paddingleftonly paddingrightonly" href="'.$_SERVER["PHP_SELF"].'?action=showlog_customer_price&token='.newToken().'&socid='.$object->id.'&prodid='.$line->fk_product.'">';
851 print img_info();
852 print '</a>';
853 print ' ';
854 print '<a class="editfielda paddingleftonly paddingrightonly" href="'.$_SERVER["PHP_SELF"].'?action=edit_customer_price&token='.newToken().'&socid='.$object->id.'&lineid='.$line->id.'">';
855 print img_edit('default', 0, 'style="vertical-align: middle;"');
856 print '</a>';
857 print ' ';
858 print '<a class="paddingleftonly paddingrightonly" href="'.$_SERVER["PHP_SELF"].'?action=delete_customer_price&token='.newToken().'&socid='.$object->id.'&lineid='.$line->id.'">';
859 print img_delete('default', 'style="vertical-align: middle;"');
860 print '</a>';
861 print '</td>';
862 }
863
864 print "</tr>\n";
865 }
866 } else {
867 $colspan = 10;
868 if ($user->hasRight('produit', 'supprimer') || $user->hasRight('service', 'supprimer')) {
869 $colspan += 1;
870 }
871 print '<tr class="oddeven"><td colspan="'.$colspan.'">'.$langs->trans('None').'</td></tr>';
872 }
873
874 print "</table>";
875 print '</div>';
876
877 print "</form>";
878 }
879}
880
881// End of page
882llxFooter();
883$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($head='', $title='', $help_url='', $target='', $disablejs=0, $disablehead=0, $arrayofjs='', $arrayofcss='', $morequerystring='', $morecssonbody='', $replacemainareaby='', $disablenofollow=0, $disablenoindex=0)
Empty header.
Definition wrapper.php:70
Class to manage generation of HTML components Only common components must be here.
File of class to manage predefined price products or services by customer.
Class to manage products or services.
Class to manage third parties objects (customers, suppliers, prospects...)
Class to manage Dolibarr users.
societe_prepare_head(Societe $object)
Return array of tabs to used on pages for third parties cards.
llxFooter()
Footer empty.
Definition document.php:107
load_fiche_titre($title, $morehtmlright='', $picto='generic', $pictoisfullpath=0, $id='', $morecssontable='', $morehtmlcenter='')
Load a title with picto.
setEventMessages($mesg, $mesgs, $style='mesgs', $messagekey='', $noduplicate=0, $attop=0)
Set event messages in dol_events session object.
print_barre_liste($title, $page, $file, $options='', $sortfield='', $sortorder='', $morehtmlcenter='', $num=-1, $totalnboflines='', $picto='generic', $pictoisfullpath=0, $morehtmlright='', $morecss='', $limit=-1, $selectlimitsuffix=0, $hidenavigation=0, $pagenavastextinput=0, $morehtmlrightbeforearrow='')
Print a title with navigation controls for pagination.
img_delete($titlealt='default', $other='class="pictodelete"', $morecss='')
Show delete logo.
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.
dol_eval($s, $returnvalue=1, $hideerrors=1, $onlysimplestring='1')
Replace eval function to add more security.
getDolGlobalInt($key, $default=0)
Return a Dolibarr global constant int value.
dol_sort_array(&$array, $index, $order='asc', $natsort=0, $case_sensitive=0, $keepindex=0)
Advanced sort array by the value of a given key, which produces ascending (default) or descending out...
newToken()
Return the value of token currently saved into session with name 'newtoken'.
getTitleFieldOfList($name, $thead=0, $file="", $field="", $begin="", $moreparam="", $moreattrib="", $sortfield="", $sortorder="", $prefix="", $disablesortlink=0, $tooltip='', $forcenowrapcolumntitle=0)
Get title line of an array.
GETPOST($paramname, $check='alphanohtml', $method=0, $filter=null, $options=null, $noreplace=0)
Return value of a param into GET or POST supervariable.
getDolGlobalString($key, $default='')
Return a Dolibarr global constant string value.
img_edit($titlealt='default', $float=0, $other='')
Show logo edit/modify fiche.
img_info($titlealt='default')
Show info logo.
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.