40require
'../main.inc.php';
41require_once DOL_DOCUMENT_ROOT.
'/core/lib/product.lib.php';
42require_once DOL_DOCUMENT_ROOT.
'/core/lib/price.lib.php';
43require_once DOL_DOCUMENT_ROOT.
'/product/class/product.class.php';
44require_once DOL_DOCUMENT_ROOT.
'/product/dynamic_price/class/price_expression.class.php';
45require_once DOL_DOCUMENT_ROOT.
'/product/dynamic_price/class/price_parser.class.php';
46require_once DOL_DOCUMENT_ROOT.
'/core/class/extrafields.class.php';
59 require_once DOL_DOCUMENT_ROOT.
'/product/class/productcustomerprice.class.php';
65$langs->loadLangs(array(
'products',
'bills',
'companies',
'other'));
72$action =
GETPOST(
'action',
'aZ09');
73$cancel =
GETPOST(
'cancel',
'alpha');
76$search_soc =
GETPOST(
'search_soc');
79$fieldvalue = (!empty($id) ?
$id : (!empty($ref) ? $ref :
''));
80$fieldtype = (!empty($ref) ?
'ref' :
'rowid');
82 $socid = $user->socid;
86if ($id > 0 || !empty($ref)) {
94 $conf->global->PRODUIT_MULTIPRICES_LIMIT = 5;
98$hookmanager->initHooks(array(
'productpricecard',
'globalcard'));
101 if (
$object->type == $object::TYPE_PRODUCT) {
104 if (
$object->type == $object::TYPE_SERVICE) {
108 restrictedArea($user,
'produit|service', $fieldvalue,
'product&product',
'',
'', $fieldtype);
111$maxpricesupplier = 0;
114 $permissiontoadd =
$object->getRights()->creer;
116 $permissiontoadd = ($user->hasRight(
'produit',
'creer') || $user->hasRight(
'service',
'creer'));
128$parameters = array(
'id' => $id,
'ref' => $ref);
129$reshook = $hookmanager->executeHooks(
'doActions', $parameters, $object, $action);
134if (empty($reshook)) {
135 if (
GETPOST(
'button_removefilter_x',
'alpha') ||
GETPOST(
'button_removefilter.x',
'alpha') ||
GETPOST(
'button_removefilter',
'alpha')) {
139 if ($action ==
'setlabelsellingprice' && $user->admin) {
140 require_once DOL_DOCUMENT_ROOT.
'/core/lib/admin.lib.php';
141 $keyforlabel =
'PRODUIT_MULTIPRICES_LABEL'.GETPOST(
'pricelevel');
146 if (($action ==
'update_vat') && !$cancel && $permissiontoadd) {
147 $tva_tx_txt =
GETPOST(
'tva_tx',
'alpha');
149 $price_label =
GETPOST(
'price_label',
'alpha');
152 $tva_tx = $tva_tx_txt;
155 if (preg_match(
'/\((.*)\)/', $tva_tx_txt, $reg)) {
156 $vatratecode = $reg[1];
157 $tva_tx = preg_replace(
'/\s*\(.*\)/',
'', $tva_tx_txt);
160 $tva_tx =
price2num(preg_replace(
'/\*/',
'', $tva_tx));
161 $npr = preg_match(
'/\*/', $tva_tx_txt) ? 1 : 0;
164 $localtax1_type =
'0';
165 $localtax2_type =
'0';
168 if (preg_match(
'/\((.*)\)/', $tva_tx_txt, $reg)) {
170 $vatratecode = $reg[1];
172 $sql =
"SELECT t.rowid, t.type_vat, t.code, t.recuperableonly, t.localtax1, t.localtax2, t.localtax1_type, t.localtax2_type";
173 $sql .=
" FROM ".MAIN_DB_PREFIX.
"c_tva as t, ".MAIN_DB_PREFIX.
"c_country as c";
174 $sql .=
" WHERE t.fk_pays = c.rowid AND c.code = '".$db->escape(
$mysoc->country_code).
"'";
175 $sql .=
" AND t.taux = ".((float) $tva_tx).
" AND t.active = 1";
176 $sql .=
" AND t.code = '".$db->escape($vatratecode).
"'";
177 $sql .=
" AND t.type_vat IN (0, 1)";
178 $sql .=
" AND t.entity IN (".getEntity(
'c_tva').
")";
179 $resql = $db->query($sql);
181 $obj = $db->fetch_object($resql);
183 $npr = $obj->recuperableonly;
184 $localtax1 = $obj->localtax1;
185 $localtax2 = $obj->localtax2;
186 $localtax1_type = $obj->localtax1_type;
187 $localtax2_type = $obj->localtax2_type;
192 $sql =
"SELECT t.rowid, t.code, t.recuperableonly, t.localtax1, t.localtax2, t.localtax1_type, t.localtax2_type";
193 $sql .=
" FROM ".MAIN_DB_PREFIX.
"c_tva as t, ".MAIN_DB_PREFIX.
"c_country as c";
194 $sql .=
" WHERE t.fk_pays = c.rowid AND c.code = '".$db->escape(
$mysoc->country_code).
"'";
195 $sql .=
" AND t.taux = ".((float) $tva_tx).
" AND t.active = 1";
196 $sql .=
" AND t.code = ''";
197 $sql .=
" AND t.entity IN (".getEntity(
'c_tva').
")";
198 $resql = $db->query($sql);
200 $obj = $db->fetch_object($resql);
202 $npr = $obj->recuperableonly;
203 $localtax1 = $obj->localtax1;
204 $localtax2 = $obj->localtax2;
205 $localtax1_type = $obj->localtax1_type;
206 $localtax2_type = $obj->localtax2_type;
211 $object->default_vat_code = $vatratecode;
214 $object->localtax1_tx = $localtax1;
215 $object->localtax2_tx = $localtax2;
216 $object->localtax1_type = $localtax1_type;
217 $object->localtax2_type = $localtax2_type;
218 $object->price_label = $price_label;
230 $produit_multiprices_limit =
getDolGlobalInt(
'PRODUIT_MULTIPRICES_LIMIT');
231 for ($i = 1; $i <= $produit_multiprices_limit; $i++) {
233 if (
$object->multiprices_base_type[$i] ==
'HT') {
234 $oldprice =
$object->multiprices[$i];
235 $oldminprice =
$object->multiprices_min[$i];
237 $oldprice =
$object->multiprices_ttc[$i];
238 $oldminprice =
$object->multiprices_min_ttc[$i];
240 $oldpricebasetype =
$object->multiprices_base_type[$i];
241 $oldnpr =
$object->multiprices_recuperableonly[$i];
244 $localtaxarray = array();
246 $ret =
$object->updatePrice($oldprice, $oldpricebasetype, $user, (
float) $tva_tx, $oldminprice, $level, $oldnpr, 0, 0, $localtaxarray, $vatratecode, $price_label);
255 if (
$object->price_base_type ==
'HT') {
257 $oldminprice =
$object->price_min;
259 $oldprice =
$object->price_ttc;
260 $oldminprice =
$object->price_min_ttc;
262 $oldpricebasetype =
$object->price_base_type;
266 $localtaxarray = array();
268 $ret =
$object->updatePrice($oldprice, $oldpricebasetype, $user, (
float) $tva_tx, $oldminprice, $level, $oldnpr, 0, 0, $localtaxarray, $vatratecode, $price_label);
286 $maxpricesupplier = 0;
288 if (($action ==
'update_price' || $action ==
'update_level_price') && !$cancel && $permissiontoadd) {
290 $pricestoupdate = array();
295 $maxpricesupplier =
$object->min_recommended_price();
301 $object->fk_price_expression = empty($eid) ? 0 : $eid;
303 if (
$object->fk_price_expression != 0) {
305 require_once DOL_DOCUMENT_ROOT.
'/product/dynamic_price/class/price_parser.class.php';
308 if ($priceparser->parseProduct($object) < 0) {
317 || ($action ==
'update_level_price' &&
getDolGlobalString(
'PRODUIT_CUSTOMER_PRICES_AND_MULTIPRICES')))) {
318 $newprice =
GETPOST(
'price',
'array');
319 $newprice_min =
GETPOST(
'price_min',
'array');
320 $newpricebase =
GETPOST(
'multiprices_base_type',
'array');
321 $newvattx =
GETPOST(
'tva_tx',
'array');
322 $newvatnpr =
GETPOST(
'tva_npr',
'array');
323 $newlocaltax1_tx =
GETPOST(
'localtax1_tx',
'array');
324 $newlocaltax1_type =
GETPOST(
'localtax1_type',
'array');
325 $newlocaltax2_tx =
GETPOST(
'localtax2_tx',
'array');
326 $newlocaltax2_type =
GETPOST(
'localtax2_type',
'array');
329 $object->price_autogen = (int) (
GETPOST(
'usePriceRules') ==
'on');
331 $produit_multiprices_limit =
getDolGlobalInt(
'PRODUIT_MULTIPRICES_LIMIT');
332 for ($i = 1; $i <= $produit_multiprices_limit; $i++) {
333 if (!isset($newprice[$i])) {
337 $tva_tx_txt = $newvattx[$i];
339 $tva_tx = $tva_tx_txt;
342 if (preg_match(
'/\((.*)\)/', $tva_tx_txt, $reg)) {
343 $vat_src_code = $reg[1];
344 $tva_tx = preg_replace(
'/\s*\(.*\)/',
'', $tva_tx_txt);
346 $tva_tx =
price2num(preg_replace(
'/\*/',
'', $tva_tx));
348 $npr = preg_match(
'/\*/', $tva_tx_txt) ? 1 : 0;
349 $localtax1 = $newlocaltax1_tx[$i];
350 $localtax1_type = $newlocaltax1_type[$i];
351 $localtax2 = $newlocaltax2_tx[$i];
352 $localtax2_type = $newlocaltax2_type[$i];
353 if (preg_match(
'/\((.*)\)/', $tva_tx_txt, $reg)) {
355 $vatratecode = $reg[1];
357 $sql =
"SELECT t.rowid, t.code, t.recuperableonly, t.localtax1, t.localtax2, t.localtax1_type, t.localtax2_type";
358 $sql .=
" FROM ".MAIN_DB_PREFIX.
"c_tva as t, ".MAIN_DB_PREFIX.
"c_country as c";
359 $sql .=
" WHERE t.fk_pays = c.rowid AND c.code = '".$db->escape(
$mysoc->country_code).
"'";
360 $sql .=
" AND t.taux = ".((float) $tva_tx).
" AND t.active = 1";
361 $sql .=
" AND t.code ='".$db->escape($vatratecode).
"'";
362 $sql .=
" AND t.entity IN (".getEntity(
'c_tva').
")";
363 $resql = $db->query($sql);
365 $obj = $db->fetch_object($resql);
367 $npr = $obj->recuperableonly;
368 $localtax1 = $obj->localtax1;
369 $localtax2 = $obj->localtax2;
370 $localtax1_type = $obj->localtax1_type;
371 $localtax2_type = $obj->localtax2_type;
375 if (in_array(
$mysoc->country_code, array(
'ES'))) {
382 $sql =
"SELECT t.rowid, t.code, t.recuperableonly, t.localtax1, t.localtax2, t.localtax1_type, t.localtax2_type";
383 $sql .=
" FROM ".MAIN_DB_PREFIX.
"c_tva as t, ".MAIN_DB_PREFIX.
"c_country as c";
384 $sql .=
" WHERE t.fk_pays = c.rowid AND c.code = '".$db->escape(
$mysoc->country_code).
"'";
385 $sql .=
" AND t.taux = ".((float) $tva_tx).
" AND t.active = 1";
386 $sql .=
" AND t.code = ''";
387 $resql = $db->query($sql);
389 $obj = $db->fetch_object($resql);
391 $npr = $obj->recuperableonly;
392 $localtax1 = $obj->localtax1;
393 $localtax2 = $obj->localtax2;
394 $localtax1_type = $obj->localtax1_type;
395 $localtax2_type = $obj->localtax2_type;
400 $pricestoupdate[$i] = array(
402 'price' =>
price2num($newprice[$i],
'', 2),
403 'price_min' =>
price2num($newprice_min[$i],
'', 2),
404 'price_base_type' => $newpricebase[$i],
405 'default_vat_code' => $vatratecode,
408 'localtaxes_array' => array(
'0' => $localtax1_type,
'1' => $localtax1,
'2' => $localtax2_type,
'3' => $localtax2)
419 $newpricebase =
GETPOST(
'price_base_type',
'alpha');
420 $tva_tx_txt =
GETPOST(
'tva_tx',
'alpha');
421 $price_label =
GETPOST(
'price_label',
'alpha');
423 $tva_tx = $tva_tx_txt;
426 if (preg_match(
'/\((.*)\)/', $tva_tx_txt, $reg)) {
427 $vat_src_code = $reg[1];
428 $tva_tx = preg_replace(
'/\s*\(.*\)/',
'', $tva_tx_txt);
430 $tva_tx =
price2num(preg_replace(
'/\*/',
'', $tva_tx));
432 $npr = preg_match(
'/\*/', $tva_tx_txt) ? 1 : 0;
435 $localtax1_type =
'0';
436 $localtax2_type =
'0';
438 if (preg_match(
'/\((.*)\)/', $tva_tx_txt, $reg)) {
440 $vatratecode = $reg[1];
442 $sql =
"SELECT t.rowid, t.code, t.recuperableonly, t.localtax1, t.localtax2, t.localtax1_type, t.localtax2_type";
443 $sql .=
" FROM ".MAIN_DB_PREFIX.
"c_tva as t, ".MAIN_DB_PREFIX.
"c_country as c";
444 $sql .=
" WHERE t.fk_pays = c.rowid AND c.code = '".$db->escape(
$mysoc->country_code).
"'";
445 $sql .=
" AND t.taux = ".((float) $tva_tx).
" AND t.active = 1";
446 $sql .=
" AND t.code ='".$db->escape($vatratecode).
"'";
447 $sql .=
" AND t.entity IN (".getEntity(
'c_tva').
")";
448 $resql = $db->query($sql);
450 $obj = $db->fetch_object($resql);
452 $npr = $obj->recuperableonly;
453 $localtax1 = $obj->localtax1;
454 $localtax2 = $obj->localtax2;
455 $localtax1_type = $obj->localtax1_type;
456 $localtax2_type = $obj->localtax2_type;
460 if (in_array(
$mysoc->country_code, array(
'ES'))) {
467 $sql =
"SELECT t.rowid, t.code, t.recuperableonly, t.localtax1, t.localtax2, t.localtax1_type, t.localtax2_type";
468 $sql .=
" FROM ".MAIN_DB_PREFIX.
"c_tva as t, ".MAIN_DB_PREFIX.
"c_country as c";
469 $sql .=
" WHERE t.fk_pays = c.rowid AND c.code = '".$db->escape(
$mysoc->country_code).
"'";
470 $sql .=
" AND t.taux = ".((float) $tva_tx).
" AND t.active = 1";
471 $sql .=
" AND t.code = ''";
472 $resql = $db->query($sql);
474 $obj = $db->fetch_object($resql);
476 $npr = $obj->recuperableonly;
477 $localtax1 = $obj->localtax1;
478 $localtax2 = $obj->localtax2;
479 $localtax1_type = $obj->localtax1_type;
480 $localtax2_type = $obj->localtax2_type;
485 $pricestoupdate[0] = array(
486 'price' => $newprice,
487 'price_label' => $price_label,
488 'price_min' => $newprice_min,
489 'price_base_type' => $newpricebase,
490 'default_vat_code' => $vatratecode,
493 'localtaxes_array' => array(
'0' => $localtax1_type,
'1' => $localtax1,
'2' => $localtax2_type,
'3' => $localtax2)
502 $object->packaging = (float) $packaging;
505 foreach ($pricestoupdate as $key => $val) {
506 $newprice = $val[
'price'];
508 if ($val[
'price'] < $val[
'price_min'] && !empty(
$object->fk_price_expression)) {
509 $newprice = $val[
'price_min'];
513 $newprice_min =
price2num($val[
'price_min'],
'MU');
516 if (
getDolGlobalString(
'PRODUCT_MINIMUM_RECOMMENDED_PRICE') && $newprice_min < $maxpricesupplier) {
517 setEventMessages($langs->trans(
"MinimumPriceLimit",
price($maxpricesupplier, 0,
'', 1, - 1, - 1,
'auto')),
null,
'errors');
522 if (!array_key_exists($key,
$object->multiprices) ||
$object->multiprices[$key] != $newprice ||
$object->multiprices_min[$key] != $newprice_min ||
$object->multiprices_base_type[$key] != $val[
'price_base_type'] ||
$object->multiprices_tva_tx[$key] != $newvattx) {
523 $res =
$object->updatePrice((
float) $newprice, $val[
'price_base_type'], $user, (
float) $val[
'vat_tx'], (
float) $newprice_min, $key, $val[
'npr'], $psq, 0, $val[
'localtaxes_array'], $val[
'default_vat_code'], $val[
'price_label']);
535 $price_extralabels = $extrafields->fetch_name_optionals_label(
"product_price");
537 $sql =
"SELECT rowid";
538 $sql .=
" FROM ".$object->db->prefix().
"product_price";
539 $sql .=
" WHERE entity IN (".getEntity(
'productprice').
")";
540 $sql .=
" AND price_level=".((int) $key);
541 $sql .=
" AND fk_product = ".((int)
$object->id);
542 $sql .=
" ORDER BY date_price DESC, rowid DESC";
544 $resql =
$object->db->query($sql);
546 $lineid =
$object->db->fetch_object($resql);
549 if (!empty($lineid->rowid)) {
550 foreach ($price_extralabels as $code => $label) {
551 $code_array =
GETPOST($code,
'array');
552 $object->array_options[
'options_'.$code] = $code_array[$key];
556 $object->table_element =
'product_price';
557 $result =
$object->insertExtraFields();
560 $object->table_element =
'product';
579 $action =
'edit_price';
585 if ($action ==
'delete' && $user->hasRight(
'produit',
'supprimer')) {
593 if ($action ==
'activate_price_by_qty' && $permissiontoadd) {
605 if ($action ==
'disable_price_by_qty' && $permissiontoadd) {
617 if ($action ==
'edit_price_by_qty') {
622 if ($action ==
'update_price_by_qty' && $permissiontoadd) {
632 if (empty($quantity)) {
634 setEventMessages($langs->trans(
"ErrorFieldRequired", $langs->transnoentities(
"Qty")),
null,
'errors');
636 if (empty($newprice)) {
638 setEventMessages($langs->trans(
"ErrorFieldRequired", $langs->transnoentities(
"Price")),
null,
'errors');
642 if (
$object->price_base_type ==
'TTC') {
647 $unitPrice =
price2num((
float) $price / (
float) $quantity,
'MU');
651 $sql =
"UPDATE ".MAIN_DB_PREFIX.
"product_price_by_qty SET";
652 $sql .=
" price=".((float) $price).
",";
653 $sql .=
" unitprice=".((float) $unitPrice).
",";
654 $sql .=
" quantity=".((float) $quantity).
",";
655 $sql .=
" remise_percent=".((float) $remise_percent).
",";
656 $sql .=
" remise=".((float) $remise);
657 $sql .=
" WHERE rowid = ".((int) $rowid);
659 $result = $db->query($sql);
664 $sql =
"INSERT INTO ".MAIN_DB_PREFIX.
"product_price_by_qty (fk_product_price,price,unitprice,quantity,remise_percent,remise) values (";
665 $sql .= ((int) $priceid).
','.((float) $price).
','.((float) $unitPrice).
','.((float) $quantity).
','.((float) $remise_percent).
','.((float) $remise).
')';
667 $result = $db->query($sql);
669 if ($db->lasterrno() ==
'DB_ERROR_RECORD_ALREADY_EXISTS') {
679 if ($action ==
'delete_price_by_qty' && $permissiontoadd) {
681 if (!empty($rowid)) {
682 $sql =
"DELETE FROM ".MAIN_DB_PREFIX.
"product_price_by_qty";
683 $sql .=
" WHERE rowid = ".((int) $rowid);
685 $result = $db->query($sql);
687 setEventMessages((
'delete_price_by_qty'.$langs->transnoentities(
'MissingIds')),
null,
'errors');
691 if ($action ==
'delete_all_price_by_qty' && $permissiontoadd) {
693 if (!empty($priceid)) {
694 $sql =
"DELETE FROM ".MAIN_DB_PREFIX.
"product_price_by_qty";
695 $sql .=
" WHERE fk_product_price = ".((int) $priceid);
697 $result = $db->query($sql);
699 setEventMessages((
'delete_price_by_qty'.$langs->transnoentities(
'MissingIds')),
null,
'errors');
708 if ($action ==
'add_customer_price_confirm' && !$cancel && $prodcustprice !==
null && ($user->hasRight(
'produit',
'creer') || $user->hasRight(
'service',
'creer'))) {
709 $maxpricesupplier =
$object->min_recommended_price();
711 $update_child_soc =
GETPOSTINT(
'updatechildprice');
715 $prodcustprice->ref_customer =
GETPOST(
'ref_customer',
'alpha');
716 $prodcustprice->fk_product =
$object->id;
719 $prodcustprice->price_base_type =
GETPOST(
"price_base_type",
'alpha');
720 $prodcustprice->price_label =
GETPOST(
"price_label",
'alpha');
725 $extralabels = $extrafields->fetch_name_optionals_label(
"product_customer_price");
726 $extrafield_values = $extrafields->getOptionalsFromPost(
"product_customer_price");
728 $tva_tx_txt =
GETPOST(
"tva_tx",
'alpha');
730 $tva_tx = $tva_tx_txt;
732 if (preg_match(
'/\((.*)\)/', $tva_tx_txt, $reg)) {
733 $vat_src_code = $reg[1];
734 $tva_tx = preg_replace(
'/\s*\(.*\)/',
'', $tva_tx_txt);
736 $tva_tx =
price2num(preg_replace(
'/\*/',
'', $tva_tx));
738 $npr = preg_match(
'/\*/', $tva_tx_txt) ? 1 : 0;
741 $localtax1_type =
'0';
742 $localtax2_type =
'0';
744 if (preg_match(
'/\((.*)\)/', $tva_tx_txt, $reg)) {
746 $vatratecode = $reg[1];
748 $sql =
"SELECT t.rowid, t.code, t.recuperableonly, t.localtax1, t.localtax2, t.localtax1_type, t.localtax2_type";
749 $sql .=
" FROM ".MAIN_DB_PREFIX.
"c_tva as t, ".MAIN_DB_PREFIX.
"c_country as c";
750 $sql .=
" WHERE t.fk_pays = c.rowid AND c.code = '".$db->escape(
$mysoc->country_code).
"'";
751 $sql .=
" AND t.taux = ".((float) $tva_tx).
" AND t.active = 1";
752 $sql .=
" AND t.code ='".$db->escape($vatratecode).
"'";
753 $sql .=
" AND t.entity IN (".getEntity(
'c_tva').
")";
754 $resql = $db->query($sql);
756 $obj = $db->fetch_object($resql);
758 $npr = $obj->recuperableonly;
759 $localtax1 = $obj->localtax1;
760 $localtax2 = $obj->localtax2;
761 $localtax1_type = $obj->localtax1_type;
762 $localtax2_type = $obj->localtax2_type;
766 if (in_array(
$mysoc->country_code, array(
'ES'))) {
773 $sql =
"SELECT t.rowid, t.code, t.recuperableonly, t.localtax1, t.localtax2, t.localtax1_type, t.localtax2_type";
774 $sql .=
" FROM ".MAIN_DB_PREFIX.
"c_tva as t, ".MAIN_DB_PREFIX.
"c_country as c";
775 $sql .=
" WHERE t.fk_pays = c.rowid AND c.code = '".$db->escape(
$mysoc->country_code).
"'";
776 $sql .=
" AND t.taux = ".((float) $tva_tx).
" AND t.active = 1";
777 $sql .=
" AND t.code = ''";
778 $resql = $db->query($sql);
780 $obj = $db->fetch_object($resql);
782 $npr = $obj->recuperableonly;
783 $localtax1 = $obj->localtax1;
784 $localtax2 = $obj->localtax2;
785 $localtax1_type = $obj->localtax1_type;
786 $localtax2_type = $obj->localtax2_type;
791 $prodcustprice->default_vat_code = $vatratecode;
792 $prodcustprice->tva_tx = $tva_tx;
793 $prodcustprice->recuperableonly = $npr;
794 $prodcustprice->localtax1_tx = $localtax1;
795 $prodcustprice->localtax2_tx = $localtax2;
796 $prodcustprice->localtax1_type = $localtax1_type;
797 $prodcustprice->localtax2_type = $localtax2_type;
799 if (!($prodcustprice->fk_soc > 0)) {
800 $langs->load(
"errors");
801 setEventMessages($langs->trans(
"ErrorFieldRequired", $langs->transnoentitiesnoconv(
"ThirdParty")),
null,
'errors');
803 $action =
'add_customer_price';
805 if (
getDolGlobalString(
'PRODUCT_MINIMUM_RECOMMENDED_PRICE') && $prodcustprice->price_min < (
float) $maxpricesupplier) {
806 $langs->load(
"errors");
807 setEventMessages($langs->trans(
"MinimumPriceLimit",
price((
float) $maxpricesupplier, 0,
'', 1, -1, -1,
'auto')),
null,
'errors');
809 $action =
'add_customer_price';
814 $result = $prodcustprice->create($user, 0, $update_child_soc);
816 if (!empty($extrafield_values) && is_array($extrafield_values)) {
818 $res = $productcustomerprice->fetch($prodcustprice->id);
820 foreach ($extrafield_values as $key => $value) {
821 $productcustomerprice->array_options[$key] = $value;
823 $result2 = $productcustomerprice->insertExtraFields();
825 $prodcustprice->error = $productcustomerprice->error;
826 $prodcustprice->errors = $productcustomerprice->errors;
835 $action =
'add_customer_price';
843 if ($action ==
'delete_customer_price' && $prodcustprice !==
null && ($user->hasRight(
'produit',
'supprimer') || $user->hasRight(
'service',
'supprimer'))) {
846 $result = $prodcustprice->delete($user);
849 $db->query(
"DELETE FROM ".MAIN_DB_PREFIX.
"product_customer_price_extrafields WHERE fk_object = ".((
int) $prodcustprice->id));
864 if ($action ==
'update_customer_price_confirm' && !$cancel && $prodcustprice !==
null && ($user->hasRight(
'produit',
'creer') || $user->hasRight(
'service',
'creer'))) {
865 $maxpricesupplier =
$object->min_recommended_price();
867 $update_child_soc =
GETPOSTINT(
'updatechildprice');
872 $prodcustprice->ref_customer =
GETPOST(
'ref_customer',
'alpha');
875 $prodcustprice->price_base_type =
GETPOST(
"price_base_type",
'alpha');
876 $prodcustprice->price_label =
GETPOST(
"price_label",
'alpha');
881 $extralabels = $extrafields->fetch_name_optionals_label(
"product_customer_price");
882 $extrafield_values = $extrafields->getOptionalsFromPost(
"product_customer_price");
884 $tva_tx_txt =
GETPOST(
"tva_tx");
886 $tva_tx = $tva_tx_txt;
888 if (preg_match(
'/\((.*)\)/', $tva_tx_txt, $reg)) {
889 $vat_src_code = $reg[1];
890 $tva_tx = preg_replace(
'/\s*\(.*\)/',
'', $tva_tx_txt);
892 $tva_tx =
price2num(preg_replace(
'/\*/',
'', $tva_tx));
894 $npr = preg_match(
'/\*/', $tva_tx_txt) ? 1 : 0;
897 $localtax1_type =
'0';
898 $localtax2_type =
'0';
900 if (preg_match(
'/\((.*)\)/', $tva_tx_txt, $reg)) {
902 $vatratecode = $reg[1];
904 $sql =
"SELECT t.rowid, t.code, t.recuperableonly, t.localtax1, t.localtax2, t.localtax1_type, t.localtax2_type";
905 $sql .=
" FROM ".MAIN_DB_PREFIX.
"c_tva as t, ".MAIN_DB_PREFIX.
"c_country as c";
906 $sql .=
" WHERE t.fk_pays = c.rowid AND c.code = '".$db->escape(
$mysoc->country_code).
"'";
907 $sql .=
" AND t.taux = ".((float) $tva_tx).
" AND t.active = 1";
908 $sql .=
" AND t.code ='".$db->escape($vatratecode).
"'";
909 $sql .=
" AND t.entity IN (".getEntity(
'c_tva').
")";
910 $resql = $db->query($sql);
912 $obj = $db->fetch_object($resql);
914 $npr = $obj->recuperableonly;
915 $localtax1 = $obj->localtax1;
916 $localtax2 = $obj->localtax2;
917 $localtax1_type = $obj->localtax1_type;
918 $localtax2_type = $obj->localtax2_type;
922 if (in_array(
$mysoc->country_code, array(
'ES'))) {
929 $sql =
"SELECT t.rowid, t.code, t.recuperableonly, t.localtax1, t.localtax2, t.localtax1_type, t.localtax2_type";
930 $sql .=
" FROM ".MAIN_DB_PREFIX.
"c_tva as t, ".MAIN_DB_PREFIX.
"c_country as c";
931 $sql .=
" WHERE t.fk_pays = c.rowid AND c.code = '".$db->escape(
$mysoc->country_code).
"'";
932 $sql .=
" AND t.taux = ".((float) $tva_tx).
" AND t.active = 1";
933 $sql .=
" AND t.code = ''";
934 $resql = $db->query($sql);
936 $obj = $db->fetch_object($resql);
938 $npr = $obj->recuperableonly;
939 $localtax1 = $obj->localtax1;
940 $localtax2 = $obj->localtax2;
941 $localtax1_type = $obj->localtax1_type;
942 $localtax2_type = $obj->localtax2_type;
947 $prodcustprice->default_vat_code = $vatratecode;
948 $prodcustprice->tva_tx = $tva_tx;
949 $prodcustprice->recuperableonly = $npr;
950 $prodcustprice->localtax1_tx = $localtax1;
951 $prodcustprice->localtax2_tx = $localtax2;
952 $prodcustprice->localtax1_type = $localtax1_type;
953 $prodcustprice->localtax2_type = $localtax2_type;
955 if ($prodcustprice->price_min < $maxpricesupplier &&
getDolGlobalString(
'PRODUCT_MINIMUM_RECOMMENDED_PRICE')) {
956 setEventMessages($langs->trans(
"MinimumPriceLimit",
price($maxpricesupplier, 0,
'', 1, -1, -1,
'auto')),
null,
'errors');
958 $action =
'update_customer_price';
962 $result = $prodcustprice->update($user, 0, $update_child_soc);
964 if (!empty($extrafield_values) && is_array($extrafield_values)) {
966 $res = $productcustomerprice->fetch($prodcustprice->id);
968 foreach ($extrafield_values as $key => $value) {
969 $productcustomerprice->array_options[$key] = $value;
971 $result2 = $productcustomerprice->insertExtraFields();
973 $prodcustprice->error = $productcustomerprice->error;
974 $prodcustprice->errors = $productcustomerprice->errors;
983 $action =
'update_customer_price';
997$form =
new Form($db);
999if (!empty($id) || !empty($ref)) {
1004$title = $langs->trans(
'ProductServiceCard');
1008 $title = $langs->trans(
'Product').
" ".$shortlabel.
" - ".$langs->trans(
'SellingPrices');
1009 $helpurl =
'EN:Module_Products|FR:Module_Produits|ES:Módulo_Productos';
1012 $title = $langs->trans(
'Service').
" ".$shortlabel.
" - ".$langs->trans(
'SellingPrices');
1013 $helpurl =
'EN:Module_Services_En|FR:Module_Services|ES:Módulo_Servicios';
1016llxHeader(
'', $title, $helpurl,
'', 0, 0,
'',
'',
'',
'classforhorizontalscrolloftabs mod-product page-price');
1019$titre = $langs->trans(
"CardProduct".
$object->type);
1024$linkback =
'<a href="'.DOL_URL_ROOT.
'/product/list.php?restore_lastsearch_values=1&type='.
$object->type.
'">'.$langs->trans(
"BackToList").
'</a>';
1025$object->next_prev_filter =
"(te.fk_product_type:=:".((int)
$object->type).
")";
1028if ($user->socid && !in_array(
'product', explode(
',',
getDolGlobalString(
'MAIN_MODULES_FOR_EXTERNAL')))) {
1032dol_banner_tab($object,
'ref', $linkback, $shownav,
'ref');
1035print
'<div class="fichecenter">';
1037print
'<div class="underbanner clearboth"></div>';
1038print
'<table class="border tableforfield centpercent">';
1045 if (!empty($socid)) {
1048 $soc->fetch($socid);
1052 $typeformat =
'select;0:'.$langs->trans(
"Product").
',1:'.$langs->trans(
"Service");
1053 print
'<tr><td class="">';
1054 print (!
getDolGlobalString(
'PRODUCT_DENY_CHANGE_PRODUCT_TYPE')) ? $form->editfieldkey(
"Type",
'fk_product_type', (
string)
$object->type, $object, 0, $typeformat) : $langs->trans(
'Type');
1056 print $form->editfieldval(
"Type",
'fk_product_type',
$object->type, $object, 0, $typeformat);
1061 print
'<tr><td class="titlefieldcreate">';
1062 print $langs->trans(
"SellingPrice");
1064 print
'<td colspan="2">';
1065 if (
$object->multiprices_base_type[$soc->price_level] ==
'TTC') {
1066 print
'<span class="amount">'.price(
$object->multiprices_ttc[$soc->price_level]).
'</span>';
1068 print
'<span class="amount">'.price(
$object->multiprices[$soc->price_level]).
'</span>';
1070 if (
$object->multiprices_base_type[$soc->price_level]) {
1071 print
' '.$langs->trans(
$object->multiprices_base_type[$soc->price_level]);
1073 print
' '.$langs->trans(
$object->price_base_type);
1078 print
'<tr><td>'.$langs->trans(
"MinPrice").
'</td><td colspan="2">';
1079 if (
$object->multiprices_base_type[$soc->price_level] ==
'TTC') {
1080 print
price(
$object->multiprices_min_ttc[$soc->price_level]).
' '.$langs->trans(
$object->multiprices_base_type[$soc->price_level]);
1082 print
price(
$object->multiprices_min[$soc->price_level]).
' '.$langs->trans(empty(
$object->multiprices_base_type[$soc->price_level]) ?
'HT' :
$object->multiprices_base_type[$soc->price_level]);
1088 print
'<tr><td>'.$langs->trans(
"DefaultTaxRate").
'</td><td colspan="2">';
1090 $positiverates =
'';
1092 $positiverates .= ($positiverates ?
'/' :
'').
price2num(
$object->multiprices_tva_tx[$soc->price_level]);
1095 $positiverates .= ($positiverates ?
'/' :
'').
price2num(
$object->multiprices_localtax1_tx[$soc->price_level]);
1098 $positiverates .= ($positiverates ?
'/' :
'').
price2num(
$object->multiprices_localtax2_tx[$soc->price_level]);
1100 if (empty($positiverates)) {
1101 $positiverates =
'0';
1103 echo
vatrate($positiverates.($object->default_vat_code ?
' ('.$object->default_vat_code.
')' :
''), true,
$object->tva_npr);
1108 print
'<tr><td>'.$langs->trans(
"DefaultTaxRate").
'</td><td>';
1110 $positiverates =
'';
1115 $positiverates .= ($positiverates ?
'/' :
'').
price2num(
$object->localtax1_tx);
1118 $positiverates .= ($positiverates ?
'/' :
'').
price2num(
$object->localtax2_tx);
1120 if (empty($positiverates)) {
1121 $positiverates =
'0';
1123 echo
vatrate($positiverates.($object->default_vat_code ?
' ('.$object->default_vat_code.
')' :
''), true,
$object->tva_npr);
1131 $typeformat =
'select;0:'.$langs->trans(
"Product").
',1:'.$langs->trans(
"Service");
1132 print
'<tr><td class="">';
1133 print (!
getDolGlobalString(
'PRODUCT_DENY_CHANGE_PRODUCT_TYPE')) ? $form->editfieldkey(
"Type",
'fk_product_type', (
string)
$object->type, $object, 0, $typeformat) : $langs->trans(
'Type');
1135 print $form->editfieldval(
"Type",
'fk_product_type',
$object->type, $object, 0, $typeformat);
1140 print
'<tr><td class="titlefieldcreate">'.$langs->trans(
"DefaultTaxRate").
'</td>';
1141 print
'<td colspan="2">'.vatrate(
$object->multiprices_tva_tx[1],
true).
'</td>';
1146 $typeformat =
'select;0:'.$langs->trans(
"Product").
',1:'.$langs->trans(
"Service");
1147 print
'<tr><td class="">';
1148 print (!
getDolGlobalString(
'PRODUCT_DENY_CHANGE_PRODUCT_TYPE')) ? $form->editfieldkey(
"Type",
'fk_product_type', (
string)
$object->type, $object, 0, $typeformat) : $langs->trans(
'Type');
1150 print $form->editfieldval(
"Type",
'fk_product_type',
$object->type, $object, 0, $typeformat);
1155 print
'<!-- Default VAT Rate -->';
1156 print
'<tr><td class="titlefieldcreate">'.$langs->trans(
"DefaultTaxRate").
'</td><td>';
1159 $positiverates =
'';
1161 $positiverates .= ($positiverates ?
'<span class="opacitymedium">/</span>' :
'').
price2num(
$object->tva_tx);
1164 $positiverates .= ($positiverates ?
'<span class="opacitymedium">/</span>' :
'').
price2num(
$object->localtax1_tx);
1167 $positiverates .= ($positiverates ?
'<span class="opacitymedium">/</span>' :
'').
price2num(
$object->localtax2_tx);
1169 if (empty($positiverates)) {
1170 $positiverates =
'0';
1173 print
vatrate($positiverates.($object->default_vat_code ?
' ('.$object->default_vat_code.
')' :
''), true,
$object->tva_npr, 1);
1186 print
'<table class="liste centpercent">';
1187 print
'<tr class="liste_titre"><td>';
1188 print $langs->trans(
"PriceLevel");
1190 print
' <a class="editfielda" href="'.$_SERVER[
"PHP_SELF"].
'?action=editlabelsellingprice&token='.
newToken().
'&pricelevel='.$i.
'&id='.
$object->id.
'">'.
img_edit($langs->trans(
'EditSellingPriceLabel'), 0).
'</a>';
1193 print
'<td style="text-align: right">'.$langs->trans(
"SellingPrice").
'</td>';
1194 print
'<td style="text-align: right">'.$langs->trans(
"MinPrice").
'</td>';
1196 $extrafields->fetch_name_optionals_label(
"product_price");
1197 if ($extrafields->attributes[
"product_price"] && array_key_exists(
'label', $extrafields->attributes[
"product_price"])) {
1198 $extralabels = $extrafields->attributes[
"product_price"][
'label'];
1199 if (!empty($extralabels)) {
1200 foreach ($extralabels as $key => $value) {
1202 if (!empty($extrafields->attributes[
"product_price"][
'list'][$key]) && $extrafields->attributes[
"product_price"][
'list'][$key] != 3) {
1203 if (!empty($extrafields->attributes[
"product_price"][
'langfile'][$key])) {
1204 $langs->load($extrafields->attributes[
"product_price"][
'langfile'][$key]);
1206 if (!empty($extrafields->attributes[
"product_price"][
'help'][$key])) {
1207 $extratitle = $form->textwithpicto($langs->trans($value), $langs->trans($extrafields->attributes[
"product_price"][
'help'][$key]));
1209 $extratitle = $langs->trans($value);
1211 $field =
'ef.' . $key;
1212 print
'<td style="text-align: right">'.$extratitle.
'</td>';
1219 $produit_multiprices_limit =
getDolGlobalInt(
'PRODUIT_MULTIPRICES_LIMIT');
1220 for ($i = 1; $i <= $produit_multiprices_limit; $i++) {
1221 print
'<tr class="oddeven">';
1225 $keyforlabel =
'PRODUIT_MULTIPRICES_LABEL'.$i;
1226 if (preg_match(
'/editlabelsellingprice/', $action)) {
1227 print
'<form method="post" action="'.$_SERVER[
"PHP_SELF"].
'?id='.
$object->id.
'">';
1228 print
'<input type="hidden" name="token" value="'.newToken().
'">';
1229 print
'<input type="hidden" name="action" value="setlabelsellingprice">';
1230 print
'<input type="hidden" name="pricelevel" value="'.$i.
'">';
1231 print $langs->trans(
"SellingPrice").
' '.$i.
' - ';
1232 print
'<input class="maxwidthonsmartphone" type="text" name="labelsellingprice" value="' .
getDolGlobalString($keyforlabel).
'">';
1233 print
' <input type="submit" class="button smallpaddingimp" value="'.$langs->trans(
"Modify").
'">';
1236 print $langs->trans(
"SellingPrice").
' '.$i;
1243 if (
$object->multiprices_base_type [$i] ==
'TTC') {
1244 print
'<td class="right"><span class="amount">'.price(
$object->multiprices_ttc[$i]);
1246 print
'<td class="right"><span class="amount">'.price(
$object->multiprices[$i]);
1249 if (
$object->multiprices_base_type[$i]) {
1250 print
' '.$langs->trans(
$object->multiprices_base_type [$i]).
'</span></td>';
1252 print
' '.$langs->trans(
$object->price_base_type).
'</span></td>';
1256 print
'<td style="text-align: right">';
1257 if (empty(
$object->multiprices_base_type[$i])) {
1258 $object->multiprices_base_type[$i] =
"HT";
1260 if (
$object->multiprices_base_type[$i] ==
'TTC') {
1261 print
price(
$object->multiprices_min_ttc[$i]).
' '.$langs->trans(
$object->multiprices_base_type[$i]);
1263 print
price(
$object->multiprices_min[$i]).
' '.$langs->trans(
$object->multiprices_base_type[$i]);
1266 if (!empty($extralabels)) {
1267 $sql1 =
"SELECT rowid";
1268 $sql1 .=
" FROM ".$object->db->prefix().
"product_price";
1269 $sql1 .=
" WHERE entity IN (".getEntity(
'productprice').
")";
1270 $sql1 .=
" AND price_level=".((int) $i);
1271 $sql1 .=
" AND fk_product = ".((int)
$object->id);
1272 $sql1 .=
" ORDER BY date_price DESC, rowid DESC";
1273 $sql1 .=
" LIMIT 1";
1274 $resql1 =
$object->db->query($sql1);
1276 $lineid =
$object->db->fetch_object($resql1);
1279 $sql2 .=
" fk_object";
1280 foreach ($extralabels as $key => $value) {
1281 $sql2 .=
", ".$db->sanitize($key);
1283 $sql2 .=
" FROM ".MAIN_DB_PREFIX.
"product_price_extrafields";
1284 $sql2 .=
" WHERE fk_object = ".((int) $lineid->rowid);
1285 $resql2 = $db->query($sql2);
1287 if ($db->num_rows($resql2) != 1) {
1288 foreach ($extralabels as $key => $value) {
1289 if (!empty($extrafields->attributes[
"product_price"][
'list'][$key]) && $extrafields->attributes[
"product_price"][
'list'][$key] != 3) {
1290 print
'<td align="right"></td>';
1294 $obj = $db->fetch_object($resql2);
1295 foreach ($extralabels as $key => $value) {
1296 if (!empty($extrafields->attributes[
"product_price"][
'list'][$key]) && $extrafields->attributes[
"product_price"][
'list'][$key] != 3) {
1297 print
'<td align="right">'.$extrafields->showOutputField($key, $obj->{$key},
'',
'product_price').
"</td>";
1309 print
'<tr><td>'.$langs->trans(
"PriceByQuantity").
' '.$i;
1313 print
'</td><td colspan="2">';
1315 if (
$object->prices_by_qty[$i] == 1) {
1316 print
'<table width="50%" class="border" summary="List of quantities">';
1318 print
'<tr class="liste_titre">';
1319 print
'<td>'.$langs->trans(
"PriceByQuantityRange").
' '.$i.
'</td>';
1320 print
'<td class="right">'.$langs->trans(
"HT").
'</td>';
1321 print
'<td class="right">'.$langs->trans(
"UnitPrice").
'</td>';
1322 print
'<td class="right">'.$langs->trans(
"Discount").
'</td>';
1323 print
'<td> </td>';
1326 foreach (
$object->prices_by_qty_list[$i] as $ii => $prices) {
1327 if ($action ==
'edit_price_by_qty' && $rowid == $prices[
'rowid'] && ($user->hasRight(
'produit',
'creer') || $user->hasRight(
'service',
'creer'))) {
1328 print
'<form action="'.$_SERVER[
"PHP_SELF"].
'?id='.
$object->id.
'" method="POST">';
1329 print
'<input type="hidden" name="token" value="'.newToken().
'">';
1330 print
'<input type="hidden" name="action" value="update_price_by_qty">';
1331 print
'<input type="hidden" name="priceid" value="'.$object->prices_by_qty_id[$i].
'">';
1332 print
'<input type="hidden" value="'.$prices[
'rowid'].
'" name="rowid">';
1333 print
'<tr class="'.($ii % 2 == 0 ?
'pair' :
'impair').
'">';
1334 print
'<td><input size="5" type="text" value="'.$prices[
'quantity'].
'" name="quantity"></td>';
1335 print
'<td class="right" colspan="2"><input size="10" type="text" value="'.price2num($prices[
'price'],
'MU').
'" name="price"> '.
$object->price_base_type.
'</td>';
1336 print
'<td class="right nowraponall"><input size="5" type="text" value="'.$prices[
'remise_percent'].
'" name="remise_percent"> %</td>';
1337 print
'<td class="center"><input type="submit" value="'.$langs->trans(
"Modify").
'" class="button"></td>';
1341 print
'<tr class="'.($ii % 2 == 0 ?
'pair' :
'impair').
'">';
1342 print
'<td>'.$prices[
'quantity'].
'</td>';
1343 print
'<td class="right">'.price($prices[
'price']).
'</td>';
1344 print
'<td class="right">'.price($prices[
'unitprice']).
'</td>';
1345 print
'<td class="right">'.price($prices[
'remise_percent']).
' %</td>';
1346 print
'<td class="center">';
1347 if (($user->hasRight(
'produit',
'creer') || $user->hasRight(
'service',
'creer'))) {
1348 print
'<a class="editfielda marginleftonly marginrightonly" href="'.$_SERVER[
"PHP_SELF"].
'?id='.
$object->id.
'&action=edit_price_by_qty&token='.
newToken().
'&rowid='.$prices[
"rowid"].
'">';
1350 print
'<a class="marginleftonly marginrightonly" href="'.$_SERVER[
"PHP_SELF"].
'?id='.
$object->id.
'&action=delete_price_by_qty&token='.
newToken().
'&rowid='.$prices[
"rowid"].
'">';
1359 if ($action !=
'edit_price_by_qty' && ($user->hasRight(
'produit',
'creer') || $user->hasRight(
'service',
'creer'))) {
1360 print
'<form action="'.$_SERVER[
"PHP_SELF"].
'?id='.
$object->id.
'" method="POST">';
1361 print
'<input type="hidden" name="token" value="'.newToken().
'">';
1362 print
'<input type="hidden" name="action" value="update_price_by_qty">';
1363 print
'<input type="hidden" name="priceid" value="'.$object->prices_by_qty_id[$i].
'">';
1364 print
'<input type="hidden" value="0" name="rowid">';
1365 print
'<tr class="'.($ii % 2 == 0 ?
'pair' :
'impair').
'">';
1366 print
'<td><input size="5" type="text" value="1" name="quantity"></td>';
1367 print
'<td class="right" class="nowrap"><input size="10" type="text" value="0" name="price"> '.$object->price_base_type.
'</td>';
1368 print
'<td class="right"> </td>';
1369 print
'<td class="right" class="nowraponall"><input size="5" type="text" value="0" name="remise_percent"> %</td>';
1370 print
'<td class="center"><input type="submit" value="'.$langs->trans(
"Add").
'" class="button"></td>';
1376 print
'<a class="editfielda marginleftonly marginrightonly" href="'.$_SERVER[
'PHP_SELF'].
'?id='.
$object->id.
'&action=disable_price_by_qty&level='.$i.
'&token='.
newToken().
'">('.$langs->trans(
"DisablePriceByQty").
')</a>';
1378 print $langs->trans(
"No");
1379 print
' <a class="marginleftonly marginrightonly" href="'.$_SERVER[
'PHP_SELF'].
'?id='.
$object->id.
'&action=activate_price_by_qty&level='.$i.
'&token='.
newToken().
'">('.$langs->trans(
"Activate").
')</a>';
1388 $typeformat =
'select;0:'.$langs->trans(
"Product").
',1:'.$langs->trans(
"Service");
1389 print
'<tr><td class="">';
1390 print (!
getDolGlobalString(
'PRODUCT_DENY_CHANGE_PRODUCT_TYPE')) ? $form->editfieldkey(
"Type",
'fk_product_type', (
string)
$object->type, $object, 0, $typeformat) : $langs->trans(
'Type');
1392 print $form->editfieldval(
"Type",
'fk_product_type',
$object->type, $object, 0, $typeformat);
1397 print
'<tr><td class="titlefield">'.$langs->trans(
"DefaultTaxRate").
'</td><td>';
1399 $positiverates =
'';
1404 $positiverates .= ($positiverates ?
'/' :
'').
price2num(
$object->localtax1_tx);
1407 $positiverates .= ($positiverates ?
'/' :
'').
price2num(
$object->localtax2_tx);
1409 if (empty($positiverates)) {
1410 $positiverates =
'0';
1412 echo
vatrate($positiverates.($object->default_vat_code ?
' ('.$object->default_vat_code.
')' :
''), true,
$object->tva_npr, 0, 1);
1422 print
'<tr class="field_selling_price"><td>'.$langs->trans(
"SellingPrice").
'</td><td>';
1423 if (
$object->price_base_type ==
'TTC') {
1428 print
'<i class="opacitymedium"> - ' .
price(
$object->price_ttc).
' '.$langs->trans(
'TTC') .
'</i>';
1435 print
'<tr class="field_min_price"><td>'.$langs->trans(
"MinPrice").
'</td><td>';
1436 if (
$object->price_base_type ==
'TTC') {
1441 print
'<i class="opacitymedium"> - ' .
price(
$object->price_min_ttc).
' '.$langs->trans(
'TTC') .
'</i>';
1448 print
'<tr class="field_price_label"><td>'.$form->textwithpicto($langs->trans(
"PackagingForThisProduct"), $langs->trans(
"PackagingForThisProductDesc")).
'</td><td>';
1454 print
'<tr class="field_price_label"><td>'.$langs->trans(
"PriceLabel").
'</td><td>';
1461 print
'<tr><td>'.$langs->trans(
"PriceByQuantity");
1462 if (
$object->prices_by_qty[0] == 0) {
1463 print
' <a href="'.$_SERVER[
'PHP_SELF'].
'?id='.
$object->id.
'&action=activate_price_by_qty&level=1&token='.
newToken().
'">('.$langs->trans(
"Activate").
')';
1465 print
' <a href="'.$_SERVER[
'PHP_SELF'].
'?id='.
$object->id.
'&action=disable_price_by_qty&level=1&token='.
newToken().
'">('.$langs->trans(
"DisablePriceByQty").
')';
1469 if (
$object->prices_by_qty[0] == 1) {
1470 print
'<table width="50%" class="border" summary="List of quantities">';
1471 print
'<tr class="liste_titre">';
1473 print
'<td>'.$langs->trans(
"Quantity").
'</td>';
1474 print
'<td class="right">'.$langs->trans(
"Price").
'</td>';
1475 print
'<td class="right"></td>';
1476 print
'<td class="right">'.$langs->trans(
"UnitPrice").
'</td>';
1477 print
'<td class="right">'.$langs->trans(
"Discount").
'</td>';
1478 print
'<td> </td>';
1480 if ($action !=
'edit_price_by_qty') {
1481 print
'<form action="'.$_SERVER[
"PHP_SELF"].
'?id='.
$object->id.
'" method="POST">';
1482 print
'<input type="hidden" name="token" value="'.newToken().
'">';
1483 print
'<input type="hidden" name="action" value="update_price_by_qty">';
1484 print
'<input type="hidden" name="priceid" value="'.$object->prices_by_qty_id[0].
'">';
1485 print
'<input type="hidden" value="0" name="rowid">';
1487 print
'<tr class="'.(($ii % 2) == 0 ?
'pair' :
'impair').
'">';
1488 print
'<td><input size="5" type="text" value="1" name="quantity"></td>';
1489 print
'<td class="right"><input class="width50 right" type="text" value="0" name="price"></td>';
1493 print
'<td class="right"> </td>';
1494 print
'<td class="right nowraponall"><input type="text" class="width50 right" value="0" name="remise_percent"> %</td>';
1495 print
'<td class="center"><input type="submit" value="'.$langs->trans(
"Add").
'" class="button"></td>';
1500 foreach (
$object->prices_by_qty_list[0] as $ii => $prices) {
1501 if ($action ==
'edit_price_by_qty' && $rowid == $prices[
'rowid'] && ($user->hasRight(
'produit',
'creer') || $user->hasRight(
'service',
'creer'))) {
1502 print
'<form action="'.$_SERVER[
"PHP_SELF"].
'?id='.
$object->id.
'" method="POST">';
1503 print
'<input type="hidden" name="token" value="'.newToken().
'">';
1504 print
'<input type="hidden" name="action" value="update_price_by_qty">';
1505 print
'<input type="hidden" name="priceid" value="'.$object->prices_by_qty_id[0].
'">';
1506 print
'<input type="hidden" value="'.$prices[
'rowid'].
'" name="rowid">';
1507 print
'<tr class="'.($ii % 2 == 0 ?
'pair' :
'impair').
'">';
1508 print
'<td><input size="5" type="text" value="'.$prices[
'quantity'].
'" name="quantity"></td>';
1509 print
'<td class="right"><input class="width50 right" type="text" value="'.price2num($prices[
'price'],
'MU').
'" name="price"></td>';
1510 print
'<td class="right">';
1512 print $prices[
'price_base_type'];
1514 print
'<td class="right"> </td>';
1515 print
'<td class="right nowraponall"><input class="width50 right" type="text" value="'.$prices[
'remise_percent'].
'" name="remise_percent"> %</td>';
1516 print
'<td class="center"><input type="submit" value="'.$langs->trans(
"Modify").
'" class="button"></td>';
1520 print
'<tr class="'.($ii % 2 == 0 ?
'pair' :
'impair').
'">';
1521 print
'<td>'.$prices[
'quantity'].
'</td>';
1522 print
'<td class="right">'.price($prices[
'price']).
'</td>';
1523 print
'<td class="right">';
1525 print $prices[
'price_base_type'];
1527 print
'<td class="right">'.price($prices[
'unitprice']).
'</td>';
1528 print
'<td class="right">'.price($prices[
'remise_percent']).
' %</td>';
1529 print
'<td class="center">';
1530 if (($user->hasRight(
'produit',
'creer') || $user->hasRight(
'service',
'creer'))) {
1531 print
'<a class="editfielda marginleftonly marginrightonly" href="'.$_SERVER[
"PHP_SELF"].
'?id='.
$object->id.
'&action=edit_price_by_qty&token='.
newToken().
'&rowid='.$prices[
"rowid"].
'">';
1533 print
'<a class="marginleftonly marginrightonly" href="'.$_SERVER[
"PHP_SELF"].
'?id='.
$object->id.
'&action=delete_price_by_qty&token='.
newToken().
'&rowid='.$prices[
"rowid"].
'">';
1544 print $langs->trans(
"No");
1553print
'<div class="clearboth"></div>';
1562if (!$action || $action ==
'delete' || $action ==
'showlog_customer_price' || $action ==
'showlog_default_price' || $action ==
'add_customer_price'
1563 || $action ==
'activate_price_by_qty' || $action ==
'disable_price_by_qty') {
1564 print
"\n".
'<div class="tabsAction">'.
"\n";
1566 $parameters = array();
1567 $reshook = $hookmanager->executeHooks(
'addMoreActionsButtons', $parameters, $object, $action);
1568 if (empty($reshook)) {
1571 print
'<div class="inline-block divButAction"><a class="butActionRefused classfortooltip" href="#" title="' .
dol_escape_htmltag($langs->trans(
"NoEditVariants")) .
'">' . $langs->trans(
"UpdateDefaultPrice") .
'</a></div>';
1575 if ($user->hasRight(
'produit',
'creer') || $user->hasRight(
'service',
'creer')) {
1576 print
'<div class="inline-block divButAction"><a class="butAction" href="' . $_SERVER[
'PHP_SELF'] .
'?action=edit_price&token='.newToken().
'&id=' .
$object->id .
'">' . $langs->trans(
"UpdateDefaultPrice") .
'</a></div>';
1578 print
'<div class="inline-block divButAction"><span class="butActionRefused" title="'.dol_escape_htmltag($langs->trans(
"NotEnoughPermissions")).
'">' . $langs->trans(
"UpdateDefaultPrice") .
'</span></div>';
1583 if ($user->hasRight(
'produit',
'creer') || $user->hasRight(
'service',
'creer')) {
1584 print
'<div class="inline-block divButAction"><a class="butAction" href="' . $_SERVER[
"PHP_SELF"] .
'?action=add_customer_price&token='.newToken().
'&id=' .
$object->id .
'">' . $langs->trans(
"AddCustomerPrice") .
'</a></div>';
1586 print
'<div class="inline-block divButAction"><span class="butActionRefused" title="'.dol_escape_htmltag($langs->trans(
"NotEnoughPermissions")).
'">' . $langs->trans(
"AddCustomerPrice") .
'</span></div>';
1591 if ($user->hasRight(
'produit',
'creer') || $user->hasRight(
'service',
'creer')) {
1592 print
'<div class="inline-block divButAction"><a class="butAction" href="' . $_SERVER[
'PHP_SELF'] .
'?action=edit_vat&token='.newToken().
'&id=' .
$object->id .
'">' . $langs->trans(
"UpdateVAT") .
'</a></div>';
1594 print
'<div class="inline-block divButAction"><span class="butActionRefused" title="'.dol_escape_htmltag($langs->trans(
"NotEnoughPermissions")).
'">' . $langs->trans(
"UpdateVAT") .
'</span></div>';
1597 if ($user->hasRight(
'produit',
'creer') || $user->hasRight(
'service',
'creer')) {
1598 print
'<div class="inline-block divButAction"><a class="butAction" href="' . $_SERVER[
'PHP_SELF'] .
'?action=edit_level_price&token='.newToken().
'&id=' .
$object->id .
'">' . $langs->trans(
"UpdateLevelPrices") .
'</a></div>';
1600 print
'<div class="inline-block divButAction"><span class="butActionRefused" title="'.dol_escape_htmltag($langs->trans(
"NotEnoughPermissions")).
'">' . $langs->trans(
"UpdateLevelPrices") .
'</span></div>';
1615if ($action ==
'edit_vat' && ($user->hasRight(
'produit',
'creer') || $user->hasRight(
'service',
'creer'))) {
1618 print
'<form action="'.$_SERVER[
"PHP_SELF"].
'?id='.
$object->id.
'" method="POST">';
1619 print
'<input type="hidden" name="token" value="'.newToken().
'">';
1620 print
'<input type="hidden" name="action" value="update_vat">';
1621 print
'<input type="hidden" name="id" value="'.$object->id.
'">';
1625 print
'<table class="border centpercent">';
1628 print
'<tr><td>'.$langs->trans(
"DefaultTaxRate").
'</td><td>';
1636 print $form->buttonsSaveCancel();
1638 print
'<br></form><br>';
1641if (($action ==
'edit_price' || $action ==
'edit_level_price') &&
$object->getRights()->creer) {
1646 print
'<!-- Edit price -->'.
"\n";
1647 print
'<form action="'.$_SERVER[
"PHP_SELF"].
'?id='.
$object->id.
'" method="POST">';
1648 print
'<input type="hidden" name="token" value="'.newToken().
'">';
1649 print
'<input type="hidden" name="action" value="update_price">';
1650 print
'<input type="hidden" name="id" value="'.$object->id.
'">';
1654 print
'<div class="div-table-responsive-no-min">';
1655 print
'<table class="border centpercent">';
1658 print
'<tr><td class="titlefield">'.$langs->trans(
"DefaultTaxRate").
'</td><td>';
1664 print $langs->trans(
'PriceBase');
1667 print $form->selectPriceBaseType(
$object->price_base_type,
"price_base_type");
1674 print
'<!-- Show price mode of dynamicprices editor -->'.
"\n";
1675 print
'<tr><td>'.$langs->trans(
"PriceMode").
'</td><td>';
1676 print
img_picto(
'',
'dynamicprice',
'class="pictofixedwidth"');
1678 $price_expression_list = array(0 => $langs->trans(
"Numeric").
' <span class="opacitymedium">('.$langs->trans(
"NoDynamicPrice").
')</span>');
1679 foreach ($price_expression->list_price_expression() as $entry) {
1680 $price_expression_list[$entry->id] = $entry->title;
1682 $price_expression_preselection =
GETPOST(
'eid') ?
GETPOST(
'eid') : (
$object->fk_price_expression ?
$object->fk_price_expression :
'0');
1683 print $form->selectarray(
'eid', $price_expression_list, $price_expression_preselection);
1684 print
' <a id="expression_editor" class="classlink">'.$langs->trans(
"PriceExpressionEditor").
'</a>';
1690 <script
type=
"text/javascript">
1691 jQuery(document).ready(
function() {
1692 jQuery(
"#expression_editor").click(
function() {
1693 window.location =
"<?php echo DOL_URL_ROOT ?>/product/dynamic_price/editor.php?id=<?php echo $id ?>&tab=price&eid=" + $(
"#eid").val();
1695 jQuery(
"#eid").change(on_change);
1698 function on_change() {
1699 if ($(
"#eid").val() == 0) {
1700 jQuery(
"#price_numeric").show();
1702 jQuery(
"#price_numeric").hide();
1711 $product->fetch($id, $ref,
'',
'1');
1712 print
'<tr id="price_numeric"><td>';
1713 $text = $langs->trans(
'SellingPrice');
1714 print $form->textwithpicto($text, $langs->trans(
"PrecisionUnitIsLimitedToXDecimals",
getDolGlobalString(
'MAIN_MAX_DECIMALS_UNIT')), 1,
'help');
1716 if (
$object->price_base_type ==
'TTC') {
1717 print
'<input name="price" size="10" value="'.price($product->price_ttc).
'">';
1719 print
'<input name="price" size="10" value="'.price($product->price).
'">';
1725 $text = $langs->trans(
'MinPrice');
1726 print $form->textwithpicto($text, $langs->trans(
"PrecisionUnitIsLimitedToXDecimals",
getDolGlobalString(
'MAIN_MAX_DECIMALS_UNIT')), 1,
'help');
1728 if (
$object->price_base_type ==
'TTC') {
1729 print
'<input name="price_min" size="10" value="'.($object->price_min_ttc ?
price(
$object->price_min_ttc) :
'').
'">';
1731 print
'<input name="price_min" size="10" value="'.($object->price_min ?
price(
$object->price_min) :
'').
'">';
1734 print
' '.$langs->trans(
"MinimumRecommendedPrice",
price((
float) $maxpricesupplier, 0,
'', 1, -1, -1,
'auto')).
' '.
img_warning().
'</td>';
1742 print $form->textwithpicto($langs->trans(
"PackagingForThisProduct"), $langs->trans(
"PackagingForThisProductDesc"));
1744 $packaging =
$object->packaging;
1745 print
'<input class="flat" name="packaging" size="5" value="' . ($packaging ?
price($packaging, 0,
'', 1, -1, 2) :
'').
'">';
1752 print $langs->trans(
'PriceLabel');
1754 print
'<input name="price_label" maxlength="255" class="minwidth300 maxwidth400onsmartphone" value="'.$object->price_label.
'">';
1758 $parameters = array();
1759 $reshook = $hookmanager->executeHooks(
'formObjectOptions', $parameters, $object, $action);
1766 print $form->buttonsSaveCancel();
1769 } elseif ($action ==
'edit_level_price' &&
$object->getRights()->creer) {
1770 print
'<!-- Edit price per level -->'.
"\n"; ?>
1773 var showHidePriceRules =
function () {
1774 var otherPrices = $(
'div.fiche form table tbody tr:not(:first)');
1775 var minPrice1 = $(
'div.fiche form input[name="price_min[1]"]');
1777 if (jQuery(
'input#usePriceRules').prop(
'checked')) {
1786 jQuery(document).ready(
function () {
1787 showHidePriceRules();
1789 jQuery(
'input#usePriceRules').click(showHidePriceRules);
1794 print
'<form action="'.$_SERVER[
"PHP_SELF"].
'?id='.
$object->id.
'" method="POST">';
1795 print
'<input type="hidden" name="token" value="'.newToken().
'">';
1796 print
'<input type="hidden" name="action" value="update_level_price">';
1797 print
'<input type="hidden" name="id" value="'.$object->id.
'">';
1802 print $langs->trans(
'UseMultipriceRules').
' <input type="checkbox" id="usePriceRules" name="usePriceRules" '.(
$object->price_autogen ?
'checked' :
'').
'><br><br>';
1805 print
'<div class="div-table-responsive-no-min">';
1806 print
'<table class="noborder">';
1807 print
'<thead><tr class="liste_titre">';
1809 print
'<td>'.$langs->trans(
"PriceLevel").
'</td>';
1812 print
'<td style="text-align: center">'.$langs->trans(
"DefaultTaxRate").
'</td>';
1817 print
'<td class="center">'.$langs->trans(
"SellingPrice").
'</td>';
1819 print
'<td class="center">'.$langs->trans(
"MinPrice").
'</td>';
1826 $extrafields->fetch_name_optionals_label(
"product_price");
1827 if ($extrafields->attributes[
"product_price"] && array_key_exists(
'label', $extrafields->attributes[
"product_price"])) {
1828 $extralabels = $extrafields->attributes[
"product_price"][
'label'];
1829 if (!empty($extralabels)) {
1830 foreach ($extralabels as $key => $value) {
1832 if (!empty($extrafields->attributes[
"product_price"][
'list'][$key]) && $extrafields->attributes[
"product_price"][
'list'][$key] != 3) {
1833 if (!empty($extrafields->attributes[
"product_price"][
'langfile'][$key])) {
1834 $langs->load($extrafields->attributes[
"product_price"][
'langfile'][$key]);
1836 if (!empty($extrafields->attributes[
"product_price"][
'help'][$key])) {
1837 $extratitle = $form->textwithpicto($langs->trans($value), $langs->trans($extrafields->attributes[
"product_price"][
'help'][$key]));
1839 $extratitle = $langs->trans($value);
1841 print
'<td style="text-align: right">'.$extratitle.
'</td>';
1846 print
'</tr></thead>';
1850 $produit_multiprices_limit =
getDolGlobalInt(
'PRODUIT_MULTIPRICES_LIMIT');
1851 for ($i = 1; $i <= $produit_multiprices_limit; $i++) {
1852 print
'<tr class="oddeven">';
1854 $keyforlabel =
'PRODUIT_MULTIPRICES_LABEL'.$i;
1856 print $form->textwithpicto($text, $langs->trans(
"PrecisionUnitIsLimitedToXDecimals",
getDolGlobalString(
'MAIN_MAX_DECIMALS_UNIT')), 1,
'help');
1862 print
'<input type="hidden" name="tva_tx['.$i.
']" value="'.(
$object->default_vat_code ?
$object->tva_tx.
' ('.
$object->default_vat_code.
')' :
$object->tva_tx).
'">';
1863 print
'<input type="hidden" name="tva_npr['.$i.
']" value="'.
$object->tva_npr.
'">';
1864 print
'<input type="hidden" name="localtax1_tx['.$i.
']" value="'.
$object->localtax1_tx.
'">';
1865 print
'<input type="hidden" name="localtax1_type['.$i.
']" value="'.
$object->localtax1_type.
'">';
1866 print
'<input type="hidden" name="localtax2_tx['.$i.
']" value="'.
$object->localtax2_tx.
'">';
1867 print
'<input type="hidden" name="localtax2_type['.$i.
']" value="'.
$object->localtax2_type.
'">';
1871 print
'<td style="text-align: center">';
1877 print
'<td style="text-align: center">';
1878 if (
$object->multiprices_base_type [$i] ==
'TTC') {
1879 print
'<input name="price['.$i.
']" size="10" value="'.
price(
$object->multiprices_ttc [$i]).
'">';
1881 print
'<input name="price['.$i.
']" size="10" value="'.
price(
$object->multiprices [$i]).
'">';
1883 print
' '.$form->selectPriceBaseType(
$object->multiprices_base_type [$i],
"multiprices_base_type[".$i.
"]");
1887 print
'<td style="text-align: center">';
1888 if (
$object->multiprices_base_type [$i] ==
'TTC') {
1889 print
'<input name="price_min['.$i.
']" size="10" value="'.
price(
$object->multiprices_min_ttc [$i]).
'">';
1891 print
'<input name="price_min['.$i.
']" size="10" value="'.
price(
$object->multiprices_min [$i]).
'">';
1894 print
'<td class="left">'.$langs->trans(
"MinimumRecommendedPrice",
price((
float) $maxpricesupplier, 0,
'', 1, -1, -1,
'auto')).
' '.
img_warning().
'</td>';
1898 if (!empty($extralabels)) {
1899 $sql1 =
"SELECT rowid";
1900 $sql1 .=
" FROM ".$object->db->prefix().
"product_price";
1901 $sql1 .=
" WHERE entity IN (".getEntity(
'productprice').
")";
1902 $sql1 .=
" AND price_level=".((int) $i);
1903 $sql1 .=
" AND fk_product = ".((int)
$object->id);
1904 $sql1 .=
" ORDER BY date_price DESC, rowid DESC";
1905 $sql1 .=
" LIMIT 1";
1906 $resql1 =
$object->db->query($sql1);
1908 $lineid =
$object->db->fetch_object($resql1);
1910 if (empty($lineid->rowid)) {
1911 foreach ($extralabels as $key => $value) {
1912 if (!empty($extrafields->attributes[
"product_price"][
'list'][$key]) && ($extrafields->attributes[
"product_price"][
'list'][$key] == 1 || $extrafields->attributes[
"product_price"][
'list'][$key] == 3 || ($action ==
"edit_level_price" && $extrafields->attributes[
"product_price"][
'list'][$key] == 4))) {
1913 if (!empty($extrafields->attributes[
"product_price"][
'langfile'][$key])) {
1914 $langs->load($extrafields->attributes[
"product_price"][
'langfile'][$key]);
1917 $extravalue = GETPOSTISSET(
'options_'.$key) ? $extrafield_values[
'options_'.$key] : $obj->{$key};
1918 print
'<td align="center"><input name="'.$key.
'['.$i.
']" size="10" value="'.$extravalue.
'"></td>';
1923 $sql .=
" fk_object";
1924 foreach ($extralabels as $key => $value) {
1925 $sql .=
", ".$db->sanitize($key);
1927 $sql .=
" FROM ".MAIN_DB_PREFIX.
"product_price_extrafields";
1928 $sql .=
" WHERE fk_object = ".((int) $lineid->rowid);
1929 $resql = $db->query($sql);
1931 $obj = $db->fetch_object($resql);
1932 foreach ($extralabels as $key => $value) {
1933 if (!empty($extrafields->attributes[
"product_price"][
'list'][$key]) && ($extrafields->attributes[
"product_price"][
'list'][$key] == 1 || $extrafields->attributes[
"product_price"][
'list'][$key] == 3 || ($action ==
"edit_level_price" && $extrafields->attributes[
"product_price"][
'list'][$key] == 4))) {
1934 if (!empty($extrafields->attributes[
"product_price"][
'langfile'][$key])) {
1935 $langs->load($extrafields->attributes[
"product_price"][
'langfile'][$key]);
1938 $extravalue = (GETPOSTISSET(
'options_'.$key) ? $extrafield_values[
'options_'.$key] : $obj->{$key} ??
'');
1939 print
'<td align="center"><input name="'.$key.
'['.$i.
']" size="10" value="'.$extravalue.
'"></td>';
1956 print $form->buttonsSaveCancel();
1967 $sortfield =
GETPOST(
'sortfield',
'aZ09comma');
1968 $sortorder =
GETPOST(
'sortorder',
'aZ09comma');
1970 if (empty($page) || $page == -1) {
1973 $offset = $limit * $page;
1974 $pageprev = $page - 1;
1975 $pagenext = $page + 1;
1977 $sortorder =
"ASC,ASC";
1980 $sortfield =
"soc.nom,t.date_begin";
1984 $filter = array(
't.fk_product' => (
string)
$object->id);
1986 if (!empty($search_soc)) {
1987 $filter[
'soc.nom'] = (string) $search_soc;
1990 if ($action ==
'add_customer_price') {
1992 $maxpricesupplier =
$object->min_recommended_price();
1994 print
'<!-- add_customer_price -->';
1997 print
'<form action="'.$_SERVER[
"PHP_SELF"].
'?id='.
$object->id.
'" method="POST">';
1998 print
'<input type="hidden" name="token" value="'.newToken().
'">';
1999 print
'<input type="hidden" name="action" value="add_customer_price_confirm">';
2000 print
'<input type="hidden" name="id" value="'.$object->id.
'">';
2002 print
'<div class="tabBar tabBarWithBottom">';
2004 print
'<table class="border centpercent">';
2006 print
'<td class="fieldrequired">'.$langs->trans(
'ThirdParty').
'</td>';
2008 $filter =
'(s.client:IN:1,2,3)';
2009 print
img_picto(
'',
'company').$form->select_company(
GETPOSTINT(
'socid'),
'socid', $filter,
'SelectThirdParty', 0, 0, array(), 0,
'minwidth300');
2014 print
'<tr><td>' . $langs->trans(
'RefCustomer') .
'</td>';
2015 print
'<td><input name="ref_customer" size="12"></td></tr>';
2019 print
'<tr><td>'.$langs->trans(
"AppliedPricesFrom").
'</td><td>';
2020 print $form->selectDate(!empty($date_begin) ? $date_begin :
dol_now(),
"date_begin", 0, 0, 1,
"date_begin");
2025 print
'<tr><td>'.$langs->trans(
"AppliedPricesTo").
'</td><td>';
2026 print $form->selectDate($date_end,
"date_end", 0, 0, 1,
"date_end");
2030 print
'<tr><td class="fieldrequired">'.$langs->trans(
"DefaultTaxRate").
'</td><td>';
2035 print
'<tr><td class="fieldrequired">';
2036 print $langs->trans(
'PriceBase');
2039 print $form->selectPriceBaseType(
$object->price_base_type,
"price_base_type");
2044 print
'<tr><td class="fieldrequired">';
2045 $text = $langs->trans(
'SellingPrice');
2046 print $form->textwithpicto($text, $langs->trans(
"PrecisionUnitIsLimitedToXDecimals",
getDolGlobalString(
'MAIN_MAX_DECIMALS_UNIT')), 1,
'help');
2048 if (
$object->price_base_type ==
'TTC') {
2049 print
'<input name="price" size="10" value="'.price(
$object->price_ttc).
'">';
2051 print
'<input name="price" size="10" value="'.price(
$object->price).
'">';
2057 $text = $langs->trans(
'MinPrice');
2058 print $form->textwithpicto($text, $langs->trans(
"PrecisionUnitIsLimitedToXDecimals",
getDolGlobalString(
'MAIN_MAX_DECIMALS_UNIT')), 1,
'help');
2059 if (
$object->price_base_type ==
'TTC') {
2060 print
'<td><input name="price_min" size="10" value="'.price(
$object->price_min_ttc).
'">';
2062 print
'<td><input name="price_min" size="10" value="'.price(
$object->price_min).
'">';
2065 print
'<td class="left">'.$langs->trans(
"MinimumRecommendedPrice",
price($maxpricesupplier, 0,
'', 1, -1, -1,
'auto')).
' '.
img_warning().
'</td>';
2071 print $langs->trans(
'PriceLabel');
2073 print
'<input name="price_label" maxlength="255" class="minwidth300 maxwidth400onsmartphone" value="'.$object->price_label.
'">';
2079 print
'<tr><td>'.$langs->trans(
"Discount").
'</td><td>';
2080 print
'<input name="discount_percent" size="10" value="'.price($discount_percent).
'">';
2084 $extrafields->fetch_name_optionals_label(
"product_customer_price");
2085 $extralabels = !empty($extrafields->attributes[
"product_customer_price"][
'label']) ? $extrafields->attributes[
"product_customer_price"][
'label'] :
'';
2086 $extrafield_values = $extrafields->getOptionalsFromPost(
"product_customer_price");
2087 if (!empty($extralabels)) {
2088 if (empty($prodcustprice->id)) {
2089 foreach ($extralabels as $key => $value) {
2090 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))) {
2091 if (!empty($extrafields->attributes[
"product_customer_price"][
'langfile'][$key])) {
2092 $langs->load($extrafields->attributes[
"product_customer_price"][
'langfile'][$key]);
2095 print
'<tr><td'.($extrafields->attributes[
"product_customer_price"][
'required'][$key] ?
' class="fieldrequired"' :
'').
'>';
2096 if (!empty($extrafields->attributes[
"product_customer_price"][
'help'][$key])) {
2097 print $form->textwithpicto($langs->trans($value), $langs->trans($extrafields->attributes[
"product_customer_price"][
'help'][$key]));
2099 print $langs->trans($value);
2101 print
'</td><td>'.$extrafields->showInputField($key, GETPOSTISSET(
'options_'.$key) ? $extrafield_values[
'options_'.$key] :
'',
'',
'',
'',
'', 0,
'product_customer_price').
'</td></tr>';
2112 print
'<div class="center">';
2115 print
'<div class="marginbottomonly">';
2116 print
'<input type="checkbox" name="updatechildprice" id="updatechildprice" value="1"> ';
2117 print
'<label for="updatechildprice">'.$langs->trans(
'ForceUpdateChildPriceSoc').
'</label>';
2120 print $form->buttonsSaveCancel();
2123 } elseif ($action ==
'edit_customer_price') {
2125 $maxpricesupplier =
$object->min_recommended_price();
2127 print
'<!-- edit_customer_price -->';
2130 $result = $prodcustprice->fetch(
GETPOSTINT(
'lineid'));
2135 print
'<form action="'.$_SERVER[
"PHP_SELF"].
'?id='.
$object->id.
'" method="POST">';
2136 print
'<input type="hidden" name="token" value="'.newToken().
'">';
2137 print
'<input type="hidden" name="action" value="update_customer_price_confirm">';
2138 print
'<input type="hidden" name="lineid" value="'.$prodcustprice->id.
'">';
2140 print
'<table class="liste centpercent">';
2142 print
'<td class="titlefield fieldrequired">'.$langs->trans(
'ThirdParty').
'</td>';
2143 $staticsoc =
new Societe($db);
2144 $staticsoc->fetch($prodcustprice->fk_soc);
2145 print
"<td>".$staticsoc->getNomUrl(1).
"</td>";
2149 print
'<tr><td>' . $langs->trans(
'RefCustomer') .
'</td>';
2150 print
'<td><input name="ref_customer" size="12" value="' .
dol_escape_htmltag($prodcustprice->ref_customer) .
'"></td></tr>';
2153 print
'<tr><td>'.$langs->trans(
"AppliedPricesFrom").
'</td><td>';
2154 print $form->selectDate($prodcustprice->date_begin,
"date_begin", 0, 0, 1,
"date_begin");
2158 print
'<tr><td>'.$langs->trans(
"AppliedPricesTo").
'</td><td>';
2159 print $form->selectDate($prodcustprice->date_end,
"date_end", 0, 0, 1,
"date_end");
2163 print
'<tr><td class="fieldrequired">'.$langs->trans(
"DefaultTaxRate").
'</td><td>';
2164 print $form->load_tva(
"tva_tx", $prodcustprice->default_vat_code ? $prodcustprice->tva_tx.
' ('.$prodcustprice->default_vat_code.
')' : $prodcustprice->tva_tx,
$mysoc, null,
$object->id, $prodcustprice->recuperableonly,
$object->
type, false, 1);
2168 print
'<tr><td class="fieldrequired">';
2169 print $langs->trans(
'PriceBase');
2172 print $form->selectPriceBaseType($prodcustprice->price_base_type,
"price_base_type");
2177 print
'<tr><td class="fieldrequired">';
2178 $text = $langs->trans(
'SellingPrice');
2179 print $form->textwithpicto($text, $langs->trans(
"PrecisionUnitIsLimitedToXDecimals",
getDolGlobalString(
'MAIN_MAX_DECIMALS_UNIT')), 1,
'help');
2181 if ($prodcustprice->price_base_type ==
'TTC') {
2182 print
'<input name="price" size="10" value="'.price($prodcustprice->price_ttc).
'">';
2184 print
'<input name="price" size="10" value="'.price($prodcustprice->price).
'">';
2190 $text = $langs->trans(
'MinPrice');
2191 print $form->textwithpicto($text, $langs->trans(
"PrecisionUnitIsLimitedToXDecimals",
getDolGlobalString(
'MAIN_MAX_DECIMALS_UNIT')), 1,
'help');
2193 if ($prodcustprice->price_base_type ==
'TTC') {
2194 print
'<input name="price_min" size="10" value="'.price($prodcustprice->price_min_ttc).
'">';
2196 print
'<input name="price_min" size="10" value="'.price($prodcustprice->price_min).
'">';
2200 print
'<td class="left">'.$langs->trans(
"MinimumRecommendedPrice",
price($maxpricesupplier, 0,
'', 1, -1, -1,
'auto')).
' '.
img_warning().
'</td>';
2206 print $langs->trans(
'PriceLabel');
2208 print
'<input name="price_label" maxlength="255" class="minwidth300 maxwidth400onsmartphone" value="'.$prodcustprice->price_label.
'">';
2213 print
'<tr><td>'.$langs->trans(
"Discount").
'</td><td>';
2214 print
'<input name="discount_percent" size="10" value="'.price($prodcustprice->discount_percent).
'">';
2218 $extrafields->fetch_name_optionals_label(
"product_customer_price");
2219 $extralabels = !empty($extrafields->attributes[
"product_customer_price"][
'label']) ? $extrafields->attributes[
"product_customer_price"][
'label'] :
'';
2220 $extrafield_values = $extrafields->getOptionalsFromPost(
"product_customer_price");
2221 if (!empty($extralabels)) {
2223 foreach ($extralabels as $key => $value) {
2224 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))) {
2225 if (!empty($extrafields->attributes[
"product_customer_price"][
'langfile'][$key])) {
2226 $langs->load($extrafields->attributes[
"product_customer_price"][
'langfile'][$key]);
2229 print
'<tr><td'.($extrafields->attributes[
"product_customer_price"][
'required'][$key] ?
' class="fieldrequired"' :
'').
'>';
2230 if (!empty($extrafields->attributes[
"product_customer_price"][
'help'][$key])) {
2231 print $form->textwithpicto($langs->trans($value), $langs->trans($extrafields->attributes[
"product_customer_price"][
'help'][$key]));
2233 print $langs->trans($value);
2235 print
'</td><td>'.$extrafields->showInputField($key, GETPOSTISSET(
'options_'.$key) ? $extrafield_values[
'options_'.$key] :
'',
'',
'',
'',
'', 0,
'product_customer_price').
'</td></tr>';
2240 $sql .=
" fk_object";
2241 foreach ($extralabels as $key => $value) {
2242 $sql .=
", ".$db->sanitize($key);
2244 $sql .=
" FROM ".MAIN_DB_PREFIX.
"product_customer_price_extrafields";
2245 $sql .=
" WHERE fk_object = ".((int) $prodcustprice->id);
2246 $resql = $db->query($sql);
2248 $obj = $db->fetch_object($resql);
2249 foreach ($extralabels as $key => $value) {
2250 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))) {
2251 if (!empty($extrafields->attributes[
"product_customer_price"][
'langfile'][$key])) {
2252 $langs->load($extrafields->attributes[
"product_customer_price"][
'langfile'][$key]);
2255 print
'<tr><td'.($extrafields->attributes[
"product_customer_price"][
'required'][$key] ?
' class="fieldrequired"' :
'').
'>';
2256 if (!empty($extrafields->attributes[
"product_customer_price"][
'help'][$key])) {
2257 print $form->textwithpicto($langs->trans($value), $langs->trans($extrafields->attributes[
"product_customer_price"][
'help'][$key]));
2259 print $langs->trans($value);
2261 print
'</td><td>'.$extrafields->showInputField($key, GETPOSTISSET(
'options_'.$key) ? $extrafield_values[
'options_'.$key] : $obj->{$key},
'',
'',
'',
'', 0,
'product_customer_price');
2273 print
'<div class="center">';
2274 print
'<div class="marginbottomonly">';
2275 print
'<input type="checkbox" name="updatechildprice" id="updatechildprice" value="1"> ';
2276 print
'<label for="updatechildprice">'.$langs->trans(
'ForceUpdateChildPriceSoc').
'</label>';
2279 print $form->buttonsSaveCancel();
2281 print
'<br></form>';
2282 } elseif ($action ==
'showlog_customer_price') {
2284 print
'<!-- list of all log of prices per customer -->'.
"\n";
2286 $sortfield =
't.datec';
2287 $filter = array(
't.fk_product' => (
string)
$object->id,
't.fk_soc' => (
string)
GETPOSTINT(
'socid'));
2290 $nbtotalofrecords =
'';
2292 $nbtotalofrecords = $prodcustprice->fetchAllLog($sortorder, $sortfield, $conf->liste_limit, $offset, $filter);
2295 $result = $prodcustprice->fetchAllLog($sortorder, $sortfield, $conf->liste_limit, $offset, $filter);
2300 $option =
'&socid='.GETPOSTINT(
'socid').
'&id='.
$object->id;
2302 $staticsoc =
new Societe($db);
2305 $title = $langs->trans(
'PriceByCustomerLog');
2306 $title .=
' - '.$staticsoc->getNomUrl(1);
2308 $backbutton =
'<a class="justalink" href="'.$_SERVER[
"PHP_SELF"].
'?id='.
$object->id.
'">'.$langs->trans(
"GoBack").
'</a>';
2311 print_barre_liste($title, $page, $_SERVER[
'PHP_SELF'], $option, $sortfield, $sortorder, $backbutton, count($prodcustprice->lines), $nbtotalofrecords,
'title_accountancy.png');
2313 if (count($prodcustprice->lines) > 0) {
2314 print
'<form action="'.$_SERVER[
"PHP_SELF"].
'?id='.
$object->id.
'" method="POST">';
2315 print
'<input type="hidden" name="token" value="'.newToken().
'">';
2316 print
'<input type="hidden" name="id" value="'.$object->id.
'">';
2318 print
'<div class="div-table-responsive-no-min">';
2319 print
'<table class="liste centpercent">';
2321 print
'<tr class="liste_titre">';
2322 print
'<td>'.$langs->trans(
"ThirdParty").
'</td>';
2323 print
'<td>'.$langs->trans(
'RefCustomer').
'</td>';
2324 print
'<td>'.$langs->trans(
"AppliedPricesFrom").
'</td>';
2325 print
'<td>'.$langs->trans(
"AppliedPricesTo").
'</td>';
2326 print
'<td class="center">'.$langs->trans(
"PriceBase").
'</td>';
2327 print
'<td class="right">'.$langs->trans(
"DefaultTaxRate").
'</td>';
2328 print
'<td class="right">'.$langs->trans(
"HT").
'</td>';
2329 print
'<td class="right">'.$langs->trans(
"TTC").
'</td>';
2330 if (
$mysoc->localtax1_assuj ==
"1" ||
$mysoc->localtax2_assuj ==
"1") {
2331 print
'<td class="right">'.$langs->trans(
"INCT").
'</td>';
2333 print
'<td class="right">'.$langs->trans(
"MinPrice").
' '.$langs->trans(
"HT").
'</td>';
2334 print
'<td class="right">'.$langs->trans(
"MinPrice").
' '.$langs->trans(
"TTC").
'</td>';
2335 print
'<td class="right">'.$langs->trans(
"PriceLabel").
'</td>';
2336 print
'<td class="right">'.$langs->trans(
"Discount").
'</td>';
2337 print
'<td class="right">'.$langs->trans(
"ChangedBy").
'</td>';
2338 print
'<td>'.$langs->trans(
"DateCreation").
'</td>';
2341 foreach ($prodcustprice->lines as $line) {
2343 $staticsoc =
new Societe($db);
2344 $staticsoc->fetch($line->fk_soc);
2346 $tva_tx = $line->default_vat_code ? $line->tva_tx.
' ('.$line->default_vat_code.
')' : $line->tva_tx;
2349 if ($line->price_base_type ==
'HT') {
2352 $pu = $line->price_ttc;
2356 $localtaxarray =
getLocalTaxesFromRate($line->tva_tx.($line->default_vat_code ?
' ('.$line->default_vat_code.
')' :
''), 0, $staticsoc,
$mysoc);
2358 $resultarray =
calcul_price_total(1, $pu, 0, (
float) $line->tva_tx, 1, 1, 0, $line->price_base_type, $line->recuperableonly,
$object->type,
$mysoc, $localtaxarray);
2360 $total_ht = $resultarray[0];
2361 $total_vat = $resultarray[1];
2362 $total_localtax1 = $resultarray[9];
2363 $total_localtax2 = $resultarray[10];
2364 $total_ttc = $resultarray[2];
2366 print
'<tr class="oddeven">';
2368 print
'<td class="tdoverflowmax125">'.$staticsoc->getNomUrl(1).
"</td>";
2369 print
'<td>'.$line->ref_customer.
'</td>';
2370 print
"<td>".dol_print_date($line->date_begin,
"day",
'tzuserrel').
"</td>";
2371 print
"<td>".dol_print_date($line->date_end,
"day",
'tzuserrel').
"</td>";
2372 print
'<td class="center">'.$langs->trans($line->price_base_type).
"</td>";
2373 print
'<td class="right nowraponall">';
2375 $positiverates =
'';
2377 $positiverates .= ($positiverates ?
'/' :
'').
price2num($line->tva_tx);
2380 $positiverates .= ($positiverates ?
'/' :
'').
price2num($line->localtax1_tx);
2383 $positiverates .= ($positiverates ?
'/' :
'').
price2num($line->localtax2_tx);
2385 if (empty($positiverates)) {
2386 $positiverates =
'0';
2389 echo
vatrate($positiverates.($line->default_vat_code ?
' ('.$line->default_vat_code.
')' :
''), true, ($line->tva_npr ? $line->tva_npr : $line->recuperableonly));
2393 print
'<td class="right"><span class="amount">'.price($line->price).
"</span></td>";
2395 print
'<td class="right"><span class="amount">'.price($line->price_ttc).
"</span></td>";
2396 if (
$mysoc->localtax1_assuj ==
"1" ||
$mysoc->localtax2_assuj ==
"1") {
2397 print
'<td class="right">'.price($resultarray[2]).
'</td>';
2400 print
'<td class="right">'.price($line->price_min).
'</td>';
2401 print
'<td class="right">'.price($line->price_min_ttc).
'</td>';
2402 print
'<td class="right">'.dolPrintHTML($line->price_label).
'</td>';
2403 print
'<td class="right">'.price($line->discount_percent).
'</td>';
2406 print
'<td class="tdoverflowmax125">';
2408 if ($line->fk_user > 0) {
2409 $userstatic =
new User($db);
2410 $userstatic->fetch($line->fk_user);
2411 print $userstatic->getNomUrl(1,
'', 0, 0, 24, 0,
'login');
2415 print
"<td>".dol_print_date($line->datec,
"dayhour",
'tzuserrel').
"</td>";
2421 print $langs->trans(
'None');
2423 } elseif ($action !=
'showlog_default_price' && $action !=
'edit_price' && $action !=
'edit_level_price') {
2425 print
'<!-- list of all prices per customer -->'.
"\n";
2428 $nbtotalofrecords =
'';
2430 $nbtotalofrecords = $prodcustprice->fetchAll($sortorder, $sortfield, 0, 0, $filter);
2433 $result = $prodcustprice->fetchAll($sortorder, $sortfield, $conf->liste_limit, $offset, $filter);
2438 $option =
'&search_soc='.$search_soc.
'&id='.
$object->id;
2441 print_barre_liste($langs->trans(
'PriceByCustomer'), $page, $_SERVER [
'PHP_SELF'], $option, $sortfield, $sortorder,
'', count($prodcustprice->lines), $nbtotalofrecords,
'title_accountancy.png');
2443 print
'<form action="'.$_SERVER[
"PHP_SELF"].
'?id='.
$object->id.
'" method="POST">';
2444 print
'<input type="hidden" name="token" value="'.newToken().
'">';
2445 print
'<input type="hidden" name="id" value="'.$object->id.
'">';
2447 print
'<!-- List of prices per customer -->'.
"\n";
2448 print
'<div class="div-table-responsive-no-min">'.
"\n";
2449 print
'<table class="liste centpercent">'.
"\n";
2451 if (count($prodcustprice->lines) > 0 || $search_soc) {
2452 $extrafields->fetch_name_optionals_label(
"product_customer_price");
2453 $custom_price_extralabels = !empty($extrafields->attributes[
"product_customer_price"][
'label']) ? $extrafields->attributes[
"product_customer_price"][
'label'] :
'';
2459 if (
$mysoc->localtax1_assuj ==
"1" ||
$mysoc->localtax2_assuj ==
"1") {
2462 if (!empty($custom_price_extralabels) && is_array($custom_price_extralabels)) {
2463 $colspan += count($custom_price_extralabels);
2466 print
'<tr class="liste_titre">';
2467 print
'<td class="liste_titre"><input type="text" class="flat maxwidth125" name="search_soc" value="'.$search_soc.
'"></td>';
2468 print
'<td class="liste_titre" colspan="'.$colspan.
'"> </td>';
2470 print
'<td class="liste_titre maxwidthsearch">';
2471 $searchpicto = $form->showFilterAndCheckAddButtons(0);
2477 print
'<tr class="liste_titre">';
2478 print
'<td>'.$langs->trans(
"ThirdParty").
'</td>';
2479 print
'<td>'.$langs->trans(
'RefCustomer').
'</td>';
2480 print
'<td>'.$langs->trans(
"AppliedPricesFrom").
'</td>';
2481 print
'<td>'.$langs->trans(
"AppliedPricesTo").
'</td>';
2482 print
'<td class="center">'.$langs->trans(
"PriceBase").
'</td>';
2483 print
'<td class="right">'.$langs->trans(
"DefaultTaxRate").
'</td>';
2484 print
'<td class="right">'.$langs->trans(
"HT").
'</td>';
2485 print
'<td class="right">'.$langs->trans(
"TTC").
'</td>';
2486 if (
$mysoc->localtax1_assuj ==
"1" ||
$mysoc->localtax2_assuj ==
"1") {
2487 print
'<td class="right">'.$langs->trans(
"INCT").
'</td>';
2489 print
'<td class="right">'.$langs->trans(
"MinPrice").
' '.$langs->trans(
"HT").
'</td>';
2490 print
'<td class="right">'.$langs->trans(
"MinPrice").
' '.$langs->trans(
"TTC").
'</td>';
2491 print
'<td class="right">'.$langs->trans(
"PriceLabel").
'</td>';
2492 print
'<td class="right">'.$langs->trans(
"Discount").
'</td>';
2494 $extrafields->fetch_name_optionals_label(
"product_customer_price");
2495 if ($extrafields->attributes[
"product_customer_price"] && array_key_exists(
'label', $extrafields->attributes[
"product_customer_price"])) {
2496 $extralabels = $extrafields->attributes[
"product_customer_price"][
'label'];
2497 if (!empty($extralabels)) {
2498 foreach ($extralabels as $key => $value) {
2500 if (!empty($extrafields->attributes[
"product_customer_price"][
'list'][$key]) && $extrafields->attributes[
"product_customer_price"][
'list'][$key] != 3) {
2501 if (!empty($extrafields->attributes[
"product_customer_price"][
'langfile'][$key])) {
2502 $langs->load($extrafields->attributes[
"product_customer_price"][
'langfile'][$key]);
2504 if (!empty($extrafields->attributes[
"product_customer_price"][
'help'][$key])) {
2505 $extratitle = $form->textwithpicto($langs->trans($value), $langs->trans($extrafields->attributes[
"product_customer_price"][
'help'][$key]));
2507 $extratitle = $langs->trans($value);
2509 print
'<td style="text-align: right">'.$extratitle.
'</td>';
2514 print
'<td>'.$langs->trans(
"ChangedBy").
'</td>';
2519 if (
$object->price_base_type ==
'HT') {
2528 $resultarray =
calcul_price_total(1, $pu, 0,
$object->tva_tx, 1, 1, 0,
$object->price_base_type, 0,
$object->type,
$mysoc, $localtaxarray);
2530 $total_ht = $resultarray[0];
2531 $total_vat = $resultarray[1];
2532 $total_localtax1 = $resultarray[9];
2533 $total_localtax2 = $resultarray[10];
2534 $total_ttc = $resultarray[2];
2537 print
'<!-- PRODUIT_CUSTOMER_PRICES_AND_MULTIPRICES -->'.
"\n";
2538 print
'<tr class="oddeven">';
2539 print
'<td colspan="4">' . $langs->trans(
'Default') .
'</td>';
2541 print
'<td class="center">'.$langs->trans(
$object->price_base_type).
"</td>";
2544 print
'<td class="right nowraponall">';
2546 $positiverates =
'';
2551 $positiverates .= ($positiverates ?
'/' :
'').
price2num(
$object->localtax1_tx);
2554 $positiverates .= ($positiverates ?
'/' :
'').
price2num(
$object->localtax2_tx);
2556 if (empty($positiverates)) {
2557 $positiverates =
'0';
2559 echo
vatrate($positiverates.($object->default_vat_code ?
' ('.$object->default_vat_code.
')' :
''), true,
$object->tva_npr);
2563 print
'<td class="right"><span class="amount">'.price(
$object->price).
"</span></td>";
2565 print
'<td class="right"><span class="amount">'.price(
$object->price_ttc).
"</span></td>";
2566 if (
$mysoc->localtax1_assuj ==
"1" ||
$mysoc->localtax2_assuj ==
"1") {
2568 print
'<td class="right"><span class="amount">'.price($resultarray[2]).
'</span></td>';
2571 print
'<td class="right">'.price(
$object->price_min).
'</td>';
2572 print
'<td class="right">'.price(
$object->price_min_ttc).
'</td>';
2573 print
'<td class="right">'.dolPrintHTML(
$object->price_label).
'</td>';
2574 print
'<td class="right"></td>';
2575 print
'<td class="right"></td>';
2576 if (!empty($extralabels)) {
2577 foreach ($extralabels as $key) {
2579 if (!empty($extrafields->attributes[
"product_customer_price"][
'list'][$key]) && $extrafields->attributes[
"product_customer_price"][
'list'][$key] != 3) {
2580 print
'<td class="right"></td>';
2584 if ($user->hasRight(
'produit',
'supprimer') || $user->hasRight(
'service',
'supprimer')) {
2585 print
'<td class="nowraponall">';
2586 print
'<a class="marginleftonly marginrightonly" href="'.$_SERVER[
"PHP_SELF"].
'?action=showlog_default_price&token='.
newToken().
'&id='.
$object->id.
'">';
2587 print
img_info($langs->trans(
'PriceByCustomerLog'));
2590 print
'<a class="marginleftonly marginrightonly editfielda" href="'.$_SERVER[
"PHP_SELF"].
'?action=edit_price&token='.
newToken().
'&id='.
$object->id.
'">';
2591 print
img_edit(
'default', 0,
'style="vertical-align: middle;"');
2598 if (count($prodcustprice->lines) > 0) {
2599 foreach ($prodcustprice->lines as $line) {
2601 $staticsoc =
new Societe($db);
2602 $staticsoc->fetch($line->fk_soc);
2604 $tva_tx = $line->default_vat_code ? $line->tva_tx.
' ('.$line->default_vat_code.
')' : $line->tva_tx;
2607 if ($line->price_base_type ==
'HT') {
2610 $pu = $line->price_ttc;
2614 $localtaxarray =
getLocalTaxesFromRate($line->tva_tx.($line->default_vat_code ?
' ('.$line->default_vat_code.
')' :
''), 0, $staticsoc,
$mysoc);
2616 $resultarray =
calcul_price_total(1, $pu, 0, (
float) $line->tva_tx, 1, 1, 0, $line->price_base_type, $line->recuperableonly,
$object->type,
$mysoc, $localtaxarray);
2618 $total_ht = $resultarray[0];
2619 $total_vat = $resultarray[1];
2620 $total_localtax1 = $resultarray[9];
2621 $total_localtax2 = $resultarray[10];
2622 $total_ttc = $resultarray[2];
2624 print
'<tr class="oddeven">';
2626 print
'<td class="tdoverflowmax125">'.$staticsoc->getNomUrl(1).
"</td>";
2627 print
'<td>'.dolPrintHTML($line->ref_customer).
'</td>';
2628 print
"<td>".dol_print_date($line->date_begin,
"day",
'tzuserrel').
"</td>";
2629 print
"<td>".dol_print_date($line->date_end,
"day",
'tzuserrel').
"</td>";
2630 print
'<td class="center">'.$langs->trans($line->price_base_type).
"</td>";
2632 print
'<td class="right nowraponall">';
2634 $positiverates =
'';
2636 $positiverates .= ($positiverates ?
'/' :
'').
price2num($line->tva_tx);
2639 $positiverates .= ($positiverates ?
'/' :
'').
price2num($line->localtax1_tx);
2642 $positiverates .= ($positiverates ?
'/' :
'').
price2num($line->localtax2_tx);
2644 if (empty($positiverates)) {
2645 $positiverates =
'0';
2648 echo
vatrate($positiverates.($line->default_vat_code ?
' ('.$line->default_vat_code.
')' :
''), true, (!empty($line->tva_npr) ? $line->tva_npr : $line->recuperableonly));
2652 print
'<td class="right"><span class="amount">'.price($line->price).
"</span></td>";
2654 print
'<td class="right"><span class="amount">'.price($line->price_ttc).
"</span></td>";
2655 if (
$mysoc->localtax1_assuj ==
"1" ||
$mysoc->localtax2_assuj ==
"1") {
2657 print
'<td class="right"><span class="amount">'.price($resultarray[2]).
'</span></td>';
2660 print
'<td class="right">'.price($line->price_min).
'</td>';
2661 print
'<td class="right">'.price($line->price_min_ttc).
'</td>';
2662 print
'<td class="right">'.dolPrintHTMLForAttribute($line->price_label).
'</td>';
2663 print
'<td class="right">'.price($line->discount_percent).
'</td>';
2666 $extrafields->fetch_name_optionals_label(
"product_customer_price");
2667 $extralabels = $extrafields->attributes[
"product_customer_price"][
'label'] ?? array();
2668 if (!empty($extralabels)) {
2670 $sql .=
" fk_object";
2671 foreach ($extralabels as $key => $value) {
2672 $sql .=
", ".$db->sanitize($key);
2674 $sql .=
" FROM ".MAIN_DB_PREFIX.
"product_customer_price_extrafields";
2675 $sql .=
" WHERE fk_object = ".((int) $line->id);
2676 $resql = $db->query($sql);
2678 if ($db->num_rows($resql) != 1) {
2679 foreach ($extralabels as $key => $value) {
2680 if (!empty($extrafields->attributes[
"product_customer_price"][
'list'][$key]) && $extrafields->attributes[
"product_customer_price"][
'list'][$key] != 3) {
2685 $obj = $db->fetch_object($resql);
2686 foreach ($extralabels as $key => $value) {
2687 if (!empty($extrafields->attributes[
"product_customer_price"][
'list'][$key]) && $extrafields->attributes[
"product_customer_price"][
'list'][$key] != 3) {
2688 print
'<td align="right">'.$extrafields->showOutputField($key, $obj->{$key},
'',
'product_customer_price').
"</td>";
2697 print
'<td class="tdoverflowmax125">';
2698 if ($line->fk_user > 0) {
2699 $userstatic =
new User($db);
2700 $userstatic->fetch($line->fk_user);
2702 print $userstatic->getNomUrl(-1,
'', 0, 0, 24, 0,
'login');
2708 print
'<td class="right nowraponall">';
2709 if ($user->hasRight(
'produit',
'creer') || $user->hasRight(
'service',
'creer')) {
2710 print
'<a href="'.$_SERVER[
"PHP_SELF"].
'?action=showlog_customer_price&token='.
newToken().
'&id='.
$object->id.
'&socid='.$line->fk_soc.
'">';
2711 print
img_info($langs->trans(
'PriceByCustomerLog'));
2714 print
'<a class="marginleftonly editfielda" href="'.$_SERVER[
"PHP_SELF"].
'?action=edit_customer_price&token='.
newToken().
'&id='.
$object->id.
'&lineid='.$line->id.
'">';
2715 print
img_edit(
'default', 0,
'style="vertical-align: middle;"');
2719 if ($user->hasRight(
'produit',
'supprimer') || $user->hasRight(
'service',
'supprimer')) {
2720 print
'<a class="marginleftonly" href="'.$_SERVER[
"PHP_SELF"].
'?action=delete_customer_price&token='.
newToken().
'&id='.
$object->id.
'&lineid='.$line->id.
'">';
2721 print
img_delete(
'default',
'style="vertical-align: middle;"');
2739if ((!
getDolGlobalString(
'PRODUIT_CUSTOMER_PRICES') || $action ==
'showlog_default_price') && !in_array($action, array(
'edit_price',
'edit_level_price',
'edit_vat'))) {
2740 $sql =
"SELECT p.rowid, p.price, p.price_ttc, p.price_base_type, p.tva_tx, p.default_vat_code, p.recuperableonly, p.localtax1_tx, p.localtax1_type, p.localtax2_tx, p.localtax2_type,";
2741 $sql .=
" p.price_level, p.price_min, p.price_min_ttc,p.price_by_qty,";
2742 $sql .=
" p.date_price as dp, p.fk_price_expression, u.rowid as user_id, u.login";
2743 $sql .=
" ,p.price_label";
2744 $sql .=
" FROM ".MAIN_DB_PREFIX.
"product_price as p,";
2745 $sql .=
" ".MAIN_DB_PREFIX.
"user as u";
2746 $sql .=
" WHERE fk_product = ".((int)
$object->id);
2747 $sql .=
" AND p.entity IN (".getEntity(
'productprice').
")";
2748 $sql .=
" AND p.fk_user_author = u.rowid";
2750 $sql .=
" AND p.price_level = ".((int) $soc->price_level);
2752 $sql .=
" ORDER BY p.date_price DESC, p.rowid DESC, p.price_level ASC";
2756 $result = $db->query($sql);
2758 print
'<div class="divlogofpreviouscustomerprice">';
2760 $num = $db->num_rows($result);
2769 $ret =
$object->updatePrice((
$object->multiprices_base_type[1] ==
'TTC' ?
$object->multiprices_ttc[1] :
$object->multiprices[1]),
$object->multiprices_base_type[1], $user, (empty(
$object->multiprices_tva_tx[1]) ? 0 :
$object->multiprices_tva_tx[1]), (
$object->multiprices_base_type[1] ==
'TTC' ?
$object->multiprices_min_ttc[1] :
$object->multiprices_min[1]), 1, 0, 0, 0, array(),
$object->default_vat_code);
2771 $ret =
$object->updatePrice((
$object->price_base_type ==
'TTC' ?
$object->price_ttc :
$object->
price),
$object->price_base_type, $user,
$object->tva_tx, (
$object->price_base_type ==
'TTC' ?
$object->price_min_ttc :
$object->price_min), 0,
$object->tva_npr, 0, 0, array(),
$object->default_vat_code);
2777 $result = $db->query($sql);
2778 $num = $db->num_rows($result);
2785 $backbutton =
'<a class="justalink" href="'.$_SERVER[
"PHP_SELF"].
'?id='.
$object->id.
'">'.$langs->trans(
"GoBack").
'</a>';
2789 print_barre_liste($langs->trans(
"DefaultPriceLog"), 0, $_SERVER[
"PHP_SELF"],
'',
'',
'', $backbutton, 0, $num,
'title_accountancy.png');
2792 print_barre_liste($langs->trans(
"PriceByCustomerLog"), 0, $_SERVER[
"PHP_SELF"],
'',
'',
'',
'', 0, $num,
'title_accountancy.png');
2795 print
'<!-- List of log prices -->'.
"\n";
2796 print
'<div class="div-table-responsive">'.
"\n";
2797 print
'<table class="liste centpercent noborder">'.
"\n";
2799 print
'<tr class="liste_titre">';
2800 print
'<th>'.$langs->trans(
"AppliedPricesFrom").
'</tg>';
2803 print
'<th class="center">'.$langs->trans(
"PriceLevel").
'</th>';
2806 print
'<th class="center">'.$langs->trans(
"Type").
'</th>';
2809 print
'<th class="center">'.$langs->trans(
"PriceBase").
'</th>';
2811 print
'<th class="right">'.$langs->trans(
"DefaultTaxRate").
'</th>';
2813 print
'<th class="right">'.$langs->trans(
"HT").
'</th>';
2814 print
'<th class="right">'.$langs->trans(
"TTC").
'</th>';
2815 if (
$mysoc->localtax1_assuj ==
"1" ||
$mysoc->localtax2_assuj ==
"1") {
2816 print
'<th class="right">'.$langs->trans(
"INCT").
'</th>';
2819 print
'<th class="right">'.$langs->trans(
"PriceExpressionSelected").
'</th>';
2821 print
'<th class="right">'.$langs->trans(
"MinPrice").
' '.$langs->trans(
"HT").
'</th>';
2822 print
'<th class="right">'.$langs->trans(
"MinPrice").
' '.$langs->trans(
"TTC").
'</th>';
2823 print
'<th class="right">'.$langs->trans(
"Label").
'</th>';
2824 print
'<th>'.$langs->trans(
"ChangedBy").
'</th>';
2825 if ($user->hasRight(
'produit',
'supprimer')) {
2826 print
'<th class="right"> </th>';
2830 $notfirstlineforlevel = array();
2834 $objp = $db->fetch_object($result);
2836 print
'<tr class="oddeven">';
2838 print
"<td>".dol_print_date($db->jdate($objp->dp),
"dayhour",
'tzuserrel').
"</td>";
2842 print
'<td class="center">'.$objp->price_level.
"</td>";
2846 $type = ($objp->price_by_qty == 1) ?
'PriceByQuantity' :
'Standard';
2847 print
'<td class="center">'.$langs->trans($type).
"</td>";
2850 print
'<td class="center">';
2851 if (empty($objp->price_by_qty)) {
2852 print $langs->trans($objp->price_base_type);
2857 print
'<td class="right">';
2859 if (empty($objp->price_by_qty)) {
2860 $positiverates =
'';
2862 $positiverates .= ($positiverates ?
'/' :
'').
price2num($objp->tva_tx);
2865 $positiverates .= ($positiverates ?
'/' :
'').
price2num($objp->localtax1_tx);
2868 $positiverates .= ($positiverates ?
'/' :
'').
price2num($objp->localtax2_tx);
2870 if (empty($positiverates)) {
2871 $positiverates =
'0';
2873 echo
vatrate($positiverates.($objp->default_vat_code ?
' ('.$objp->default_vat_code.
')' :
''), true, !empty($objp->tva_npr) ? $objp->tva_npr : 0);
2886 if ($objp->price_base_type ==
'HT') {
2889 $pu = $objp->price_ttc;
2895 $resultarray =
calcul_price_total(1, $pu, 0, $objp->tva_tx, 1, 1, 0, $objp->price_base_type, $objp->recuperableonly,
$object->type,
$mysoc, $localtaxarray);
2897 $total_ht = $resultarray[0];
2898 $total_vat = $resultarray[1];
2899 $total_localtax1 = $resultarray[9];
2900 $total_localtax2 = $resultarray[10];
2901 $total_ttc = $resultarray[2];
2904 if (!empty($objp->fk_price_expression) && !empty($conf->dynamicprices->enabled)) {
2906 $res = $price_expression->fetch($objp->fk_price_expression);
2907 $title = $price_expression->title;
2908 print
'<td class="right"></td>';
2909 print
'<td class="right"></td>';
2910 if (
$mysoc->localtax1_assuj ==
"1" ||
$mysoc->localtax2_assuj ==
"1") {
2911 print
'<td class="right"></td>';
2913 print
'<td class="right">'.$title.
"</td>";
2916 print
'<td class="right">';
2917 if (empty($objp->price_by_qty)) {
2918 print
'<span class="amount">'.price($objp->price).
'</span>';
2922 print
'<td class="right">';
2923 if (empty($objp->price_by_qty)) {
2924 $price_ttc = $objp->price_ttc;
2925 print
'<span class="amount">'.price($price_ttc).
'<span>';
2928 if (
$mysoc->localtax1_assuj ==
"1" ||
$mysoc->localtax2_assuj ==
"1") {
2929 print
'<td class="right">';
2930 print $resultarray[2];
2934 print
'<td class="right"></td>';
2939 print
'<td class="right">';
2940 if (empty($objp->price_by_qty)) {
2941 print
price($objp->price_min);
2946 print
'<td class="right">';
2947 if (empty($objp->price_by_qty)) {
2948 $price_min_ttc = $objp->price_min_ttc;
2949 print
price($price_min_ttc);
2959 print
'<td class="tdoverflowmax125">';
2960 if ($objp->user_id > 0) {
2962 $userstatic =
new User($db);
2963 $userstatic->fetch($objp->user_id);
2964 print $userstatic->getNomUrl(-1,
'', 0, 0, 24, 0,
'login');
2969 if ($user->hasRight(
'produit',
'supprimer')) {
2972 if (empty($notfirstlineforlevel[$objp->price_level])) {
2973 $notfirstlineforlevel[$objp->price_level] = 1;
2981 print
'<td class="right">';
2982 if ($candelete || ($db->jdate($objp->dp) >=
dol_now())) {
2983 print
'<a href="'.$_SERVER[
"PHP_SELF"].
'?action=delete&token='.
newToken().
'&id='.
$object->id.
'&lineid='.$objp->rowid.
'">';
$id
Support class for third parties, contacts, members, users or resources.
if(! $sortfield) if(! $sortorder) $object
dolibarr_set_const($db, $name, $value, $type='chaine', $visible=0, $note='', $entity=1)
Insert a parameter (key,value) into database (delete old key then insert it again).
llxFooter($comment='', $zone='private', $disabledoutputofmessages=0)
Empty footer.
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.
Class for accessing price expression table.
Class to parse product price expressions.
File of class to manage predefined price products or services by customer.
Class to manage products or services.
const TYPE_PRODUCT
Regular product.
const TYPE_SERVICE
Service.
Class to manage third parties objects (customers, suppliers, prospects...)
Class to manage Dolibarr users.
dol_now($mode='gmt')
Return date for now.
dol_mktime($hour, $minute, $second, $month, $day, $year, $gm='auto', $check=1)
Return a timestamp date built from detailed information (by default a local PHP server timestamp) Rep...
setEventMessages($mesg, $mesgs, $style='mesgs', $messagekey='', $noduplicate=0, $attop=0)
Set event messages in dol_events session object.
vatrate($rate, $addpercent=false, $info_bits=0, $usestarfornpr=0, $html=0)
Return a string with VAT rate label formatted for view output Used into pdf and HTML pages.
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_picto($titlealt, $picto, $moreatt='', $pictoisfullpath=0, $srconly=0, $notitle=0, $alt='', $morecss='', $marginleftonlyshort=2, $allowothertags=array())
Show picto whatever it's its name (generic function)
img_warning($titlealt='default', $moreatt='', $morecss='pictowarning')
Show warning logo.
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, $morecssdiv='')
Show tabs of a record.
dolPrintHTML($s, $allowiframe=0)
Return a string (that can be on several lines) ready to be output on a HTML page.
price2num($amount, $rounding='', $option=0)
Function that return a number with universal decimal format (decimal separator is '.
dol_get_fiche_end($notab=0)
Return tab footer of a card.
price($amount, $form=0, $outlangs='', $trunc=1, $rounding=-1, $forcerounding=-1, $currency_code='')
Function to format a value into an amount for visual output Function used into PDF and HTML pages.
getDolGlobalInt($key, $default=0)
Return a Dolibarr global constant int value.
getLocalTaxesFromRate($vatrate, $local, $buyer, $seller, $firstparamisid=0)
Get type and rate of localtaxes for a particular vat rate/country of a thirdparty.
newToken()
Return the value of token currently saved into session with name 'newtoken'.
GETPOST($paramname, $check='alphanohtml', $method=0, $filter=null, $options=null, $noreplace=0)
Return value of a param into GET or POST supervariable.
dol_clone($srcobject, $native=2)
Create a clone of instance of object (new instance with same value for each properties) With native =...
dol_print_error($db=null, $error='', $errors=null)
Displays error message system with all the information to facilitate the diagnosis and the escalation...
load_fiche_titre($title, $morehtmlright='', $picto='generic', $pictoisfullpath=0, $id='', $morecssontable='', $morehtmlcenter='', $morecssonpicto='widthpictotitle')
Load a title with picto.
dol_trunc($string, $size=40, $trunc='right', $stringencoding='UTF-8', $nodot=0, $display=0)
Truncate a string to a particular length adding '…' if string larger than length.
getDolGlobalString($key, $default='')
Return a Dolibarr global constant string value.
isModEnabled($module)
Is Dolibarr module enabled.
img_edit($titlealt='default', $float=0, $other='')
Show logo edit/modify fiche.
get_localtax($vatrate, $local, $thirdparty_buyer=null, $thirdparty_seller=null, $vatnpr=0)
Return localtax rate for a particular VAT rate, when selling a product with vat $vatrate,...
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...
calcul_price_total($qty, $pu, $remise_percent_ligne, $txtva, $uselocaltax1_rate, $uselocaltax2_rate, $remise_percent_global, $price_base_type, $info_bits, $type, $seller=null, $localtaxes_array=[], $progress=100, $multicurrency_tx=1, $pu_devise=0, $multicurrency_code='')
Calculate totals (net, vat, ...) of a line.
product_prepare_head($object)
Prepare array with list of tabs.
if(preg_match('/(crypted|dolcrypt):/i', $dolibarr_main_db_pass)||!empty($dolibarr_main_db_encrypted_pass)) $conf db type
'integer', 'integer:ObjectClass:PathToClass[:AddCreateButtonOrNot[:Filter[:Sortfield]]]',...
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.